37#define MODNAME "devfs"
40#define M_PRINTF(format, args...) printf(MODNAME ": " format, ## args)
42#define BANNER "DEVFS %s\n"
44#define MAX_OPENFILES 32
45#define MAX_OPEN_DIRFILES 16
109 if((subdev > 999) || (subdev < 0))
116 name[loop++] = ((subdev / 100) % 10) +
'0';
117 name[loop++] = ((subdev / 10) % 10) +
'0';
118 name[loop++] = (subdev % 10) +
'0';
123 if(name[0] ==
'0') loop = 1;
124 if((name[0] ==
'0') && (name[1] ==
'0')) loop = 2;
146 while(dev_scan != NULL)
148 if((curr_no + dev_scan->subdev_count) > (u32)devno)
152 if(dev_scan->subdevs[subdev_loop].valid)
165 dirent->stat.size = dev_scan->subdevs[subdev_loop].extent.
loc32[0];
166 dirent->stat.hisize = dev_scan->subdevs[subdev_loop].extent.
loc32[1];
177 strcpy(dirent->name, dev_scan->node.
name);
180 return strlen(dirent->name);
184 curr_no += dev_scan->subdev_count;
186 dev_scan = dev_scan->
forw;
203 if((node == NULL) || (node->
name == NULL))
211 printf(
"create_device: Alloc Failed\n");
217 if(dev->node.
name != NULL)
219 dev->node.
name = AllocSysMemory(ALLOC_FIRST, strlen(node->
name) + 1, NULL);
220 if(dev->node.
name == NULL)
225 memcpy(dev->node.
name, node->
name, strlen(node->
name) + 1);
228 if(dev->node.
desc != NULL)
230 dev->node.
desc = AllocSysMemory(ALLOC_FIRST, strlen(node->
desc) + 1, NULL);
231 if(dev->node.
name == NULL)
233 FreeSysMemory(dev->node.
name);
237 memcpy(dev->node.
desc, node->
desc, strlen(node->
desc) + 1);
255 FreeSysMemory(dev->node.
name);
260 FreeSysMemory(dev->node.
desc);
288 while(dev_scan != NULL)
291 if(strlen(dev_scan->node.
name) <= strlen(name))
293 if(strncmp(dev_scan->node.
name, name, strlen(dev_scan->node.
name)) == 0)
298 dev_scan = dev_scan->
forw;
316 while(dev_scan != NULL)
318 if(dev_scan->hDev == hDev)
322 dev_scan = dev_scan->
forw;
348 M_PRINTF(
"open: Name is NULL\n");
352 if((name[0] ==
'\\') || (name[0] ==
'/'))
366 name_len = strlen(dev->node.
name);
368 if((
unsigned int)name_len == strlen(name))
370 M_PRINTF(
"open: No subdevice number in filename %s\n", name);
374 subdev = strtoul(&name[name_len + fn_offset], &endp, 10);
375 if(((subdev == 0) && (name[name_len + fn_offset] !=
'0'))
379 M_PRINTF(
"open: Invalid subdev number %d\n", subdev);
386 M_PRINTF(
"open: Invalid filename\n");
390 if(!dev->subdevs[subdev].valid)
393 M_PRINTF(
"open: No subdev registered\n");
398 && (dev->subdevs[subdev].open_refcount > 0))
401 M_PRINTF(
"open: Exclusive subdevice already opened\n");
405 if(dev->subdevs[subdev].open_refcount == MAX_OPENFILES)
407 M_PRINTF(
"open: Reached open file limit for sub device\n");
411 if(((mode & O_RDONLY) || ((mode & O_RDWR) == O_RDWR))
414 M_PRINTF(
"open: Read mode requested but not permitted\n");
418 if(((mode & O_WRONLY) || ((mode & O_RDWR) == O_RDWR))
421 M_PRINTF(
"open: Write mode requested but not permitted\n");
428 M_PRINTF(
"open: Allocation failure\n");
438 dev->subdevs[subdev].open_refcount++;
440 while((loop < MAX_OPENFILES) && (dev->subdevs[subdev].open_files[loop]))
444 if(loop == MAX_OPENFILES)
447 M_PRINTF(
"open: Inconsistency between number of open files and available slot\n");
451 dev->subdevs[subdev].open_files[loop] = file->
privdata;
452 dev->open_refcount++;
453 M_PRINTF(
"open: Opened device %s subdev %d\n", dev->node.
name, subdev);
457 M_PRINTF(
"open: Couldn't find the device\n");
483 if(dev->subdevs[data->subdev].open_refcount > 0)
485 dev->subdevs[data->subdev].open_refcount--;
487 if(dev->open_refcount > 0)
489 dev->open_refcount--;
493 while((loop < MAX_OPENFILES)
494 && (dev->subdevs[data->subdev].open_files[loop] != data))
499 if(loop != MAX_OPENFILES)
501 dev->subdevs[data->subdev].open_files[loop] = NULL;
505 M_PRINTF(
"close: Could not find opened file\n");
508 M_PRINTF(
"close: Closing device %s subdev %d\n", dev->node.
name, data->subdev);
555 if(dev->node.
ioctl != NULL)
559 dev_info.
data = dev->subdevs[data->subdev].data;
560 dev_info.
subdev = data->subdev;
561 dev_info.
mode = data->mode;
562 dev_info.
loc = data->loc;
602 strncpy(buf, dev->node.
desc, buflen-1);
603 *(((u8 *)buf + buflen)) = 0;
610 if(dev->node.
ioctl != NULL)
614 dev_info.
data = dev->subdevs[data->subdev].data;
615 dev_info.
subdev = data->subdev;
616 dev_info.
mode = data->mode;
617 dev_info.
loc = data->loc;
652 if((dev->node.
read != NULL)
658 dev_info.
data = dev->subdevs[data->subdev].data;
659 dev_info.
subdev = data->subdev;
660 dev_info.
mode = data->mode;
661 dev_info.
loc = data->loc;
662 bytes_read = dev->node.
read(&dev_info, buf, len);
665 data->loc.loc64 += (u64) bytes_read;
699 if((dev->node.
write != NULL)
705 dev_info.
data = dev->subdevs[data->subdev].data;
706 dev_info.
subdev = data->subdev;
707 dev_info.
mode = data->mode;
708 dev_info.
loc = data->loc;
709 bytes_written = dev->node.
write(&dev_info, buf, len);
710 if(bytes_written > 0)
712 data->loc.loc64 += (u64) bytes_written;
714 return bytes_written;
747 case SEEK_SET:
if(loc > 0)
748 data->loc.loc64 = (u64) loc;
750 case SEEK_CUR:
if(loc > 0)
751 data->loc.loc64 += (u64) loc;
752 else if((u64)((s64) -loc) < data->loc.loc64)
753 data->loc.loc64 += (s64) loc;
755 case SEEK_END:
if((loc > 0)
756 && (dev->subdevs[data->subdev].extent.
loc64 >= (u64) loc))
757 data->loc.loc64 = dev->subdevs[data->subdev].extent.
loc64 - (u64) loc;
759 default:
return -
EPERM;
767 return data->loc.loc32[0];
795 case SEEK_SET:
if(loc > 0)
796 data->loc.loc64 = (u64) loc;
798 case SEEK_CUR:
if(loc > 0)
799 data->loc.loc64 += (u64) loc;
800 else if((u64)((s64) -loc) < data->loc.loc64)
801 data->loc.loc64 += (s64) loc;
803 case SEEK_END:
if((loc > 0) && (dev->subdevs[data->subdev].extent.
loc64 >= (u64) loc))
804 data->loc.loc64 = dev->subdevs[data->subdev].extent.
loc64 - (u64) loc;
806 default:
return -
EPERM;
815 return data->loc.loc32[0];
827 if((name == NULL) || ((name[0] !=
'\\') && (name[0] !=
'/')))
829 M_PRINTF(
"dopen: Not a valid directory name\n");
834 for(dir_loop = 0; dir_loop < MAX_OPEN_DIRFILES; dir_loop++)
836 if(!open_dirfiles[dir_loop].opened)
838 open_dirfiles[dir_loop].
devno = 0;
840 file->
privdata = &open_dirfiles[dir_loop];
869int devfs_dread(
iop_file_t *file, fio_dirent_t *buf)
913 if((name[0] ==
'\\') || (name[0] ==
'/'))
931 name_len = strlen(dev->node.
name);
933 if((
unsigned int)name_len == strlen(name))
935 M_PRINTF(
"getstat: No subdevice number in filename %s\n", name);
939 subdev = strtoul(&name[name_len + fn_offset], &endp, 10);
940 if(((subdev == 0) && (name[name_len + fn_offset] !=
'0'))
944 M_PRINTF(
"getstat: Invalid subdev number %d\n", subdev);
951 M_PRINTF(
"getstat: Invalid filename\n");
955 if(!dev->subdevs[subdev].valid)
957 M_PRINTF(
"getstat: No subdev registered\n");
962 memset(stat, 0,
sizeof(fio_stat_t));
966 stat->size = dev->subdevs[subdev].extent.
loc32[0];
967 stat->hisize = dev->subdevs[subdev].extent.
loc32[1];
982IOMANX_RETURN_VALUE_IMPL(0);
983IOMANX_RETURN_VALUE_IMPL(
EPERM);
986 IOMANX_RETURN_VALUE(0),
987 IOMANX_RETURN_VALUE(0),
988 IOMANX_RETURN_VALUE(
EPERM),
992 IOMANX_RETURN_VALUE(
EPERM),
993 IOMANX_RETURN_VALUE(
EPERM),
995 IOMANX_RETURN_VALUE(
EPERM),
996 IOMANX_RETURN_VALUE(
EPERM),
997 IOMANX_RETURN_VALUE(
EPERM),
1002 IOMANX_RETURN_VALUE(
EPERM),
1003 IOMANX_RETURN_VALUE(
EPERM),
1004 IOMANX_RETURN_VALUE(
EPERM),
1005 IOMANX_RETURN_VALUE(
EPERM),
1006 IOMANX_RETURN_VALUE(
EPERM),
1007 IOMANX_RETURN_VALUE(
EPERM),
1008 IOMANX_RETURN_VALUE_S64(
EPERM),
1009 IOMANX_RETURN_VALUE(
EPERM),
1010 IOMANX_RETURN_VALUE(
EPERM),
1011 IOMANX_RETURN_VALUE(
EPERM),
1019 "PS2 Device FS Driver",
1034 DelDrv(devfs_device.name);
1036 return AddDrv(&devfs_device);
1046 int res = MODULE_NO_RESIDENT_END;
1052 printf(BANNER, VERSION);
1054 if ((err = RegisterLibraryEntries(&_exp_devfs)) != 0) {
1055 M_PRINTF(
"Library is already registered, exiting.\n");
1056 printf(
"err=%d\n", err);
1060 res =
init_devfs() ? MODULE_NO_RESIDENT_END : MODULE_RESIDENT_END;
1063 M_PRINTF(
"devfs_device_t size=%d\n", (
int)(
sizeof(
devfs_device_t)));
1064 M_PRINTF(
"Driver loaded.\n");
1079 if((name == NULL) || (name[0] == 0))
1091 while(name[str_loop])
1095 ch = name[str_loop];
1096 if(((ch >=
'a') && (ch <=
'z')) || ((ch >=
'A') && (ch <=
'Z')))
1118 M_PRINTF(
"AddDevice: node == NULL\n");
1124 M_PRINTF(
"AddDevice: node name invalid\n");
1130 M_PRINTF(
"AddDevice: cannot add new device. Already exists\n");
1137 M_PRINTF(
"AddDevice: failed to allocate device structure\n");
1147 while(dev_scan->
forw)
1149 dev_scan = dev_scan->
forw;
1151 dev_scan->
forw = dev;
1152 dev->back = dev_scan;
1155 dev->hDev = dev_count++;
1157 M_PRINTF(
"AddDevice: Registered device (%s)\n", node->
name);
1182 for(openfile_loop = 0; openfile_loop < MAX_OPENFILES; openfile_loop++)
1184 if(dev->subdevs[subdev_loop].open_files[openfile_loop])
1186 dev->subdevs[subdev_loop].open_files[openfile_loop]->
dev = NULL;
1224 M_PRINTF(
"AddSubDevice: Sub device number too big\n");
1228 if(dev->subdevs[subdev_no].valid)
1230 M_PRINTF(
"AddSubDevice: Sub device already created\n");
1234 dev->subdevs[subdev_no].data = data;
1235 dev->subdevs[subdev_no].valid = 1;
1236 dev->subdevs[subdev_no].mode = mode;
1237 dev->subdevs[subdev_no].open_refcount = 0;
1238 dev->subdevs[subdev_no].extent = extent;
1239 memset(dev->subdevs[subdev_no].open_files, 0,
sizeof(
ioman_data_t *) * MAX_OPENFILES);
1240 dev->subdev_count++;
1244 M_PRINTF(
"AddSubDevice: Couldn't find device ID\n");
1264 M_PRINTF(
"DelSubDevice: Sub device number too big\n");
1268 if(!dev->subdevs[subdev_no].valid)
1270 M_PRINTF(
"DelSubDevice: Sub device not created\n");
1274 dev->subdevs[subdev_no].data = NULL;
1275 dev->subdevs[subdev_no].valid = 0;
1276 dev->subdevs[subdev_no].mode = 0;
1277 dev->subdevs[subdev_no].open_refcount = 0;
1278 dev->subdevs[subdev_no].extent.
loc64= 0;
1279 for(openfile_loop = 0; openfile_loop < MAX_OPENFILES; openfile_loop++)
1281 if(dev->subdevs[subdev_no].open_files[openfile_loop])
1283 dev->subdevs[subdev_no].open_files[openfile_loop]->
dev = NULL;
1284 dev->subdevs[subdev_no].open_files[openfile_loop] = NULL;
1287 dev->subdev_count--;
int devfs_dopen(iop_file_t *file, const char *name)
int devfs_lseek64(iop_file_t *file, long long loc, int whence)
int devfs_getstat(iop_file_t *file, const char *name, iox_stat_t *stat)
int devfs_check_devname(const char *name)
int devfs_write(iop_file_t *file, void *buf, int len)
int devfs_lseek(iop_file_t *file, long loc, int whence)
int devfs_delete_device(devfs_device_t *dev)
const char * devfs_subdev_to_str(int subdev)
int _start(int argc, char *argv[])
int devfs_close(iop_file_t *file)
int devfs_dclose(iop_file_t *file)
int devfs_ioctl(iop_file_t *file, int cmd, void *args)
devfs_device_t * root_device
devfs_device_t * devfs_create_device(const devfs_node_t *node)
struct _devfs_device * forw
int devfs_open(iop_file_t *file, const char *name, int mode, int unused)
int devfs_ioctl2(iop_file_t *file, int cmd, void *args, unsigned int arglen, void *buf, unsigned int buflen)
devfs_device_t * devfs_find_devicename(const char *name)
int devfs_read(iop_file_t *file, void *buf, int len)
devfs_device_t * devfs_find_deviceid(HDEV hDev)
int devfs_fill_dirent(iox_dirent_t *dirent, int devno)
HDEV DevFSAddDevice(const devfs_node_t *node)
#define DEVFS_MAX_DESC_LENGTH
int DevFSAddSubDevice(HDEV hDev, u32 subdev_no, s32 mode, devfs_loc_t extent, void *data)
#define DEVFS_IOCTL_TYPE_1
int DevFSDelDevice(HDEV hDev)
#define DEVFS_MAX_SUBDEVS
#define DEVFS_MAX_DEVNAME_LENGTH
int DevFSDelSubDevice(HDEV hDev, u32 subdev_no)
#define DEVFS_IOCTL_GETDESC
#define DEVFS_IOCTL_TYPE_2