12#include <irx_imports.h>
15#define MODNAME "subfile_driver"
19static int subfile_op_open(
iop_file_t *f,
const char *name,
int mode);
21static int subfile_op_read(
iop_file_t *f,
void *ptr,
int size);
22static int subfile_op_lseek(
iop_file_t *f,
int pos,
int mode);
32IOMAN_RETURN_VALUE_IMPL(0);
35 IOMAN_RETURN_VALUE(0),
36 IOMAN_RETURN_VALUE(0),
37 IOMAN_RETURN_VALUE(0),
41 IOMAN_RETURN_VALUE(0),
43 IOMAN_RETURN_VALUE(0),
44 IOMAN_RETURN_VALUE(0),
45 IOMAN_RETURN_VALUE(0),
46 IOMAN_RETURN_VALUE(0),
47 IOMAN_RETURN_VALUE(0),
48 IOMAN_RETURN_VALUE(0),
49 IOMAN_RETURN_VALUE(0),
50 IOMAN_RETURN_VALUE(0),
51 IOMAN_RETURN_VALUE(0),
63int _start(
int ac,
char *av[])
70 memset(subfile_info, 0,
sizeof(subfile_info));
71 for ( i = 0; i < (int)(
sizeof(subfile_info) /
sizeof(subfile_info[0])); i += 1 )
73 subfile_info[i].m_fd = -1;
76 tmpbuf = AllocSysMemory(ALLOC_LAST, 0x4000, NULL);
79 return MODULE_NO_RESIDENT_END;
80 return (AddDrv(&subfile_dev) < 0) ? MODULE_NO_RESIDENT_END : MODULE_RESIDENT_END;
83static int subfile_op_open(
iop_file_t *f,
const char *name,
int mode)
91 char curfilename[128];
97 curfilename[0] =
'\x00';
99 for ( i = 0; name[i]; ++i )
105 curfilename[i] = (name[i] !=
',') ? name[i] :
'\x00';
106 if ( curfilename[i] ==
'\x00' )
116 if ( name[i] ==
',' )
125 if ( name[i] <
'A' || name[i] >
'F' )
127 namechr_int = name[i] -
'7';
131 namechr_int = name[i] -
'0';
134 cur_baseoffset = 16 * cur_baseoffset + namechr_int;
136 cur_totalsize = 16 * cur_totalsize + namechr_int;
141 cur_fd = open(curfilename, FIO_O_RDONLY);
147 for ( i = 0; i < (int)(
sizeof(subfile_info) /
sizeof(subfile_info[0])) && subfile_info[i].m_fd >= 0; i += 1 )
150 if ( i >= (
int)(
sizeof(subfile_info) /
sizeof(subfile_info[0])) )
156 subfile_info[i].m_fd = cur_fd;
157 subfile_info[i].m_baseoffset = cur_baseoffset;
158 subfile_info[i].m_totalsize = cur_totalsize;
159 subfile_info[i].m_curpos = 0;
170 if ( privdata == NULL )
174 close(privdata->m_fd);
180static int subfile_op_read(
iop_file_t *f,
void *ptr,
int size)
185 int baseoffs_plus_curpos_size;
188 if ( privdata == NULL )
192 if ( ((uiptr)ptr & 3) != 0 )
196 for ( size_tmp = (privdata->m_totalsize - privdata->m_curpos < size) ? privdata->m_totalsize - privdata->m_curpos :
200 size_tmp -= baseoffs_plus_curpos_size, i += baseoffs_plus_curpos_size )
202 int baseoffs_plus_curpos;
203 int baseoffs_plus_curpos_chunk;
204 u32 baseoffs_plus_curpos_sub;
205 int baseoffs_plus_curpos_mask;
207 baseoffs_plus_curpos = privdata->m_baseoffset + privdata->m_curpos + i;
208 baseoffs_plus_curpos_chunk = baseoffs_plus_curpos & ~0x1FF;
209 baseoffs_plus_curpos_sub = privdata->m_baseoffset + privdata->m_totalsize - baseoffs_plus_curpos_chunk;
210 baseoffs_plus_curpos_mask = baseoffs_plus_curpos_sub & 0x1FF;
211 if ( (u32)(size_tmp + 0x400) < baseoffs_plus_curpos_sub )
213 baseoffs_plus_curpos_sub = size_tmp + 0x400;
214 baseoffs_plus_curpos_mask = baseoffs_plus_curpos_sub & 0x1FF;
216 if ( baseoffs_plus_curpos_mask )
217 baseoffs_plus_curpos_sub = (baseoffs_plus_curpos_sub + 0x1FF) & ~0x1FF;
218 if ( baseoffs_plus_curpos_sub > 0x4000 )
220 baseoffs_plus_curpos_sub = 0x4000;
222 baseoffs_plus_curpos_size = (baseoffs_plus_curpos_chunk + baseoffs_plus_curpos_sub) - baseoffs_plus_curpos;
223 if ( size_tmp < baseoffs_plus_curpos_size )
224 baseoffs_plus_curpos_size = size_tmp;
225 lseek(privdata->m_fd, baseoffs_plus_curpos_chunk, FIO_SEEK_SET);
226 read(privdata->m_fd, tmpbuf, baseoffs_plus_curpos_sub);
227 memcpy((u8 *)ptr + i, (u8 *)tmpbuf + (baseoffs_plus_curpos & 0x1FF), baseoffs_plus_curpos_size);
229 privdata->m_curpos += i;
233static int subfile_op_lseek(
iop_file_t *f,
int pos,
int mode)
241 if ( privdata == NULL )
249 offs_relative = privdata->m_curpos;
252 offs_relative = privdata->m_totalsize;
257 m_totalsize = privdata->m_totalsize;
258 pos_plus_curpos = pos + offs_relative;
259 if ( (
int)m_totalsize >= pos_plus_curpos )
262 if ( pos_plus_curpos >= 0 )
263 m_totalsize = pos_plus_curpos;
265 privdata->m_curpos = m_totalsize;
int CpuResumeIntr(int state)
int CpuSuspendIntr(int *state)