PS2SDK
PS2 Homebrew Libraries
Loading...
Searching...
No Matches
cdvdfsv.c
1/*
2# _____ ___ ____ ___ ____
3# ____| | ____| | | |____|
4# | ___| |____ ___| ____| | \ PS2DEV Open Source Project.
5#-----------------------------------------------------------------------
6# Copyright ps2dev - http://www.ps2dev.org
7# Licenced under Academic Free License version 2.0
8# Review ps2sdk README & LICENSE files for further details.
9*/
10
11#include "irx_imports.h"
12
13#include <cdvd-ioctl.h>
14#include <kerr.h>
15#include <libcdvd-rpc.h>
16
17IRX_ID("cdvd_ee_driver", 2, 38);
18// Based on the module from SCE SDK 3.1.0.
19
20extern struct irx_export_table _exp_cdvdfsv;
21
22static int cdvdfsv_init();
23static void cdvdfsv_main_th(void *arg);
24int *cdvdfsv_dummyentry(int arg1);
25static void cdvdfsv_parseargs(int ac, char **av);
26static void cdvdfsv_poffloop();
27static void cdvdfsv_rpc1_th(void *arg);
28static void cdvdfsv_rpc3_th(void *arg);
29static void cdvdfsv_rpc2_th(void *arg);
30unsigned int optimized_memcpy(char *dst, const char *src, unsigned int n);
31
32static int g_cdvdfsv_def_pri = 81;
33static int g_verbose_level = 0;
34static int g_cdvdfsv_spinctl = -1;
35static int g_cdvdfsv_plbreak = 0;
36static int g_cdvdfsv_nopocm = 0;
37static int g_cdvdfsv_rpc5flg = 0;
38static int g_cdvdfsv_rpc3flg = 0;
39#if 0
40static iop_library_t g_modload_libinfo = { NULL, NULL, 256, 0, "modload", { NULL } };
41#endif
42static int g_cdvdfsv_r2retry = 0;
43static int g_cdvdfsv_r2count = 0;
44static int g_cdvdfsv_sid_err_recover_cnt = 0;
45static int g_cdvdfsv_err_count = 0;
46static void *g_cdvdfsv_fsvrbuf;
47static char *g_cdvdfsv_rtocbuf;
48static SifDmaTransfer_t g_cdvdfsv_fssdd;
49static SifDmaTransfer_t g_cdvdfsv_iomrsdd;
50static SifDmaTransfer_t g_cdvdfsv_rdp2sdd;
51static SifDmaTransfer_t g_cdvdfsv_multi_dmat[16];
52static sceCdRMode g_cdvdfsv_rmodeee;
53static SifDmaTransfer_t g_cdvdfsv_datasdd;
54static SifDmaTransfer_t g_cdvdfsv_eerpsdd;
55static SifDmaTransfer_t g_cdvdfsv_chrdsdd;
56static SifDmaTransfer_t g_cdvdfsv_eereadfull_dma1;
57static SifDmaTransfer_t g_cdvdfsv_eereadfull_dma2;
58static SifDmaTransfer_t g_cdvdfsv_rtocsdd;
59static iop_sys_clock_t g_cdvdfsv_read_timeout;
60static int g_cdvdman_intr_efid;
61static int g_scmd_evid;
62static int g_cdvdfsv_thids[4];
63static cdvdman_internal_struct_t *g_cdvdman_istruct_ptr;
64static cdvdfsv_rpc1_outpacket_t g_cdvdfsv_initres;
65static cdvdfsv_unaligned_data_outpacket_t g_cdvdfsv_eereadx;
66static SifRpcDataQueue_t g_rpc_qdata2;
67static SifRpcDataQueue_t g_rpc_qdata1;
68static SifRpcDataQueue_t g_rpc_qdata3;
69static SifRpcServerData_t g_rpc_sdata1;
70static SifRpcServerData_t g_rpc_sdata4;
71static SifRpcServerData_t g_rpc_sdata5;
72static SifRpcServerData_t g_rpc_sdata2;
73static SifRpcServerData_t g_rpc_sdata6;
74static SifRpcServerData_t g_rpc_sdata3;
75static cdvdfsv_rpc4_outpacket_t g_cdvdfsv_srchres;
76static int g_cdvdfsv_readpos;
77static int g_cdvdfsv_rderror;
78static cdvdfsv_rpc2_outpacket_t g_diskready_res;
79static cdvdfsv_rpc5_outpacket_t g_crr;
80static cdvdfsv_rpc3_outpacket_t g_outbuf;
81static int g_rpc_buffer3[260];
82static int g_rpc_buffer5[256];
83static int g_rpc_buffer1[4];
84static int g_rpc_buffer4[76];
85static int g_rpc_buffer2[4];
86
87static int cdvdfsv_checkdmastat(int trid)
88{
89 int retval;
90 int state;
91
92 if ( QueryIntrContext() )
93 return sceSifDmaStat(trid);
94 CpuSuspendIntr(&state);
95 retval = sceSifDmaStat(trid);
96 CpuResumeIntr(state);
97 return retval;
98}
99
100static int cdvdfsv_cleanuprpc()
101{
102 unsigned int i;
103
104 sceSifRemoveRpc(&g_rpc_sdata1, &g_rpc_qdata1);
105 sceSifRemoveRpc(&g_rpc_sdata2, &g_rpc_qdata1);
106 sceSifRemoveRpc(&g_rpc_sdata3, &g_rpc_qdata1);
107 sceSifRemoveRpc(&g_rpc_sdata6, &g_rpc_qdata3);
108 sceSifRemoveRpc(&g_rpc_sdata4, &g_rpc_qdata2);
109 sceSifRemoveRpc(&g_rpc_sdata5, &g_rpc_qdata2);
110 sceSifRemoveRpcQueue(&g_rpc_qdata1);
111 sceSifRemoveRpcQueue(&g_rpc_qdata2);
112 sceSifRemoveRpcQueue(&g_rpc_qdata3);
113 g_cdvdfsv_nopocm = 1;
114 g_cdvdfsv_plbreak = 1;
115 for ( i = 0; i < (sizeof(g_cdvdfsv_thids) / sizeof(g_cdvdfsv_thids[0])); i += 1 )
116 {
117 TerminateThread(g_cdvdfsv_thids[i]);
118 DeleteThread(g_cdvdfsv_thids[i]);
119 }
120 return 1;
121}
122
123int _start(int ac, char *av[], void *startaddr, ModuleInfo_t *mi)
124{
125#if 0
126 const u16 *LibraryEntryTable;
127#endif
128 int state;
129
130 (void)startaddr;
131
132 if ( ac < 0 )
133 {
134 int error_code;
135
136 // cppcheck-suppress knownConditionTrueFalse
137 if ( g_cdvdfsv_rpc5flg || g_cdvdfsv_rpc3flg || !cdvdfsv_cleanuprpc() )
138 {
139 return MODULE_REMOVABLE_END;
140 }
141 CpuSuspendIntr(&state);
142 error_code = ReleaseLibraryEntries(&_exp_cdvdfsv);
143 CpuResumeIntr(state);
144 if ( error_code && error_code != KE_LIBRARY_NOTFOUND )
145 {
146 KPRINTF("ReleaseLibraryEntries Error code %d\n", error_code);
147 return MODULE_REMOVABLE_END;
148 }
149 return MODULE_NO_RESIDENT_END;
150 }
151 if ( RegisterLibraryEntries(&_exp_cdvdfsv) )
152 {
153 return MODULE_NO_RESIDENT_END;
154 }
155 g_cdvdfsv_fsvrbuf = sceGetFsvRbuf();
156 // Unofficial: setting of unused variable removed
157 g_cdvdfsv_rtocbuf = (char *)g_cdvdfsv_fsvrbuf;
158 cdvdfsv_parseargs(ac, av);
159 cdvdfsv_init();
160#if 0
161 CpuSuspendIntr(&state);
162 LibraryEntryTable = (u16 *)QueryLibraryEntryTable(&g_modload_libinfo);
163 CpuResumeIntr(state);
164 if ( !LibraryEntryTable || (*(LibraryEntryTable - 6) < 0x104) )
165 {
166 KPRINTF("Warning cdvdfsv.irx: Unload function can't be used.\n");
167 return MODULE_RESIDENT_END;
168 }
169 return MODULE_REMOVABLE_END;
170#else
171 if ( mi && ((mi->newflags & 2) != 0) )
172 mi->newflags |= 0x10;
173 return MODULE_RESIDENT_END;
174#endif
175}
176
177static int cdvdfsv_init()
178{
179 const int *BootMode;
180 iop_thread_t thparam;
181 int scres;
182
183 BootMode = QueryBootMode(3);
184 if ( BootMode && (BootMode[1] & 2) )
185 {
186 PRINTF(" No cdvd driver \n");
187 return 1;
188 }
189 sceCdSC(0xFFFFFFF2, (int *)&g_cdvdman_istruct_ptr);
190 g_scmd_evid = sceCdSC(0xFFFFFFE7, &scres);
191 thparam.attr = TH_C;
192 thparam.thread = cdvdfsv_main_th;
193 thparam.stacksize = 0x800;
194 thparam.option = 0;
195 thparam.priority = g_cdvdfsv_def_pri - 1;
196 g_cdvdfsv_thids[0] = CreateThread(&thparam);
197 if ( g_cdvdfsv_thids[0] <= 0 )
198 {
199 return 1;
200 }
201 StartThread(g_cdvdfsv_thids[0], 0);
202 return 0;
203}
204
205static void cdvdfsv_main_th(void *arg)
206{
207 iop_thread_t thparam1;
208 iop_thread_t thparam2;
209
210 (void)arg;
211
212 if ( !sceSifCheckInit() )
213 sceSifInit();
214 sceSifInitRpc(0);
215 PRINTF("cdvd driver module version 0.1.1 (C)SCEI\n");
216 thparam2.thread = cdvdfsv_rpc1_th;
217 thparam2.attr = TH_C;
218 thparam2.stacksize = 0x1900;
219 thparam2.option = 0;
220 thparam2.priority = g_cdvdfsv_def_pri;
221 g_cdvdfsv_thids[1] = CreateThread(&thparam2);
222 StartThread(g_cdvdfsv_thids[1], 0);
223 thparam1.attr = TH_C;
224 thparam1.thread = cdvdfsv_rpc2_th;
225 thparam1.stacksize = 0x1900;
226 thparam1.option = 0;
227 thparam1.priority = g_cdvdfsv_def_pri;
228 g_cdvdfsv_thids[2] = CreateThread(&thparam1);
229 StartThread(g_cdvdfsv_thids[2], 0);
230 thparam1.thread = cdvdfsv_rpc3_th;
231 thparam1.attr = TH_C;
232 thparam1.stacksize = 0x800;
233 thparam1.option = 0;
234 thparam1.priority = g_cdvdfsv_def_pri;
235 g_cdvdfsv_thids[3] = CreateThread(&thparam1);
236 StartThread(g_cdvdfsv_thids[3], 0);
237 cdvdfsv_poffloop();
238 ExitDeleteThread();
239}
240
241int *cdvdfsv_dummyentry(int arg1)
242{
243 VERBOSE_PRINTF(1, "Dummy Entry Called\n");
244 if ( arg1 != 128 )
245 return 0;
246 return &g_verbose_level;
247}
248
249static void cdvdfsv_parseargs(int ac, char **av)
250{
251 int i;
252
253 g_cdvdfsv_def_pri = 81;
254 for ( i = 1; i < ac; i += 1 )
255 {
256 if ( !strncmp(av[i], "thpri=", 6) )
257 {
258 g_cdvdfsv_def_pri = strtol(av[i] + 6, 0, 10);
259 if ( (unsigned int)(g_cdvdfsv_def_pri - 9) >= 0x73 )
260 {
261 PRINTF("Cdvdfsv:thpri=%d Illegal priority\n", g_cdvdfsv_def_pri);
262 g_cdvdfsv_def_pri = 81;
263 }
264 if ( g_cdvdfsv_def_pri == 9 )
265 g_cdvdfsv_def_pri = 10;
266 }
267 }
268}
269
271{
272 iop_thread_info_t thinfo;
273
274 if ( (unsigned int)(priority - 9) >= 0x73 )
275 return -403;
276 if ( priority == 9 )
277 priority = 10;
278 ReferThreadStatus(0, &thinfo);
279 ChangeThreadPriority(0, 8);
280 ChangeThreadPriority(g_cdvdfsv_thids[0], priority - 1);
281 ChangeThreadPriority(g_cdvdfsv_thids[2], priority);
282 ChangeThreadPriority(g_cdvdfsv_thids[1], priority);
283 ChangeThreadPriority(g_cdvdfsv_thids[3], priority);
284 return 0;
285}
286
287static void *cbrpc_rpc1_cdinit(int fno, void *buffer, int length)
288{
289 int scres_unused;
290
291 (void)fno;
292 (void)length;
293
294 VERBOSE_PRINTF(1, "sceCdInit call\n");
295 sceCdInit(((const cdvdfsv_rpc1_inpacket_t *)buffer)->m_mode);
296 g_cdvdfsv_spinctl = -1;
297 g_cdvdfsv_initres.m_debug_mode = g_verbose_level ? 254 : 0;
298 g_cdvdfsv_initres.m_cdvdfsv_ver = (u16)_irx_id.v;
299 g_cdvdfsv_initres.m_cdvdman_ver = sceCdSC(0xFFFFFFF7, &scres_unused);
300 VERBOSE_PRINTF(1, "sceCdInit end\n");
301 g_cdvdfsv_initres.m_retres = 1;
302 return (void *)&g_cdvdfsv_initres;
303}
304
305static void cdvdfsv_rpc3_16_break(const cdvdfsv_rpc3_inpacket_t *inbuf, int buflen, cdvdfsv_rpc3_outpacket_t *outbuf)
306{
307 (void)inbuf;
308 (void)buflen;
309
310 VERBOSE_PRINTF(1, "sceCdAbort call\n");
311 sceCdBreak();
312 outbuf->m_retres = 1;
313}
314
315static void *cbrpc_rpc4_fscall(int fno, void *buffer, int length)
316{
317 int scres;
318 int state;
320
321 (void)fno;
322
323 inbuf = buffer;
324 scres = 255;
325 sceCdSC(0xFFFFFFF6, &scres);
326 VERBOSE_PRINTF(1, "search file name %s call struct_siz %d\n", inbuf->m_pkt_sz12c.m_path, length);
327 switch ( length )
328 {
329 case sizeof(inbuf->m_pkt_sz12c):
330 g_cdvdfsv_srchres.m_retres =
331 sceCdLayerSearchFile(&(inbuf->m_pkt_sz12c.m_fp), inbuf->m_pkt_sz12c.m_path, inbuf->m_pkt_sz12c.m_layer);
332 g_cdvdfsv_fssdd.src = buffer;
333 g_cdvdfsv_fssdd.dest = (void *)inbuf->m_pkt_sz12c.m_eedest;
334 g_cdvdfsv_fssdd.size = sizeof(sceCdlFILE) + 4;
335 break;
336 case sizeof(inbuf->m_pkt_sz128):
337 PRINTF("sceCdSearchFile: Called from Not_Dual_layer Version.\n");
338 g_cdvdfsv_srchres.m_retres = sceCdSearchFile(&(inbuf->m_pkt_sz128.m_fp), inbuf->m_pkt_sz128.m_path);
339 g_cdvdfsv_fssdd.src = buffer;
340 g_cdvdfsv_fssdd.dest = (void *)inbuf->m_pkt_sz128.m_eedest;
341 g_cdvdfsv_fssdd.size = sizeof(sceCdlFILE) + 4;
342 break;
343 default:
344 PRINTF("Warning sceCdSearchFile: Called from Old liblary.\n");
345 g_cdvdfsv_srchres.m_retres = sceCdSearchFile(&(inbuf->m_pkt_sz124.m_fp), inbuf->m_pkt_sz124.m_path);
346 g_cdvdfsv_fssdd.src = buffer;
347 g_cdvdfsv_fssdd.dest = (void *)inbuf->m_pkt_sz124.m_eedest;
348 g_cdvdfsv_fssdd.size = sizeof(sceCdlFILE);
349 break;
350 }
351 g_cdvdfsv_fssdd.attr = 0;
352 while ( 1 )
353 {
354 int trid;
355
356 CpuSuspendIntr(&state);
357 trid = sceSifSetDma(&g_cdvdfsv_fssdd, 1);
358 CpuResumeIntr(state);
359 if ( trid )
360 break;
361 DelayThread(500);
362 }
363 scres = 0;
364 sceCdSC(0xFFFFFFF6, &scres);
365 return (void *)&g_cdvdfsv_srchres;
366}
367
368static int read_timeout_alarm_cb(const iop_sys_clock_t *sys_clock)
369{
370 int read_timeout;
371
372 read_timeout = sys_clock->lo / 0x9000;
373 KPRINTF("Read Time Out %d(msec)\n", read_timeout);
374 sceCdSC(0xFFFFFFEE, &read_timeout);
375 return !sceCdBreak();
376}
377
378static void cdvdfsv_rpc5_0D_iopmread(const cdvdfsv_rpc5_inpacket_t *inbuf, int buflen, cdvdfsv_rpc5_outpacket_t *outbuf)
379{
380 int cmd_error;
381 int trid;
382 int scres_unused;
383 int error_code;
384 int state;
385
386 (void)buflen;
387 (void)outbuf;
388
389 g_cdvdfsv_rderror = SCECdErREADCFR;
390 g_cdvdfsv_read_timeout.hi = 0;
391 g_cdvdfsv_read_timeout.lo = 0x9000 * sceCdSC(0xFFFFFFF1, &scres_unused);
392 g_cdvdfsv_iomrsdd.src = &g_cdvdfsv_readpos;
393 g_cdvdfsv_iomrsdd.size = sizeof(g_cdvdfsv_readpos);
394 g_cdvdfsv_iomrsdd.attr = 0;
395 g_cdvdfsv_iomrsdd.dest = (void *)inbuf->m_pkt_0D.m_eedest;
396 VERBOSE_PRINTF(
397 1,
398 "sceCdReadIOPm addr= 0x%08x sector= %d\n",
399 (unsigned int)(uiptr)(inbuf->m_pkt_0D.m_buf),
400 (int)(inbuf->m_pkt_0D.m_sectors));
401 cmd_error = sceCdRE(
402 inbuf->m_pkt_0D.m_lbn, inbuf->m_pkt_0D.m_sectors, inbuf->m_pkt_0D.m_buf, (sceCdRMode *)&inbuf->m_pkt_0D.m_mode);
403 while ( sceCdSync(1) )
404 {
405 g_cdvdfsv_readpos = sceCdGetReadPos();
406 while ( 1 )
407 {
408 CpuSuspendIntr(&state);
409 trid = sceSifSetDma(&g_cdvdfsv_iomrsdd, 1);
410 CpuResumeIntr(state);
411 if ( trid )
412 break;
413 DelayThread(500);
414 }
415 DelayThread(8000);
416 while ( cdvdfsv_checkdmastat(trid) >= 0 )
417 ;
418 }
419 error_code = sceCdGetError();
420 if ( error_code || !cmd_error )
421 {
422 if ( !cmd_error )
423 sceCdSC(0xFFFFFFFE, &g_cdvdfsv_rderror);
424 VERBOSE_PRINTF(1, "Read error code %x cmd error %d\n", error_code, cmd_error);
425 }
426}
427
428static u8 cdvdfsv_syncdec(int flag, int xorkey, int arg2, u8 data)
429{
430 return flag ? (((data << (arg2 % 8)) | (data >> (8 - arg2 % 8))) ^ xorkey) : data;
431}
432
433static int cdvdfsv_cb_read()
434{
435 iSetEventFlag(g_cdvdman_intr_efid, 0x20);
436 return 0;
437}
438
439static int cdvdfsv_checksid(u32 lsn, u32 sectors, u32 ps2dvd, void *buf, int decflag, int decshift, u32 *syncdec_mask)
440{
441 int scret;
442 u32 i;
443 u32 readlsn;
444 int syncdec;
445 u8 syncdec_4;
446 sceCdlLOCCD rpos;
447 int scres;
448 int ipi_emu;
449
450 ipi_emu = 0;
451 *syncdec_mask = 0;
452 scret = decflag ? sceCdSC(0xFFFFFFE8, &scres) : 0;
453 syncdec_4 = 0;
454 for ( i = 0; i < sectors; i += 1 )
455 {
456 if ( ps2dvd )
457 {
458 syncdec = cdvdfsv_syncdec(decflag, scret, decshift, ((u8 *)buf + (i * 0x810))[3]);
459 syncdec += cdvdfsv_syncdec(decflag, scret, decshift, ((u8 *)buf + (i * 0x810))[2]) << 8;
460 syncdec += cdvdfsv_syncdec(decflag, scret, decshift, ((u8 *)buf + (i * 0x810))[1]) << 16;
461 syncdec_4 = cdvdfsv_syncdec(decflag, scret, decshift, ((u8 *)buf + (i * 0x810))[0]);
462 if ( i && !*syncdec_mask )
463 {
464 ipi_emu = syncdec_4 & 0xC;
465 }
466 else if ( !i )
467 {
468 *syncdec_mask = syncdec_4 & 0xC;
469 }
470 readlsn = syncdec - 0x30000;
471 if (
472 g_cdvdman_istruct_ptr->m_opo_or_para && (lsn + i) >= g_cdvdman_istruct_ptr->m_layer_1_lsn
473 && g_cdvdman_istruct_ptr->m_opo_or_para == 1 )
474 {
475 readlsn += g_cdvdman_istruct_ptr->m_layer_1_lsn;
476 }
477 }
478 else
479 {
480 rpos.minute = cdvdfsv_syncdec(decflag, scret, decshift, ((u8 *)buf + (i * 0x924))[0]);
481 rpos.second = cdvdfsv_syncdec(decflag, scret, decshift, ((u8 *)buf + (i * 0x924))[1]);
482 rpos.sector = cdvdfsv_syncdec(decflag, scret, decshift, ((u8 *)buf + (i * 0x924))[2]);
483 readlsn = sceCdPosToInt(&rpos);
484 }
485 if ( readlsn != (lsn + i) || ipi_emu )
486 {
487 VERBOSE_PRINTF(
488 1,
489 "Read_EE Sector_ID error lsn= %d readlsn= %d layer= %d layer1_start %d\n",
490 (int)(lsn + i),
491 (int)readlsn,
492 (syncdec_4 & 1),
493 (int)(g_cdvdman_istruct_ptr->m_layer_1_lsn));
494 return 0;
495 }
496 }
497 if ( *syncdec_mask )
498 {
499 VERBOSE_PRINTF(
500 1, "Read_EE NO_Data_zone error lsn= %d layer= %d SecID %02x\n", (int)lsn, (syncdec_4 & 1), (int)(*syncdec_mask));
501 }
502 return 1;
503}
504
505static int readproc2(
506 u32 lsn,
507 u32 nsec,
508 sceCdRMode *mode,
509 u32 sector_size_selection,
510 int do_multi_retries,
511 int enable_dec_shift,
512 int dec_shift,
513 char *ee_addr,
514 int fssift,
515 int secsize,
516 int dmasize,
517 SifDmaTransfer_t *post_dmat)
518{
519 unsigned int i;
520 int csec;
521 int read_res_tmp;
522 int trid;
523 int j;
524 int size_2;
525 int sector_sizes[2];
526 int error_code;
527 int scres_unused;
528 int state;
529 u32 syncdec_mask;
530 u32 chcr;
531 int error_code_tmp;
532 char *ee_addr_tmp;
533 int dmasize_tmp;
534 int csec_comm;
535 int nsec_div_cdvdfsv_sectors;
536 int retry_flag1;
537 int retry_flag2;
538 int sector_size;
539
540 error_code_tmp = 0;
541 sector_sizes[0] = 0x924;
542 sector_sizes[1] = 0x810;
543 g_cdvdfsv_read_timeout.hi = 0;
544 g_cdvdfsv_read_timeout.lo = 0x9000 * sceCdSC(0xFFFFFFF1, &scres_unused);
545 g_cdvdfsv_rderror = SCECdErREADCF;
546 g_cdvdfsv_r2retry = 0;
547 g_cdvdfsv_r2count = 0;
548 if ( secsize != 0x924 && !fssift )
549 {
550 for ( i = 0; i < (sizeof(g_cdvdfsv_multi_dmat) / sizeof(g_cdvdfsv_multi_dmat[0])); i += 1 )
551 {
552 g_cdvdfsv_multi_dmat[i].attr = 0;
553 g_cdvdfsv_multi_dmat[i].size = secsize;
554 }
555 }
556 sector_size = sector_sizes[sector_size_selection];
557 while ( 1 )
558 {
559 while ( 1 )
560 {
561 csec = (nsec <= (sizeof(g_cdvdfsv_multi_dmat) / sizeof(g_cdvdfsv_multi_dmat[0]))) ?
562 nsec :
563 (sizeof(g_cdvdfsv_multi_dmat) / sizeof(g_cdvdfsv_multi_dmat[0]));
564 nsec_div_cdvdfsv_sectors = (nsec >> 4) + (!!((nsec & 0xF)));
565 retry_flag2 = 0;
566 ee_addr_tmp = ee_addr;
567 dmasize_tmp = dmasize;
568 g_cdvdman_istruct_ptr->m_dec_mode_set = 1;
569 g_cdvdman_istruct_ptr->m_dec_mode_last_set = 0;
570 CpuSuspendIntr(&state);
571 if ( enable_dec_shift )
572 {
573 g_cdvdman_istruct_ptr->m_dec_shift = dec_shift;
574 g_cdvdman_istruct_ptr->m_dec_state = 2;
575 }
576 if ( g_cdvdfsv_r2retry )
577 {
578 VERBOSE_KPRINTF(1, "Rty_Read\n");
579 read_res_tmp = (sector_size_selection ? sceCdRV : sceCdRead0)(
580 (lsn >= 0x60) ? (lsn - 0x10 * g_cdvdfsv_r2retry) : (lsn + 0x10 * g_cdvdfsv_r2retry + 0x60),
581 0x10,
582 &g_cdvdfsv_rtocbuf[0x1248],
583 mode,
584 0,
585 0);
586 CpuResumeIntr(state);
587 }
588 else
589 {
590 read_res_tmp = (sector_size_selection ? sceCdRV : sceCdRead0)(
591 lsn, nsec, &g_cdvdfsv_rtocbuf[0x1248], mode, csec, cdvdfsv_cb_read);
592 CpuResumeIntr(state);
593 if ( read_res_tmp )
594 {
595 SetAlarm(&g_cdvdfsv_read_timeout, (unsigned int (*)(void *))read_timeout_alarm_cb, &g_cdvdfsv_read_timeout);
596 csec_comm = 0;
597 retry_flag1 = 0;
598 break;
599 }
600 }
601 if ( !read_res_tmp )
602 {
603 g_cdvdman_istruct_ptr->m_dec_state = 0;
604 g_cdvdman_istruct_ptr->m_dec_mode_set = 0;
605 sceCdSC(0xFFFFFFFE, &g_cdvdfsv_rderror);
606 return 0;
607 }
608 sceCdSync(3);
609 g_cdvdfsv_r2retry -= 1;
610 }
611 for ( i = 0; (int)i < nsec_div_cdvdfsv_sectors; i += 1 )
612 {
613 sceCdSync(32);
614 if ( g_cdvdman_istruct_ptr->m_dec_mode_last_set )
615 break;
616 if ( !sceCdGetError() )
617 {
618 if ( cdvdfsv_checksid(
619 lsn + csec_comm,
620 csec,
621 sector_size_selection,
622 &g_cdvdfsv_rtocbuf[0x1248],
623 enable_dec_shift,
624 dec_shift,
625 &syncdec_mask) )
626 {
627 if ( do_multi_retries && syncdec_mask && !i )
628 {
629 retry_flag1 = 1;
630 error_code_tmp = SCECdErIPI;
631 }
632 }
633 else if ( do_multi_retries )
634 {
635 retry_flag2 = 1;
636 retry_flag1 = 1;
637 }
638 if ( retry_flag1 || g_cdvdfsv_r2retry )
639 {
640 }
641 else if ( secsize == 0x924 && !sector_size_selection )
642 {
643 if ( fssift )
644 {
645 if ( i )
646 {
647 optimized_memcpy(&g_cdvdfsv_rtocbuf[secsize], &g_cdvdfsv_rtocbuf[fssift], secsize - fssift);
648 optimized_memcpy(g_cdvdfsv_rtocbuf, &g_cdvdfsv_rtocbuf[secsize + secsize * csec], secsize);
649 g_cdvdfsv_rdp2sdd.size =
650 ((int)i == nsec_div_cdvdfsv_sectors - 1) ? dmasize_tmp : (secsize * (csec - 1) + fssift);
651 optimized_memcpy(
652 &g_cdvdfsv_rtocbuf[secsize + secsize - fssift],
653 &g_cdvdfsv_rtocbuf[secsize * 2],
654 g_cdvdfsv_rdp2sdd.size);
655 }
656 else
657 {
658 optimized_memcpy(g_cdvdfsv_rtocbuf, &g_cdvdfsv_rtocbuf[secsize * 2 + secsize * (csec - 1)], secsize);
659 g_cdvdfsv_rdp2sdd.size = ((int)i == nsec_div_cdvdfsv_sectors - 1) ? dmasize_tmp : (secsize * (csec - 1));
660 optimized_memcpy(
661 &g_cdvdfsv_rtocbuf[secsize], &g_cdvdfsv_rtocbuf[secsize * 2 + fssift], g_cdvdfsv_rdp2sdd.size);
662 }
663 g_cdvdfsv_rdp2sdd.src = &g_cdvdfsv_rtocbuf[secsize];
664 }
665 else
666 {
667 g_cdvdfsv_rdp2sdd.src = &g_cdvdfsv_rtocbuf[secsize * 2];
668 g_cdvdfsv_rdp2sdd.size = secsize * csec;
669 }
670 g_cdvdfsv_rdp2sdd.attr = 0;
671 g_cdvdfsv_rdp2sdd.dest = ee_addr_tmp;
672 ee_addr_tmp += g_cdvdfsv_rdp2sdd.size;
673 dmasize_tmp -= g_cdvdfsv_rdp2sdd.size;
674 while ( 1 )
675 {
676 CpuSuspendIntr(&state);
677 trid = sceSifSetDma(&g_cdvdfsv_rdp2sdd, 1);
678 CpuResumeIntr(state);
679 if ( trid )
680 break;
681 DelayThread(500);
682 }
683 while ( cdvdfsv_checkdmastat(trid) >= 0 )
684 ;
685 }
686 else if ( !fssift )
687 {
688 for ( j = 0; j < csec; j += 1 )
689 {
690 g_cdvdfsv_multi_dmat[j].dest = &ee_addr[(csec_comm + j) * secsize];
691 g_cdvdfsv_multi_dmat[j].src = &g_cdvdfsv_rtocbuf[0x1248 + (j * sector_size) + 12];
692 }
693 while ( 1 )
694 {
695 CpuSuspendIntr(&state);
696 trid = sceSifSetDma(g_cdvdfsv_multi_dmat, csec);
697 CpuResumeIntr(state);
698 if ( trid )
699 break;
700 DelayThread(500);
701 }
702 while ( cdvdfsv_checkdmastat(trid) >= 0 )
703 ;
704 }
705 else
706 {
707 size_2 = ((int)i != nsec_div_cdvdfsv_sectors - 1) ? fssift : secsize;
708 g_cdvdfsv_rdp2sdd.size = dmasize_tmp;
709 if ( i )
710 {
711 optimized_memcpy(&g_cdvdfsv_rtocbuf[0x924], &g_cdvdfsv_rtocbuf[fssift + 12], secsize - fssift);
712 optimized_memcpy(g_cdvdfsv_rtocbuf, &g_cdvdfsv_rtocbuf[0x1248 + (csec - 1) * sector_size], sector_size);
713 for ( j = 0; j < csec - 1; j += 1 )
714 {
715 optimized_memcpy(
716 &g_cdvdfsv_rtocbuf[0x924 + secsize - fssift + (j * secsize)],
717 &g_cdvdfsv_rtocbuf[0x1248 + 12 + (j * sector_size)],
718 secsize);
719 }
720 optimized_memcpy(
721 &g_cdvdfsv_rtocbuf[0x924 + secsize - fssift + ((csec - 1) * secsize)],
722 &g_cdvdfsv_rtocbuf[0x1248 + 12 + ((csec - 1) * sector_size)],
723 size_2);
724 if ( (int)i != nsec_div_cdvdfsv_sectors - 1 )
725 {
726 g_cdvdfsv_rdp2sdd.size = secsize * csec;
727 }
728 }
729 else
730 {
731 optimized_memcpy(g_cdvdfsv_rtocbuf, &g_cdvdfsv_rtocbuf[0x1248 + (csec - 1) * sector_size], sector_size);
732 optimized_memcpy(&g_cdvdfsv_rtocbuf[0x924], &g_cdvdfsv_rtocbuf[0x1248 + fssift + 12], secsize - fssift);
733 for ( j = 0; j < csec - 2; j += 1 )
734 {
735 optimized_memcpy(
736 &g_cdvdfsv_rtocbuf[0x924 + secsize - fssift + (j * secsize)],
737 &g_cdvdfsv_rtocbuf[0x1248 + sector_size + 12 + (j * sector_size)],
738 secsize);
739 }
740 optimized_memcpy(
741 &g_cdvdfsv_rtocbuf[0x924 + secsize - fssift + ((csec - 2) * secsize)],
742 &g_cdvdfsv_rtocbuf[0x1248 + sector_size + 12 + ((csec - 2) * sector_size)],
743 size_2);
744 if ( (int)i != nsec_div_cdvdfsv_sectors - 1 )
745 {
746 g_cdvdfsv_rdp2sdd.size = secsize * (csec - 1);
747 }
748 }
749 g_cdvdfsv_rdp2sdd.src = &g_cdvdfsv_rtocbuf[0x924];
750 g_cdvdfsv_rdp2sdd.attr = 0;
751 g_cdvdfsv_rdp2sdd.dest = ee_addr_tmp;
752 ee_addr_tmp += g_cdvdfsv_rdp2sdd.size;
753 dmasize_tmp -= g_cdvdfsv_rdp2sdd.size;
754 while ( 1 )
755 {
756 CpuSuspendIntr(&state);
757 trid = sceSifSetDma(&g_cdvdfsv_rdp2sdd, 1);
758 CpuResumeIntr(state);
759 if ( trid )
760 break;
761 DelayThread(500);
762 }
763 while ( cdvdfsv_checkdmastat(trid) >= 0 )
764 ;
765 }
766 }
767 else
768 {
769 retry_flag1 = 1;
770 }
771 CpuSuspendIntr(&state);
772 if ( (int)i == nsec_div_cdvdfsv_sectors - 1 )
773 {
774 DisableIntr(IOP_IRQ_DMA_CDVD, (int *)&chcr);
775 }
776 else
777 {
778 csec_comm = csec_comm + csec;
779 csec = ((unsigned int)csec > nsec - (unsigned int)csec_comm) ?
780 (nsec - (unsigned int)csec_comm) :
781 (sizeof(g_cdvdfsv_multi_dmat) / sizeof(g_cdvdfsv_multi_dmat[0]));
782 ClearEventFlag(g_cdvdman_intr_efid, ~0x20);
783 dmac_ch_set_chcr(3, 0);
784 dmac_ch_get_chcr(3);
785 g_cdvdman_istruct_ptr->m_dma3_param.m_dma3_maddress = &g_cdvdfsv_rtocbuf[0x1248];
786 dmac_ch_set_madr(3, (uiptr)(&g_cdvdfsv_rtocbuf[0x1248]));
787 dmac_ch_set_bcr(
788 3,
789 g_cdvdman_istruct_ptr->m_dma3_param.m_dma3_blkwords
790 | ((g_cdvdman_istruct_ptr->m_dma3_param.m_dma3_blkcount * csec) << 16));
791 dmac_ch_set_chcr(3, 0x41000200);
792 chcr = dmac_ch_get_chcr(3);
793 if ( post_dmat )
794 {
795 g_cdvdfsv_readpos += secsize * csec;
796 sceSifSetDma(post_dmat, 1);
797 }
798 }
799 CpuResumeIntr(state);
800 }
801 sceCdSync(5);
802 CancelAlarm((unsigned int (*)(void *))read_timeout_alarm_cb, &g_cdvdfsv_read_timeout);
803 g_cdvdman_istruct_ptr->m_dec_mode_set = 0;
804 g_cdvdman_istruct_ptr->m_dec_state = 0;
805 error_code = sceCdGetError();
806 if ( (u16)g_cdvdman_istruct_ptr->m_dec_mode_last_set )
807 {
808 retry_flag2 = 1;
809 error_code = 0;
810 mode->spindlctrl = 16;
811 }
812 if ( error_code || g_cdvdfsv_r2count >= 5 )
813 break;
814 if ( !retry_flag2 )
815 {
816 if ( !error_code_tmp )
817 return 1;
818 sceCdSC(0xFFFFFFFE, &error_code_tmp);
819 VERBOSE_KPRINTF(1, "secid_chk_ee_trns lsn %d nsec %d IPI Err\n", lsn, nsec);
820 return 0;
821 }
822 if ( !g_cdvdfsv_r2retry )
823 {
824 g_cdvdfsv_r2count += 1;
825 VERBOSE_PRINTF(1, "Read_CD/DVD-ROM Error Recover Start\n");
826 g_cdvdfsv_r2retry = 3;
827 }
828 }
829 if ( g_cdvdfsv_r2count >= 5 && !error_code )
830 {
831 sceCdSC(0xFFFFFFFE, &g_cdvdfsv_rderror);
832 }
833 return 0;
834}
835
836static int readproc1(
837 unsigned int lsn,
838 u32 nsec,
839 void *retptr,
840 sceCdRMode *rmode,
841 int ps2dvd,
842 int enable_retries,
843 int dec_shift_enable,
844 int dec_shift_value)
845{
846 int scres_unused;
847 int state;
848 u32 syncdec_mask;
849 int error_code_tmp;
850
851 error_code_tmp = 0;
852 g_cdvdfsv_read_timeout.hi = 0;
853 g_cdvdfsv_read_timeout.lo = 0x9000 * sceCdSC(0xFFFFFFF1, &scres_unused);
854 g_cdvdfsv_rderror = SCECdErREADCF;
855 g_cdvdfsv_sid_err_recover_cnt = 0;
856 g_cdvdfsv_err_count = 0;
857 while ( 1 )
858 {
859 int cmd_error;
860 int error_code;
861
862 CpuSuspendIntr(&state);
863 if ( dec_shift_enable )
864 {
865 g_cdvdman_istruct_ptr->m_dec_shift = dec_shift_value;
866 g_cdvdman_istruct_ptr->m_dec_state = 2;
867 }
868 cmd_error = (ps2dvd ? sceCdRV : sceCdRead0)(
869 (lsn >= 0x30) ? (lsn - 0x10 * g_cdvdfsv_sid_err_recover_cnt) : (lsn + 0x10 * g_cdvdfsv_sid_err_recover_cnt),
870 nsec,
871 retptr,
872 rmode,
873 0,
874 0);
875 CpuResumeIntr(state);
876 if ( cmd_error )
877 SetAlarm(&g_cdvdfsv_read_timeout, (unsigned int (*)(void *))read_timeout_alarm_cb, &g_cdvdfsv_read_timeout);
878 sceCdSync(5);
879 CancelAlarm((unsigned int (*)(void *))read_timeout_alarm_cb, &g_cdvdfsv_read_timeout);
880 g_cdvdman_istruct_ptr->m_dec_state = 0;
881 error_code = sceCdGetError();
882 if ( error_code || !cmd_error || g_cdvdfsv_err_count >= 5 )
883 {
884 VERBOSE_KPRINTF(1, "Read error error code %x cmd error %d\n", error_code, cmd_error);
885 if ( (!cmd_error || g_cdvdfsv_err_count >= 5) && (!error_code) )
886 {
887 sceCdSC(0xFFFFFFFE, &g_cdvdfsv_rderror);
888 }
889 return 0;
890 }
891 if ( cdvdfsv_checksid(lsn, nsec, ps2dvd, retptr, dec_shift_enable, dec_shift_value, &syncdec_mask) )
892 {
893 if ( enable_retries && syncdec_mask )
894 error_code_tmp = SCECdErIPI;
895 break;
896 }
897 if ( !enable_retries )
898 break;
899 if ( !g_cdvdfsv_sid_err_recover_cnt )
900 {
901 g_cdvdfsv_err_count += 1;
902 VERBOSE_PRINTF(1, "Read_CD/DVD-ROM Sector_ID Error Recover Start\n");
903 g_cdvdfsv_sid_err_recover_cnt = 3;
904 }
905 g_cdvdfsv_sid_err_recover_cnt -= 1;
906 }
907 if ( !error_code_tmp )
908 return 1;
909 sceCdSC(0xFFFFFFFE, &error_code_tmp);
910 VERBOSE_KPRINTF(1, "secid_chk lsn %d nsec %d IPI Err\n", lsn, nsec);
911 return 0;
912}
913
914static void cdvdfsv_rpc5_01_readee(
915 const cdvdfsv_rpc5_inpacket_t *inbuf, int buflen, cdvdfsv_rpc5_outpacket_t *outbuf, u32 ps2dvd, int sync, int decflag)
916{
917 unsigned int secsize;
918 unsigned int bsize;
919 unsigned int bsize_tmp;
920 unsigned int psize;
921 unsigned int ssize;
922 unsigned int i;
923 int sizestuff;
924 u32 needed_offset;
925 int sector_sizes[2];
926 int scres_unused;
927 int lsndualchg_res;
928 int state;
929 unsigned int buf_offs_sum;
930 unsigned int paddr;
931 int saddr;
932 int datapattern;
933 unsigned int len2_plus_sec2;
934 int trid;
935 int decval;
936 int early_break;
937
938 (void)buflen;
939
940 early_break = 0;
941 trid = 0;
942 buf_offs_sum = 0;
943 sector_sizes[0] = 0x924;
944 sector_sizes[1] = 0x810;
945 g_cdvdfsv_rmodeee = inbuf->m_pkt_01.m_rmodeee;
946 lsndualchg_res = inbuf->m_pkt_01.m_lbn;
947 decval = decflag ? inbuf->m_pkt_01.m_decval : 0;
948 g_cdvdfsv_eerpsdd.src = &g_cdvdfsv_readpos;
949 g_cdvdfsv_eerpsdd.size = sizeof(g_cdvdfsv_readpos);
950 g_cdvdfsv_eerpsdd.attr = 0;
951 g_cdvdfsv_eerpsdd.dest = (void *)inbuf->m_pkt_01.m_eedest;
952 if ( ps2dvd )
953 {
954 if ( !sceCdSC(0xFFFFFFEA, &scres_unused) )
955 {
956 g_cdvdfsv_rderror = SCECdErREADCFR;
957 sceCdSC(0xFFFFFFFE, &g_cdvdfsv_rderror);
958 bsize = 0;
959 psize = 0;
960 ssize = 0;
961 saddr = 0;
962 paddr = 0;
963 early_break = 1;
964 }
965 else
966 {
967 lsndualchg_res = sceCdSC(0xFFFFFFE9, &lsndualchg_res);
968 secsize = 0x800;
969 datapattern = SCECdSecS2048;
970 g_cdvdfsv_rmodeee.datapattern = SCECdSecS2048;
971 }
972 }
973 else
974 {
975 datapattern = g_cdvdfsv_rmodeee.datapattern;
976 switch ( datapattern )
977 {
978 case SCECdSecS2328:
979 secsize = 0x918;
980 break;
981 case SCECdSecS2340:
982 secsize = 0x924;
983 break;
984 case SCECdSecS2048:
985 default:
986 secsize = 0x800;
987 break;
988 }
989 g_cdvdfsv_rmodeee.datapattern = SCECdSecS2340;
990 }
991 len2_plus_sec2 = lsndualchg_res + inbuf->m_pkt_01.m_sectors;
992 if ( !early_break )
993 {
994 int all_sec_bytes;
995
996 all_sec_bytes = secsize * inbuf->m_pkt_01.m_sectors;
997 if ( g_cdvdfsv_spinctl != -1 )
998 g_cdvdfsv_rmodeee.spindlctrl = g_cdvdfsv_spinctl;
999 paddr = inbuf->m_pkt_01.m_paddr;
1000 saddr = (paddr + all_sec_bytes) & ~0x3F;
1001 psize = ((paddr & 0x3F)) ? ((paddr & ~0x3F) - (paddr - 0x40)) : 0;
1002 bsize = saddr - (paddr + psize);
1003 ssize = paddr + all_sec_bytes - saddr;
1004 VERBOSE_KPRINTF(1, "CD/DVD-ROM lsn= %d sec= %d\n", lsndualchg_res, inbuf->m_pkt_01.m_sectors);
1005 VERBOSE_KPRINTF(1, "f psize= %d bsize= %d ssize= %d\n", psize, bsize, ssize);
1006 }
1007 if ( psize )
1008 {
1009 u32 sectors;
1010
1011 sectors = (len2_plus_sec2 < lsndualchg_res + buf_offs_sum / secsize + 2) ? 1 : 2;
1012 VERBOSE_PRINTF(
1013 1,
1014 "0 CD_READ LBN= %d sectors= %d all= %d\n",
1015 (int)(lsndualchg_res + buf_offs_sum / secsize),
1016 (int)sectors,
1017 (int)inbuf->m_pkt_01.m_sectors);
1018 if ( !readproc1(
1019 lsndualchg_res + buf_offs_sum / secsize,
1020 sectors,
1021 g_cdvdfsv_rtocbuf,
1022 &g_cdvdfsv_rmodeee,
1023 ps2dvd,
1024 sync,
1025 decflag,
1026 decval) )
1027 {
1028 ssize = 0;
1029 psize = 0;
1030 bsize = 0;
1031 }
1032 else
1033 {
1034 if ( datapattern != SCECdSecS2340 || ps2dvd )
1035 {
1036 int rtoc_ind;
1037
1038 rtoc_ind = 12;
1039 for ( i = 0; i < psize; i += 1 )
1040 {
1041 rtoc_ind += (i && !(i % secsize)) ? (sector_sizes[ps2dvd] - secsize) : 0;
1042 g_cdvdfsv_eereadx.m_pbuf1[i] = g_cdvdfsv_rtocbuf[rtoc_ind + i];
1043 }
1044 }
1045 else
1046 {
1047 for ( i = 0; i < psize; i += 1 )
1048 g_cdvdfsv_eereadx.m_pbuf1[i] = g_cdvdfsv_rtocbuf[i];
1049 }
1050 buf_offs_sum += psize;
1051 }
1052 }
1053 bsize_tmp = bsize;
1054 for ( i = 0; i < bsize; i += sizestuff )
1055 {
1056 u32 offs_sector_only;
1057
1058 bsize_tmp = bsize - i;
1059 if ( g_cdvdfsv_spinctl != -1 )
1060 g_cdvdfsv_rmodeee.spindlctrl = g_cdvdfsv_spinctl;
1061 offs_sector_only = lsndualchg_res + buf_offs_sum / secsize;
1062 if ( (unsigned int)(secsize << 6) >= bsize_tmp )
1063 {
1064 needed_offset = (bsize_tmp / secsize) + (!!(bsize_tmp % secsize));
1065 sizestuff = bsize_tmp;
1066 }
1067 else
1068 {
1069 needed_offset = (((offs_sector_only & 0xF)) && (!(secsize & 0xF))) ? (0x10 - (offs_sector_only & 0xF)) : 0x40;
1070 sizestuff = secsize * needed_offset;
1071 }
1072 needed_offset += !!((buf_offs_sum + i) % secsize);
1073 if ( len2_plus_sec2 < offs_sector_only + needed_offset )
1074 needed_offset = len2_plus_sec2 - (lsndualchg_res + (buf_offs_sum + i) / secsize);
1075 g_cdvdfsv_readpos = buf_offs_sum + i;
1076 if ( !readproc2(
1077 offs_sector_only,
1078 needed_offset,
1079 &g_cdvdfsv_rmodeee,
1080 ps2dvd,
1081 sync,
1082 decflag,
1083 decval,
1084 (char *)(inbuf->m_pkt_01.m_paddr + psize) + i,
1085 (buf_offs_sum + i) % secsize,
1086 secsize,
1087 sizestuff,
1088 &g_cdvdfsv_eerpsdd) )
1089 {
1090 bsize_tmp = 0;
1091 early_break = 1;
1092 break;
1093 }
1094 while ( cdvdfsv_checkdmastat(trid) >= 0 )
1095 ;
1096 CpuSuspendIntr(&state);
1097 trid = sceSifSetDma(&g_cdvdfsv_eerpsdd, 1);
1098 CpuResumeIntr(state);
1099 }
1100 buf_offs_sum += i;
1101 bsize = bsize_tmp;
1102 if ( !early_break && ssize )
1103 {
1104 u32 sectors_1;
1105 unsigned int buf_offs_sum_bytes_in_sector;
1106
1107 buf_offs_sum_bytes_in_sector = buf_offs_sum % secsize;
1108 sectors_1 = (len2_plus_sec2 < lsndualchg_res + buf_offs_sum / secsize + 2) ? 1 : 2;
1109 VERBOSE_PRINTF(
1110 1, "2 CD_READ LBN= %d sectors= %d\n", (int)(lsndualchg_res + buf_offs_sum / secsize), (int)sectors_1);
1111 if ( !readproc1(
1112 lsndualchg_res + buf_offs_sum / secsize,
1113 sectors_1,
1114 g_cdvdfsv_rtocbuf,
1115 &g_cdvdfsv_rmodeee,
1116 ps2dvd,
1117 sync,
1118 decflag,
1119 decval) )
1120 {
1121 bsize = 0;
1122 }
1123 else
1124 {
1125 if ( datapattern != SCECdSecS2340 || ps2dvd )
1126 {
1127 int i2_offs;
1128
1129 i2_offs = 12;
1130 for ( i = 0; i < ssize; i += 1 )
1131 {
1132 i2_offs +=
1133 ((i + buf_offs_sum_bytes_in_sector)
1134 && (i % secsize) == (secsize - (buf_offs_sum_bytes_in_sector ? buf_offs_sum_bytes_in_sector : secsize))) ?
1135 (sector_sizes[ps2dvd] - secsize) :
1136 0;
1137 g_cdvdfsv_eereadx.m_pbuf2[i] = g_cdvdfsv_rtocbuf[buf_offs_sum_bytes_in_sector + i2_offs + i];
1138 }
1139 }
1140 else
1141 {
1142 for ( i = 0; i < ssize; i += 1 )
1143 g_cdvdfsv_eereadx.m_pbuf2[i] = g_cdvdfsv_rtocbuf[buf_offs_sum_bytes_in_sector + i];
1144 }
1145 buf_offs_sum += ssize;
1146 }
1147 }
1148 g_cdvdfsv_eereadx.m_b1len = psize;
1149 g_cdvdfsv_eereadx.m_b2len = ssize;
1150 g_cdvdfsv_eereadx.m_b1dst = paddr;
1151 g_cdvdfsv_eereadx.m_b2dst = saddr;
1152 VERBOSE_PRINTF(
1153 1, "b psize= %d paddr= %08x bsize= %d ssize= %d saddr %08x\n", (int)psize, paddr, (int)bsize, (int)ssize, saddr);
1154 while ( cdvdfsv_checkdmastat(trid) >= 0 )
1155 ;
1156 g_cdvdfsv_datasdd.src = &g_cdvdfsv_eereadx;
1157 g_cdvdfsv_datasdd.size = sizeof(g_cdvdfsv_eereadx);
1158 g_cdvdfsv_datasdd.attr = 0;
1159 g_cdvdfsv_readpos = buf_offs_sum;
1160 g_cdvdfsv_datasdd.dest = (void *)inbuf->m_pkt_01.m_eeremaindest;
1161 while ( 1 )
1162 {
1163 CpuSuspendIntr(&state);
1164 trid = sceSifSetDma(&g_cdvdfsv_datasdd, 1);
1165 sceSifSetDma(&g_cdvdfsv_eerpsdd, 1);
1166 CpuResumeIntr(state);
1167 if ( trid )
1168 break;
1169 DelayThread(500);
1170 }
1171 while ( cdvdfsv_checkdmastat(trid) >= 0 )
1172 ;
1173 g_cdvdfsv_spinctl = -1;
1174 VERBOSE_PRINTF(1, "read end\n");
1175 outbuf->m_retres = buf_offs_sum;
1176}
1177
1178static int
1179cdvdfsv_chreadee(int secoffs, int seccount, char *ee_addr, const sceCdRMode *in_rmode, u32 disktype_14, int sync)
1180{
1181 unsigned int secsize;
1182 unsigned int i;
1183 int readsize_bytes;
1184 sceCdRMode rmode;
1185 int scres_unused;
1186 int lsndualchg_res;
1187
1188 lsndualchg_res = secoffs;
1189 rmode = *in_rmode;
1190 if ( disktype_14 )
1191 {
1192 if ( !sceCdSC(0xFFFFFFEA, &scres_unused) )
1193 {
1194 g_cdvdfsv_rderror = SCECdErREADCFR;
1195 sceCdSC(0xFFFFFFFE, &g_cdvdfsv_rderror);
1196 return 1;
1197 }
1198 secsize = 0x800;
1199 lsndualchg_res = sceCdSC(0xFFFFFFE9, &lsndualchg_res);
1200 rmode.datapattern = SCECdSecS2048;
1201 }
1202 else
1203 {
1204 switch ( rmode.datapattern )
1205 {
1206 case SCECdSecS2328:
1207 secsize = 0x918;
1208 break;
1209 case SCECdSecS2340:
1210 secsize = 0x924;
1211 break;
1212 case SCECdSecS2048:
1213 default:
1214 secsize = 0x800;
1215 break;
1216 }
1217 rmode.datapattern = SCECdSecS2340;
1218 }
1219 for ( i = 0; i < (unsigned int)(secsize * seccount); i += readsize_bytes )
1220 {
1221 unsigned int bytescount;
1222 int sectors_partial;
1223 int bytescount_in_sectors;
1224
1225 bytescount = (unsigned int)(secsize * seccount) - i;
1226 sectors_partial = (lsndualchg_res + i / secsize) & 0xF;
1227 bytescount_in_sectors = 0x10;
1228 readsize_bytes = secsize * bytescount_in_sectors;
1229 if ( (unsigned int)readsize_bytes >= bytescount )
1230 {
1231 bytescount_in_sectors = (bytescount / secsize) + (!!(bytescount % secsize));
1232 readsize_bytes = bytescount;
1233 }
1234 else if ( sectors_partial && !(secsize & 0xF) )
1235 {
1236 bytescount_in_sectors -= sectors_partial;
1237 }
1238 if ( !readproc2(
1239 lsndualchg_res + i / secsize,
1240 bytescount_in_sectors,
1241 &rmode,
1242 disktype_14,
1243 sync,
1244 0,
1245 0,
1246 ee_addr + i,
1247 0,
1248 secsize,
1249 readsize_bytes,
1250 0) )
1251 {
1252 break;
1253 }
1254 }
1255 return 1;
1256}
1257
1258void cdvdfsv_rpc5_0F_readchain(const cdvdfsv_rpc5_inpacket_t *inbuf, int buflen, cdvdfsv_rpc5_outpacket_t *outbuf)
1259{
1260 int sector_size;
1261 unsigned int i;
1262 const sceCdRChain *chain;
1263 void *buf;
1264 int re_result;
1265 int trid;
1266 int scres_unused;
1267 int state;
1268
1269 (void)buflen;
1270 (void)outbuf;
1271
1272 g_cdvdfsv_rderror = SCECdErREADCFR;
1273 g_cdvdfsv_readpos = 0;
1274 g_cdvdman_istruct_ptr->m_break_cdvdfsv_readchain = 0;
1275 g_cdvdfsv_chrdsdd.src = &g_cdvdfsv_readpos;
1276 g_cdvdfsv_chrdsdd.size = sizeof(g_cdvdfsv_readpos);
1277 g_cdvdfsv_chrdsdd.attr = 0;
1278 g_cdvdfsv_chrdsdd.dest = (void *)inbuf->m_pkt_0F.m_eedest;
1279 switch ( inbuf->m_pkt_0F.m_mode.datapattern )
1280 {
1281 case SCECdSecS2328:
1282 sector_size = 0x918;
1283 break;
1284 case SCECdSecS2340:
1285 sector_size = 0x924;
1286 break;
1287 case SCECdSecS2048:
1288 default:
1289 sector_size = 0x800;
1290 break;
1291 }
1292 chain = inbuf->m_pkt_0F.m_readChain;
1293 for ( i = 0; i < 0x40; i += 1 )
1294 {
1295 if ( g_cdvdman_istruct_ptr->m_break_cdvdfsv_readchain )
1296 {
1297 VERBOSE_PRINTF(1, "ReadChain cnt %d on sceCdBreak()\n", (int)i);
1298 return;
1299 }
1300 if ( chain[i].lbn == 0xFFFFFFFF || chain[i].sectors == 0xFFFFFFFF || chain[i].buffer == 0xFFFFFFFF )
1301 return;
1302 if ( (chain[i].buffer & 1) )
1303 {
1304 buf = (void *)(chain[i].buffer & ~1);
1305 VERBOSE_PRINTF(
1306 1,
1307 "ReadChain lsn= %d nsec= %d buf= %08x secsize= %d\n",
1308 (int)(chain[i].lbn),
1309 (int)(chain[i].sectors),
1310 (unsigned int)(uiptr)buf,
1311 inbuf->m_pkt_0F.m_mode.datapattern);
1312 re_result = sceCdRE(chain[i].lbn, chain[i].sectors, buf, (sceCdRMode *)&(inbuf->m_pkt_0F.m_mode));
1313 if ( re_result == 1 )
1314 {
1315 sceCdSync(0);
1316 re_result = !sceCdGetError();
1317 }
1318 else
1319 {
1320 sceCdSC(0xFFFFFFFE, &g_cdvdfsv_rderror);
1321 }
1322 }
1323 else
1324 {
1325 VERBOSE_PRINTF(
1326 1, "ReadChain EE Memory addr= 0x%08x sector= %d\n", (unsigned int)(chain[i].lbn), (int)(chain[i].sectors));
1327 // The following call to sceCdGetDiskType was inlined
1328 re_result = cdvdfsv_chreadee(
1329 chain[i].lbn,
1330 chain[i].sectors,
1331 (char *)chain[i].buffer,
1332 &(inbuf->m_pkt_0F.m_mode),
1334 !sceCdSC(0xFFFFFFFC, &scres_unused));
1335 }
1336 if ( !re_result )
1337 {
1338 VERBOSE_PRINTF(1, "ReadChain error code= 0x%02x\n", sceCdGetError());
1339 break;
1340 }
1341 g_cdvdfsv_readpos += chain[i].sectors * sector_size;
1342 while ( 1 )
1343 {
1344 CpuSuspendIntr(&state);
1345 trid = sceSifSetDma(&g_cdvdfsv_chrdsdd, 1);
1346 CpuResumeIntr(state);
1347 if ( trid )
1348 break;
1349 DelayThread(500);
1350 }
1351 while ( cdvdfsv_checkdmastat(trid) >= 0 )
1352 ;
1353 }
1354}
1355
1356void cdvdfsv_rpc5_02_readcdda(const cdvdfsv_rpc5_inpacket_t *inbuf, int buflen, cdvdfsv_rpc5_outpacket_t *outbuf)
1357{
1358 int trid1;
1359 unsigned int sector_size;
1360 int all_sec_bytes;
1361 unsigned int buf_1_toalign;
1362 int cmd_error;
1363 int error_code;
1364 unsigned int i;
1365 int trid2;
1366 int state;
1367 int error_code_tmp;
1368 unsigned int buf_offs;
1369 unsigned int buf_toalign;
1370 unsigned int buf_sec_tmp;
1371 unsigned int lbn_1_end;
1372
1373 trid1 = 0;
1374 g_cdvdfsv_rderror = SCECdErREADCFR;
1375 error_code_tmp = 0;
1376 g_cdvdfsv_eereadfull_dma2.src = &g_cdvdfsv_readpos;
1377 g_cdvdfsv_eereadfull_dma2.size = sizeof(g_cdvdfsv_readpos);
1378 g_cdvdfsv_eereadfull_dma2.attr = 0;
1379 g_cdvdfsv_eereadfull_dma2.dest = (void *)inbuf->m_pkt_02.m_eedest;
1380 switch ( inbuf->m_pkt_02.m_mode.datapattern )
1381 {
1382 case SCECdSecS2368:
1383 sector_size = 0x940;
1384 break;
1385 case SCECdSecS2352:
1386 case SCECdSecS2448:
1387 default:
1388 sector_size = 0x930;
1389 break;
1390 }
1391 buf_offs = 0;
1392 all_sec_bytes = sector_size * inbuf->m_pkt_02.m_sectors;
1393 lbn_1_end = inbuf->m_pkt_02.m_lbn + inbuf->m_pkt_02.m_sectors;
1394 buf_toalign =
1395 ((inbuf->m_pkt_02.m_buf & 0x3F)) ? ((inbuf->m_pkt_02.m_buf & ~0x3F) - (inbuf->m_pkt_02.m_buf - 0x40)) : 0;
1396 buf_1_toalign = (inbuf->m_pkt_02.m_buf + all_sec_bytes) & ~0x3F;
1397 buf_sec_tmp = all_sec_bytes - (buf_1_toalign - inbuf->m_pkt_02.m_buf);
1398 if ( buf_toalign )
1399 {
1400 unsigned int buf_offs_sectors;
1401 u32 sectors_1;
1402
1403 buf_offs_sectors = buf_offs / sector_size;
1404 sectors_1 = (lbn_1_end < inbuf->m_pkt_02.m_lbn + buf_offs / sector_size + 2) ? 1 : 2;
1405 VERBOSE_PRINTF(
1406 1,
1407 "0 CD_READ LBN= %d sectors= %d all= %d\n",
1408 (int)(inbuf->m_pkt_02.m_lbn + buf_offs_sectors),
1409 (int)sectors_1,
1410 (int)inbuf->m_pkt_02.m_sectors);
1411 cmd_error = sceCdReadCDDA(
1412 inbuf->m_pkt_02.m_lbn + buf_offs_sectors, sectors_1, g_cdvdfsv_rtocbuf, (sceCdRMode *)&inbuf->m_pkt_02.m_mode);
1413 sceCdSync(3);
1414 error_code = sceCdGetError();
1415 if ( error_code || !cmd_error )
1416 {
1417 if ( !cmd_error )
1418 sceCdSC(0xFFFFFFFE, &g_cdvdfsv_rderror);
1419 VERBOSE_PRINTF(1, "Read error code %x cmd error %d\n", error_code, cmd_error);
1420 if ( error_code == SCECdErEOM || error_code == SCECdErSFRMTNG )
1421 error_code_tmp = error_code;
1422 else
1423 {
1424 buf_toalign = 0;
1425 }
1426 }
1427 if ( error_code_tmp && error_code_tmp != SCECdErEOM && error_code_tmp != SCECdErSFRMTNG )
1428 {
1429 for ( i = 0; i < buf_toalign; i += 1 )
1430 {
1431 g_cdvdfsv_eereadx.m_pbuf1[i] = g_cdvdfsv_rtocbuf[i];
1432 }
1433 buf_offs += buf_toalign;
1434 }
1435 }
1436 if ( error_code_tmp && error_code_tmp != SCECdErEOM && error_code_tmp != SCECdErSFRMTNG )
1437 {
1438 unsigned int sector_count_in_bytes;
1439 unsigned int buf_aligned;
1440
1441 for ( buf_aligned = inbuf->m_pkt_02.m_buf + buf_toalign; buf_aligned < buf_1_toalign;
1442 buf_aligned += sector_count_in_bytes )
1443 {
1444 unsigned int buf_align_remain;
1445 unsigned int buf_offs_mod_sector_size;
1446 u32 lsn_2;
1447 u32 sector_count;
1448
1449 buf_align_remain = buf_1_toalign - buf_aligned;
1450 buf_offs_mod_sector_size = buf_offs % sector_size;
1451 lsn_2 = inbuf->m_pkt_02.m_lbn + buf_offs / sector_size;
1452 sector_count_in_bytes = 8 * sector_size;
1453 if ( sector_count_in_bytes >= buf_align_remain )
1454 {
1455 sector_count_in_bytes = buf_align_remain;
1456 sector_count =
1457 (buf_align_remain / sector_size) + (!!(buf_align_remain % sector_size)) + (!!buf_offs_mod_sector_size);
1458 }
1459 else
1460 {
1461 sector_count = 8 + (!!(buf_offs % sector_size));
1462 }
1463 if ( sector_count > lbn_1_end - lsn_2 )
1464 sector_count = lbn_1_end - lsn_2;
1465 while ( cdvdfsv_checkdmastat(trid1) >= 0 )
1466 ;
1467 cmd_error = sceCdReadCDDA(lsn_2, sector_count, g_cdvdfsv_rtocbuf, (sceCdRMode *)&inbuf->m_pkt_02.m_mode);
1468 sceCdSync(3);
1469 error_code = sceCdGetError();
1470 if ( error_code || !cmd_error )
1471 {
1472 if ( !cmd_error )
1473 sceCdSC(0xFFFFFFFE, &g_cdvdfsv_rderror);
1474 VERBOSE_PRINTF(1, "Read error code %x cmd error %d\n", error_code, cmd_error);
1475 if ( error_code == SCECdErEOM || error_code == SCECdErSFRMTNG )
1476 {
1477 error_code_tmp = error_code;
1478 break;
1479 }
1480 }
1481 if ( buf_offs_mod_sector_size )
1482 optimized_memcpy(g_cdvdfsv_rtocbuf, &g_cdvdfsv_rtocbuf[buf_offs_mod_sector_size], sector_count_in_bytes);
1483 g_cdvdfsv_eereadfull_dma1.src = g_cdvdfsv_rtocbuf;
1484 g_cdvdfsv_eereadfull_dma1.size = sector_count_in_bytes;
1485 g_cdvdfsv_eereadfull_dma1.attr = 0;
1486 g_cdvdfsv_eereadfull_dma1.dest = (char *)buf_aligned;
1487 g_cdvdfsv_readpos = buf_offs;
1488 while ( 1 )
1489 {
1490 CpuSuspendIntr(&state);
1491 trid1 = sceSifSetDma(&g_cdvdfsv_eereadfull_dma1, 1);
1492 CpuResumeIntr(state);
1493 if ( trid1 )
1494 break;
1495 DelayThread(500);
1496 }
1497 if ( (unsigned int)buflen >= 0x19 )
1498 {
1499 CpuSuspendIntr(&state);
1500 sceSifSetDma(&g_cdvdfsv_eereadfull_dma2, 1);
1501 CpuResumeIntr(state);
1502 }
1503 buf_offs += sector_count_in_bytes;
1504 }
1505 }
1506 if ( (error_code_tmp && error_code_tmp != SCECdErEOM && error_code_tmp != SCECdErSFRMTNG) && buf_sec_tmp )
1507 {
1508 u32 sectors_3;
1509 u32 lsn_3;
1510
1511 lsn_3 = inbuf->m_pkt_02.m_lbn + buf_offs / sector_size;
1512 sectors_3 = (lbn_1_end < lsn_3 + 2) ? 1 : 2;
1513 VERBOSE_PRINTF(
1514 1,
1515 "0 CD_READ LBN= %d sectors= %d all= %d\n",
1516 (int)(inbuf->m_pkt_02.m_lbn + buf_offs / sector_size),
1517 (int)sectors_3,
1518 (int)inbuf->m_pkt_02.m_sectors);
1519 VERBOSE_PRINTF(1, "2 CD_READ LBN= %d sectors= %d\n", (int)lsn_3, (int)sectors_3);
1520 cmd_error = sceCdReadCDDA(lsn_3, sectors_3, g_cdvdfsv_rtocbuf, (sceCdRMode *)&inbuf->m_pkt_02.m_mode);
1521 sceCdSync(3);
1522 error_code = sceCdGetError();
1523 if ( error_code || !cmd_error )
1524 {
1525 if ( !cmd_error )
1526 sceCdSC(0xFFFFFFFE, &g_cdvdfsv_rderror);
1527 VERBOSE_PRINTF(1, "Read error code %x cmd error %d\n", error_code, cmd_error);
1528 if ( error_code == SCECdErEOM || error_code == SCECdErSFRMTNG )
1529 error_code_tmp = error_code;
1530 else
1531 buf_sec_tmp = 0;
1532 }
1533 for ( i = 0; i < buf_sec_tmp; i += 1 )
1534 {
1535 g_cdvdfsv_eereadx.m_pbuf2[i] = g_cdvdfsv_rtocbuf[(buf_offs % sector_size) + i];
1536 }
1537 buf_offs += buf_sec_tmp;
1538 }
1539 g_cdvdfsv_eereadx.m_b1len = buf_toalign;
1540 g_cdvdfsv_eereadx.m_b2len = buf_sec_tmp;
1541 g_cdvdfsv_eereadx.m_b1dst = inbuf->m_pkt_02.m_buf;
1542 g_cdvdfsv_eereadx.m_b2dst = buf_1_toalign;
1543 while ( cdvdfsv_checkdmastat(trid1) >= 0 )
1544 ;
1545 g_cdvdfsv_eereadfull_dma1.src = &g_cdvdfsv_eereadx;
1546 g_cdvdfsv_eereadfull_dma1.size = sizeof(g_cdvdfsv_eereadx);
1547 g_cdvdfsv_eereadfull_dma1.attr = 0;
1548 g_cdvdfsv_readpos = buf_offs;
1549 g_cdvdfsv_eereadfull_dma1.dest = (void *)inbuf->m_pkt_02.m_eeremaindest;
1550 while ( 1 )
1551 {
1552 CpuSuspendIntr(&state);
1553 trid2 = sceSifSetDma(&g_cdvdfsv_eereadfull_dma1, 1);
1554 if ( (unsigned int)buflen >= 0x19 )
1555 sceSifSetDma(&g_cdvdfsv_eereadfull_dma2, 1);
1556 CpuResumeIntr(state);
1557 if ( trid2 )
1558 break;
1559 DelayThread(500);
1560 }
1561 while ( cdvdfsv_checkdmastat(trid2) >= 0 )
1562 ;
1563 if ( error_code_tmp )
1564 sceCdSC(0xFFFFFFFE, &error_code_tmp);
1565 VERBOSE_PRINTF(1, "read end\n");
1566 outbuf->m_retres = buf_offs;
1567}
1568
1569void *cbrpc_rpc2_diskready(int fno, void *buffer, int length)
1570{
1571 (void)fno;
1572 (void)length;
1573
1574 // The following call to sceCdStatus was inlined
1575 VERBOSE_KPRINTF(1, "DISK READY call 0x%02x\n", sceCdStatus());
1576 // The following call to sceCdDiskReady was inlined
1577 g_diskready_res.m_retres = sceCdDiskReady(((const cdvdfsv_rpc2_inpacket_t *)buffer)->m_mode);
1578 return (void *)&g_diskready_res;
1579}
1580
1581static void cdvdfsv_rpc5_04_gettoc(const cdvdfsv_rpc5_inpacket_t *inbuf, int buflen, cdvdfsv_rpc5_outpacket_t *outbuf)
1582{
1583 int trid;
1584 int state;
1585
1586 (void)buflen;
1587
1588 VERBOSE_PRINTF(1, "GET TOC call 0x%08x\n", (int)inbuf);
1589 outbuf->m_retres = sceCdGetToc((u8 *)g_cdvdfsv_rtocbuf);
1590 VERBOSE_PRINTF(1, "GET TOC called\n");
1591 g_cdvdfsv_rtocsdd.src = g_cdvdfsv_rtocbuf;
1592 g_cdvdfsv_rtocsdd.size = 0x810;
1593 g_cdvdfsv_rtocsdd.attr = 0;
1594 g_cdvdfsv_rtocsdd.dest = (void *)inbuf->m_pkt_04.m_eedest;
1595 while ( 1 )
1596 {
1597 CpuSuspendIntr(&state);
1598 trid = sceSifSetDma(&g_cdvdfsv_rtocsdd, 1);
1599 CpuResumeIntr(state);
1600 if ( trid )
1601 break;
1602 DelayThread(500);
1603 }
1604 while ( cdvdfsv_checkdmastat(trid) >= 0 )
1605 ;
1606 // The following call to sceCdGetDiskType was inlined
1607 switch ( sceCdGetDiskType() )
1608 {
1609 case SCECdPS2DVD:
1610 case SCECdDVDVR:
1611 case SCECdDVDV:
1612 outbuf->m_pkt_04.m_isdvd = 1;
1613 break;
1614 default:
1615 outbuf->m_pkt_04.m_isdvd = 0;
1616 break;
1617 }
1618}
1619
1620static void cdvdfsv_rpc3_03_disktype(const cdvdfsv_rpc3_inpacket_t *inbuf, int buflen, cdvdfsv_rpc3_outpacket_t *outbuf)
1621{
1622 (void)inbuf;
1623 (void)buflen;
1624
1625 outbuf->m_retres = sceCdGetDiskType();
1626}
1627
1628static void cdvdfsv_rpc3_0C_cdstatus(const cdvdfsv_rpc3_inpacket_t *inbuf, int buflen, cdvdfsv_rpc3_outpacket_t *outbuf)
1629{
1630 (void)inbuf;
1631 (void)buflen;
1632
1633 outbuf->m_retres = sceCdStatus();
1634}
1635
1636static void cdvdfsv_rpc3_06_ri(const cdvdfsv_rpc3_inpacket_t *inbuf, int buflen, cdvdfsv_rpc3_outpacket_t *outbuf)
1637{
1638 int i;
1639 u32 efbits;
1640
1641 (void)inbuf;
1642 (void)buflen;
1643
1644 outbuf->m_retres = 0;
1645 for ( i = 0; i < 3 && !outbuf->m_retres; i += 1 )
1646 {
1647 WaitEventFlag(g_scmd_evid, 1, WEF_AND, &efbits);
1648 outbuf->m_retres = sceCdRI(outbuf->m_pkt_06.m_buffer, &outbuf->m_pkt_06.m_result);
1649 }
1650}
1651
1652static void cdvdfsv_rpc3_1A_rm(const cdvdfsv_rpc3_inpacket_t *inbuf, int buflen, cdvdfsv_rpc3_outpacket_t *outbuf)
1653{
1654 int i;
1655 u32 efbits;
1656
1657 (void)inbuf;
1658 (void)buflen;
1659
1660 outbuf->m_retres = 0;
1661 for ( i = 0; i < 3 && !outbuf->m_retres; i += 1 )
1662 {
1663 WaitEventFlag(g_scmd_evid, 1, WEF_AND, &efbits);
1664 outbuf->m_retres = sceCdRM(outbuf->m_pkt_1A.m_buffer, &outbuf->m_pkt_1A.m_status);
1665 }
1666}
1667
1668#ifdef CDVD_VARIANT_DNAS
1669static void cdvdfsv_rpc3_24_readguid(const cdvdfsv_rpc3_inpacket_t *inbuf, int buflen, cdvdfsv_rpc3_outpacket_t *outbuf)
1670{
1671 int i;
1672 u32 efbits;
1673
1674 (void)inbuf;
1675 (void)buflen;
1676
1677 outbuf->m_retres = 0;
1678 for ( i = 0; i < 3 && !outbuf->m_retres; i += 1 )
1679 {
1680 WaitEventFlag(g_scmd_evid, 1, WEF_AND, &efbits);
1681 outbuf->m_retres = sceCdReadGUID(&outbuf->m_pkt_24.m_guid);
1682 }
1683}
1684
1685static void
1686cdvdfsv_rpc3_26_readmodelid(const cdvdfsv_rpc3_inpacket_t *inbuf, int buflen, cdvdfsv_rpc3_outpacket_t *outbuf)
1687{
1688 int i;
1689 u32 efbits;
1690
1691 (void)inbuf;
1692 (void)buflen;
1693
1694 outbuf->m_retres = 0;
1695 for ( i = 0; i < 3 && !outbuf->m_retres; i += 1 )
1696 {
1697 WaitEventFlag(g_scmd_evid, 1, WEF_AND, &efbits);
1698 outbuf->m_retres = sceCdReadModelID(&outbuf->m_pkt_26.m_id);
1699 }
1700}
1701#endif
1702
1703static void cdvdfsv_rpc3_22_mmode(const cdvdfsv_rpc3_inpacket_t *inbuf, int buflen, cdvdfsv_rpc3_outpacket_t *outbuf)
1704{
1705 if ( buflen == 4 || !inbuf->m_pkt_22.m_char4 )
1706 {
1707 outbuf->m_retres = sceCdMmode(inbuf->m_pkt_22.m_media);
1708 }
1709}
1710
1711static void
1712cdvdfsv_rpc3_23_changethreadpriority(const cdvdfsv_rpc3_inpacket_t *inbuf, int buflen, cdvdfsv_rpc3_outpacket_t *outbuf)
1713{
1714 (void)buflen;
1715
1716 outbuf->m_retres = sceCdChangeThreadPriority(inbuf->m_pkt_23.m_priority);
1717}
1718
1719static void cdvdfsv_rpc3_21_poweroff(const cdvdfsv_rpc3_inpacket_t *inbuf, int buflen, cdvdfsv_rpc3_outpacket_t *outbuf)
1720{
1721 int i;
1722 u32 efbits;
1723
1724 (void)inbuf;
1725 (void)buflen;
1726
1727 outbuf->m_retres = 0;
1728 for ( i = 0; i < 3 && !outbuf->m_retres; i += 1 )
1729 {
1730 WaitEventFlag(g_scmd_evid, 1, WEF_AND, &efbits);
1731 outbuf->m_retres = sceCdPowerOff(&outbuf->m_pkt_21.m_result);
1732 }
1733}
1734
1735static void
1736cdvdfsv_rpc3_15_ctrladout(const cdvdfsv_rpc3_inpacket_t *inbuf, int buflen, cdvdfsv_rpc3_outpacket_t *outbuf)
1737{
1738 int i;
1739 u32 efbits;
1740
1741 (void)buflen;
1742
1743 outbuf->m_retres = 0;
1744 for ( i = 0; i < 3 && !outbuf->m_retres; i += 1 )
1745 {
1746 WaitEventFlag(g_scmd_evid, 1, WEF_AND, &efbits);
1747 outbuf->m_retres = sceCdCtrlADout(inbuf->m_pkt_15.m_mode, &outbuf->m_pkt_15.m_status);
1748 }
1749}
1750
1751static void
1752cdvdfsv_rpc3_01_readclock(const cdvdfsv_rpc3_inpacket_t *inbuf, int buflen, cdvdfsv_rpc3_outpacket_t *outbuf)
1753{
1754 int i;
1755 u32 efbits;
1756
1757 (void)inbuf;
1758 (void)buflen;
1759
1760 outbuf->m_retres = 0;
1761 for ( i = 0; i < 3 && !outbuf->m_retres; i += 1 )
1762 {
1763 WaitEventFlag(g_scmd_evid, 1, WEF_AND, &efbits);
1764 outbuf->m_retres = sceCdReadClock(&outbuf->m_pkt_01.m_clock);
1765 }
1766}
1767
1768#ifdef CDVD_VARIANT_DNAS
1769static void
1770cdvdfsv_rpc5_11_readdiskid(const cdvdfsv_rpc5_inpacket_t *inbuf, int buflen, cdvdfsv_rpc5_outpacket_t *outbuf)
1771{
1772 (void)inbuf;
1773 (void)buflen;
1774
1775 outbuf->m_retres = sceCdReadDiskID((unsigned int *)&(outbuf->m_pkt_11.m_diskid));
1776}
1777
1778static void
1779cdvdfsv_rpc5_17_doesuniquekeyexist(const cdvdfsv_rpc5_inpacket_t *inbuf, int buflen, cdvdfsv_rpc5_outpacket_t *outbuf)
1780{
1781 (void)inbuf;
1782 (void)buflen;
1783
1784 outbuf->m_retres = sceCdDoesUniqueKeyExist(&outbuf->m_pkt_17.m_status);
1785}
1786#endif
1787
1788static void
1789cdvdfsv_rpc3_0B_applyscmd(const cdvdfsv_rpc3_inpacket_t *inbuf, int buflen, cdvdfsv_rpc3_outpacket_t *outbuf)
1790{
1791 (void)buflen;
1792
1794 inbuf->m_pkt_0B.m_cmdNum, &inbuf->m_pkt_0B.m_inBuff, inbuf->m_pkt_0B.m_inBuffSize, &(outbuf->m_pkt_0B.m_outbuf));
1795}
1796
1797static void
1798cdvdfsv_rpc5_0C_applyncmd(const cdvdfsv_rpc5_inpacket_t *inbuf, int buflen, cdvdfsv_rpc5_outpacket_t *outbuf)
1799{
1800 (void)buflen;
1801
1802 outbuf->m_retres = sceCdApplyNCmd(inbuf->m_pkt_0C.m_cmdNum, &inbuf->m_pkt_0C.m_inBuff, inbuf->m_pkt_0C.m_inBuffSize);
1803 sceCdSync(2);
1804}
1805
1806static void cdvdfsv_rpc3_04_geterror(const cdvdfsv_rpc3_inpacket_t *inbuf, int buflen, cdvdfsv_rpc3_outpacket_t *outbuf)
1807{
1808 (void)inbuf;
1809 (void)buflen;
1810
1811 outbuf->m_retres = sceCdGetError();
1812}
1813
1814static void cdvdfsv_rpc3_05_trayreq(const cdvdfsv_rpc3_inpacket_t *inbuf, int buflen, cdvdfsv_rpc3_outpacket_t *outbuf)
1815{
1816 int i;
1817 u32 efbits;
1818
1819 (void)buflen;
1820
1821 outbuf->m_retres = 0;
1822 for ( i = 0; i < 3 && !outbuf->m_retres; i += 1 )
1823 {
1824 WaitEventFlag(g_scmd_evid, 1, WEF_AND, &efbits);
1825 outbuf->m_retres = sceCdTrayReq(inbuf->m_pkt_05.m_param, &outbuf->m_pkt_05.m_traychk);
1826 }
1827}
1828
1829static void
1830cdvdfsv_rpc3_25_settimeout(const cdvdfsv_rpc3_inpacket_t *inbuf, int buflen, cdvdfsv_rpc3_outpacket_t *outbuf)
1831{
1832 (void)buflen;
1833
1834 outbuf->m_retres = sceCdSetTimeout(inbuf->m_pkt_25.m_param, inbuf->m_pkt_25.m_timeout);
1835}
1836
1837static void
1838cdvdfsv_rpc3_27_readdvddualinfo(const cdvdfsv_rpc3_inpacket_t *inbuf, int buflen, cdvdfsv_rpc3_outpacket_t *outbuf)
1839{
1840 (void)inbuf;
1841 (void)buflen;
1842
1843 outbuf->m_retres = sceCdReadDvdDualInfo(&outbuf->m_pkt_27.m_on_dual, &outbuf->m_pkt_27.m_layer1_start);
1844}
1845
1846static int cdvdfsv_rpc5_0E_diskready()
1847{
1848 int is_detecting;
1849 int scres_unused;
1850
1851 is_detecting = 0;
1852 // The following call to sceCdGetDiskType was inlined
1853 switch ( sceCdGetDiskType() )
1854 {
1855 case SCECdDETCT:
1856 case SCECdDETCTCD:
1857 case SCECdDETCTDVDS:
1858 case SCECdDETCTDVDD:
1859 is_detecting = 1;
1860 break;
1861 default:
1862 break;
1863 }
1864 // The following call to sceCdDiskReady was inlined
1865 if (
1866 (sceCdDiskReady(8) & 0xC0) != 0x40 || sceCdSC(0xFFFFFFFD, &scres_unused) || !sceCdSC(0xFFFFFFF4, &scres_unused)
1867 || is_detecting )
1868 {
1869 VERBOSE_PRINTF(1, "Drive Not Ready\n");
1870 return 6;
1871 }
1872 return 2;
1873}
1874
1875static void *cbrpc_rpc5_cdvdncmds(int fno, void *buffer, int length)
1876{
1877 int scres_unused;
1878 int fno_1;
1879
1880 fno_1 = fno;
1881 VERBOSE_PRINTF(1, "sce_cdvd N cmd start %d\n", fno);
1882 g_cdvdfsv_rpc5flg = 1;
1883 sceCdSC(0xFFFFFFF6, &fno_1);
1884 switch ( fno )
1885 {
1886 case 1:
1887 // The following call to sceCdGetDiskType was inlined
1888 cdvdfsv_rpc5_01_readee(
1889 buffer, length, &g_crr, !(sceCdGetDiskType() ^ SCECdPS2DVD), !sceCdSC(0xFFFFFFFC, &scres_unused), 0);
1890 break;
1891 case 2:
1892 cdvdfsv_rpc5_02_readcdda(buffer, length, &g_crr);
1893 break;
1894 case 4:
1895 cdvdfsv_rpc5_04_gettoc(buffer, length, &g_crr);
1896 break;
1897 case 5:
1898 VERBOSE_PRINTF(1, "Call Seek lsn= %d\n", (int)(((const cdvdfsv_rpc5_inpacket_t *)buffer)->m_pkt_05.m_lbn));
1899 g_crr.m_retres = sceCdSeek(((const cdvdfsv_rpc5_inpacket_t *)buffer)->m_pkt_05.m_lbn);
1900 VERBOSE_PRINTF(1, "Call Seek end\n");
1901 sceCdSync(6);
1902 break;
1903 case 6:
1904 VERBOSE_PRINTF(1, "Call Standby\n");
1905 g_crr.m_retres = sceCdStandby();
1906 sceCdSync(4);
1907 VERBOSE_PRINTF(1, "Call Standby called\n");
1908 break;
1909 case 7:
1910 VERBOSE_PRINTF(1, "Call Stop\n");
1911 g_crr.m_retres = sceCdStop();
1912 sceCdSync(4);
1913 break;
1914 case 8:
1915 VERBOSE_PRINTF(1, "Call Pause\n");
1916 g_crr.m_retres = sceCdPause();
1917 sceCdSync(6);
1918 break;
1919 case 9:
1920 if ( devctl("cdrom_stm0:", 0x4396, buffer, length, &g_crr.m_retres, 4) < 0 )
1921 g_crr.m_retres = 0;
1922 break;
1923 case 10:
1924 if ( devctl("cdrom_stm0:", 0x4398, buffer, length, &g_crr.m_retres, 4) < 0 )
1925 g_crr.m_retres = 0;
1926 break;
1927 case 12:
1928 cdvdfsv_rpc5_0C_applyncmd(buffer, length, &g_crr);
1929 break;
1930 case 13:
1931 cdvdfsv_rpc5_0D_iopmread(buffer, length, &g_crr);
1932 break;
1933 case 14:
1934 g_crr.m_retres = cdvdfsv_rpc5_0E_diskready();
1935 break;
1936 case 15:
1937 cdvdfsv_rpc5_0F_readchain(buffer, length, &g_crr);
1938 break;
1939#ifdef CDVD_VARIANT_DNAS
1940 case 17:
1941 cdvdfsv_rpc5_11_readdiskid(buffer, length, &g_crr);
1942 break;
1943#endif
1944 case 19:
1945 // The following call to sceCdGetDiskType was inlined
1946 cdvdfsv_rpc5_01_readee(
1947 buffer, length, &g_crr, !(sceCdGetDiskType() ^ SCECdPS2DVD), 1, !g_cdvdman_istruct_ptr->m_no_dec_flag);
1948 break;
1949#ifdef CDVD_VARIANT_DNAS
1950 case 23:
1951 cdvdfsv_rpc5_17_doesuniquekeyexist(buffer, length, &g_crr);
1952 break;
1953#endif
1954 default:
1955 VERBOSE_PRINTF(1, "sce_cdvd no block IO :unrecognized code %x\n", fno);
1956 g_crr.m_retres = 0;
1957 break;
1958 }
1959 fno_1 = 0;
1960 sceCdSC(0xFFFFFFF6, &fno_1);
1961 g_cdvdfsv_rpc5flg = 0;
1962 VERBOSE_PRINTF(1, "sce_cdvd N cmd end\n");
1963 return (void *)&g_crr;
1964}
1965
1966// cppcheck-suppress constParameterCallback
1967static void *cbrpc_rpc3_cdvdscmds(int fno, void *buffer, int length)
1968{
1969 VERBOSE_PRINTF(1, "sce_cdvd S cmd start %d\n", fno);
1970 g_cdvdfsv_rpc3flg = 1;
1971 switch ( fno )
1972 {
1973 case 1:
1974 cdvdfsv_rpc3_01_readclock(buffer, length, &g_outbuf);
1975 break;
1976 case 3:
1977 cdvdfsv_rpc3_03_disktype(buffer, length, &g_outbuf);
1978 break;
1979 case 4:
1980 cdvdfsv_rpc3_04_geterror(buffer, length, &g_outbuf);
1981 break;
1982 case 5:
1983 cdvdfsv_rpc3_05_trayreq(buffer, length, &g_outbuf);
1984 break;
1985 case 6:
1986 cdvdfsv_rpc3_06_ri(buffer, length, &g_outbuf);
1987 break;
1988 case 11:
1989 cdvdfsv_rpc3_0B_applyscmd(buffer, length, &g_outbuf);
1990 break;
1991 case 12:
1992 cdvdfsv_rpc3_0C_cdstatus(buffer, length, &g_outbuf);
1993 break;
1994 case 21:
1995 cdvdfsv_rpc3_15_ctrladout(buffer, length, &g_outbuf);
1996 break;
1997 case 22:
1998 cdvdfsv_rpc3_16_break(buffer, length, &g_outbuf);
1999 break;
2000 case 26:
2001 cdvdfsv_rpc3_1A_rm(buffer, length, &g_outbuf);
2002 break;
2003 case 33:
2004 cdvdfsv_rpc3_21_poweroff(buffer, length, &g_outbuf);
2005 break;
2006 case 34:
2007 cdvdfsv_rpc3_22_mmode(buffer, length, &g_outbuf);
2008 break;
2009 case 35:
2010 cdvdfsv_rpc3_23_changethreadpriority(buffer, length, &g_outbuf);
2011 break;
2012#ifdef CDVD_VARIANT_DNAS
2013 case 36:
2014 cdvdfsv_rpc3_24_readguid(buffer, length, &g_outbuf);
2015 break;
2016#endif
2017 case 37:
2018 cdvdfsv_rpc3_25_settimeout(buffer, length, &g_outbuf);
2019 break;
2020#ifdef CDVD_VARIANT_DNAS
2021 case 38:
2022 cdvdfsv_rpc3_26_readmodelid(buffer, length, &g_outbuf);
2023 break;
2024#endif
2025 case 39:
2026 cdvdfsv_rpc3_27_readdvddualinfo(buffer, length, &g_outbuf);
2027 break;
2028 default:
2029 VERBOSE_PRINTF(1, "sce_cdvd block IO :unrecognized code 0x%02x\n", fno);
2030 g_outbuf.m_retres = 0;
2031 break;
2032 }
2033 VERBOSE_PRINTF(1, "sce_cdvd S cmd end\n");
2034 g_cdvdfsv_rpc3flg = 0;
2035 return (void *)&g_outbuf;
2036}
2037
2038static void cdvdfsv_poffloop()
2039{
2040 int trid;
2041 char cmdpkt[16];
2042 int scres;
2043 u32 efbits;
2044
2045 g_cdvdman_intr_efid = sceCdSC(0xFFFFFFF5, &scres);
2046 while ( 1 )
2047 {
2048 ClearEventFlag(g_cdvdman_intr_efid, ~4);
2049 WaitEventFlag(g_cdvdman_intr_efid, 4, WEF_AND, &efbits);
2050 if ( g_cdvdfsv_nopocm )
2051 break;
2052 if ( !g_cdvdfsv_plbreak )
2053 {
2054 while ( 1 )
2055 {
2056 trid = sceSifSendCmd(0x80000012, cmdpkt, sizeof(cmdpkt), 0, 0, 0);
2057 if ( trid )
2058 break;
2059 DelayThread(500);
2060 }
2061 while ( cdvdfsv_checkdmastat(trid) >= 0 )
2062 ;
2063 }
2064 }
2065}
2066
2067static void cdvdfsv_rpc1_th(void *arg)
2068{
2069 (void)arg;
2070
2071 sceSifSetRpcQueue(&g_rpc_qdata1, GetThreadId());
2072 sceSifRegisterRpc(&g_rpc_sdata1, 0x80000592, cbrpc_rpc1_cdinit, g_rpc_buffer1, 0, 0, &g_rpc_qdata1);
2073 sceSifRegisterRpc(&g_rpc_sdata2, 0x8000059A, cbrpc_rpc2_diskready, g_rpc_buffer2, 0, 0, &g_rpc_qdata1);
2074 sceSifRegisterRpc(&g_rpc_sdata3, 0x80000593, cbrpc_rpc3_cdvdscmds, g_rpc_buffer3, 0, 0, &g_rpc_qdata1);
2075 sceSifRpcLoop(&g_rpc_qdata1);
2076 ExitDeleteThread();
2077}
2078
2079static void cdvdfsv_rpc3_th(void *arg)
2080{
2081 (void)arg;
2082
2083 sceSifSetRpcQueue(&g_rpc_qdata3, GetThreadId());
2084 sceSifRegisterRpc(&g_rpc_sdata6, 0x8000059C, cbrpc_rpc2_diskready, g_rpc_buffer2, 0, 0, &g_rpc_qdata3);
2085 sceSifRpcLoop(&g_rpc_qdata3);
2086 ExitDeleteThread();
2087}
2088
2089static void cdvdfsv_rpc2_th(void *arg)
2090{
2091 (void)arg;
2092
2093 sceSifSetRpcQueue(&g_rpc_qdata2, GetThreadId());
2094 sceSifRegisterRpc(&g_rpc_sdata4, 0x80000597, cbrpc_rpc4_fscall, g_rpc_buffer4, 0, 0, &g_rpc_qdata2);
2095 sceSifRegisterRpc(&g_rpc_sdata5, 0x80000595, cbrpc_rpc5_cdvdncmds, g_rpc_buffer5, 0, 0, &g_rpc_qdata2);
2096 sceSifRpcLoop(&g_rpc_qdata2);
2097 ExitDeleteThread();
2098}
2099
2100// Unofficial: unused obfuscation code was removed
2101
2102// clang-format off
2103__asm__ (
2104 "\t" ".set push" "\n"
2105 "\t" ".set noat" "\n"
2106 "\t" ".set noreorder" "\n"
2107 "\t" ".global optimized_memcpy" "\n"
2108 "\t" "optimized_memcpy:" "\n"
2109 "\t" " srl $a3, $a2, 2" "\n"
2110 "\t" " beqz $a3, .Loptimized_memcpy_12" "\n"
2111 "\t" " or $a3, $a0, $a1" "\n"
2112 "\t" " andi $a3, $a3, 0x3" "\n"
2113 "\t" " bnez $a3, .Loptimized_memcpy_3" "\n"
2114 "\t" " nop" "\n"
2115 "\t" " srl $a3, $a2, 2" "\n"
2116 "\t" " addiu $at, $zero, 0xC" "\n"
2117 "\t" " div $zero, $a3, $at" "\n"
2118 "\t" " mflo $a3" "\n"
2119 "\t" " mfhi $v1" "\n"
2120 "\t" " beqz $v1, .Loptimized_memcpy_2" "\n"
2121 "\t" " nop" "\n"
2122 "\t" ".Loptimized_memcpy_1:" "\n"
2123 "\t" " lw $v0, 0x0($a1)" "\n"
2124 "\t" " addiu $v1, $v1, -0x1" "\n"
2125 "\t" " sw $v0, 0x0($a0)" "\n"
2126 "\t" " addiu $a1, $a1, 0x4" "\n"
2127 "\t" " bnez $v1, .Loptimized_memcpy_1" "\n"
2128 "\t" " addiu $a0, $a0, 0x4" "\n"
2129 "\t" " beqz $a3, .Loptimized_memcpy_12" "\n"
2130 "\t" " nop" "\n"
2131 "\t" ".Loptimized_memcpy_2:" "\n"
2132 "\t" " lw $v0, 0x0($a1)" "\n"
2133 "\t" " lw $v1, 0x4($a1)" "\n"
2134 "\t" " lw $t0, 0x8($a1)" "\n"
2135 "\t" " lw $t1, 0xC($a1)" "\n"
2136 "\t" " lw $t2, 0x10($a1)" "\n"
2137 "\t" " lw $t3, 0x14($a1)" "\n"
2138 "\t" " lw $t4, 0x18($a1)" "\n"
2139 "\t" " lw $t5, 0x1C($a1)" "\n"
2140 "\t" " lw $t6, 0x20($a1)" "\n"
2141 "\t" " lw $t7, 0x24($a1)" "\n"
2142 "\t" " lw $t8, 0x28($a1)" "\n"
2143 "\t" " lw $t9, 0x2C($a1)" "\n"
2144 "\t" " addiu $a3, $a3, -0x1" "\n"
2145 "\t" " sw $v0, 0x0($a0)" "\n"
2146 "\t" " sw $v1, 0x4($a0)" "\n"
2147 "\t" " sw $t0, 0x8($a0)" "\n"
2148 "\t" " sw $t1, 0xC($a0)" "\n"
2149 "\t" " sw $t2, 0x10($a0)" "\n"
2150 "\t" " sw $t3, 0x14($a0)" "\n"
2151 "\t" " sw $t4, 0x18($a0)" "\n"
2152 "\t" " sw $t5, 0x1C($a0)" "\n"
2153 "\t" " sw $t6, 0x20($a0)" "\n"
2154 "\t" " sw $t7, 0x24($a0)" "\n"
2155 "\t" " sw $t8, 0x28($a0)" "\n"
2156 "\t" " sw $t9, 0x2C($a0)" "\n"
2157 "\t" " addiu $a1, $a1, 0x30" "\n"
2158 "\t" " bnez $a3, .Loptimized_memcpy_2" "\n"
2159 "\t" " addiu $a0, $a0, 0x30" "\n"
2160 "\t" " j .Loptimized_memcpy_12" "\n"
2161 "\t" " nop" "\n"
2162 "\t" ".Loptimized_memcpy_3:" "\n"
2163 "\t" " andi $a3, $a0, 0x3" "\n"
2164 "\t" " beqz $a3, .Loptimized_memcpy_6" "\n"
2165 "\t" " andi $a3, $a1, 0x3" "\n"
2166 "\t" " beqz $a3, .Loptimized_memcpy_6" "\n"
2167 "\t" " nop" "\n"
2168 "\t" " srl $a3, $a2, 2" "\n"
2169 "\t" " addiu $at, $zero, 0xC" "\n"
2170 "\t" " div $zero, $a3, $at" "\n"
2171 "\t" " mflo $a3" "\n"
2172 "\t" " mfhi $v1" "\n"
2173 "\t" " beqz $v1, .Loptimized_memcpy_5" "\n"
2174 "\t" " nop" "\n"
2175 "\t" ".Loptimized_memcpy_4:" "\n"
2176 "\t" " lwl $v0, 0x3($a1)" "\n"
2177 "\t" " lwr $v0, 0x0($a1)" "\n"
2178 "\t" " addiu $v1, $v1, -0x1" "\n"
2179 "\t" " swl $v0, 0x3($a0)" "\n"
2180 "\t" " swr $v0, 0x0($a0)" "\n"
2181 "\t" " addiu $a1, $a1, 0x4" "\n"
2182 "\t" " bnez $v1, .Loptimized_memcpy_4" "\n"
2183 "\t" " addiu $a0, $a0, 0x4" "\n"
2184 "\t" " beqz $a3, .Loptimized_memcpy_12" "\n"
2185 "\t" " nop" "\n"
2186 "\t" ".Loptimized_memcpy_5:" "\n"
2187 "\t" " lwl $v0, 0x3($a1)" "\n"
2188 "\t" " lwr $v0, 0x0($a1)" "\n"
2189 "\t" " lwl $v1, 0x7($a1)" "\n"
2190 "\t" " lwr $v1, 0x4($a1)" "\n"
2191 "\t" " lwl $t0, 0xB($a1)" "\n"
2192 "\t" " lwr $t0, 0x8($a1)" "\n"
2193 "\t" " lwl $t1, 0xF($a1)" "\n"
2194 "\t" " lwr $t1, 0xC($a1)" "\n"
2195 "\t" " lwl $t2, 0x13($a1)" "\n"
2196 "\t" " lwr $t2, 0x10($a1)" "\n"
2197 "\t" " lwl $t3, 0x17($a1)" "\n"
2198 "\t" " lwr $t3, 0x14($a1)" "\n"
2199 "\t" " lwl $t4, 0x1B($a1)" "\n"
2200 "\t" " lwr $t4, 0x18($a1)" "\n"
2201 "\t" " lwl $t5, 0x1F($a1)" "\n"
2202 "\t" " lwr $t5, 0x1C($a1)" "\n"
2203 "\t" " lwl $t6, 0x23($a1)" "\n"
2204 "\t" " lwr $t6, 0x20($a1)" "\n"
2205 "\t" " lwl $t7, 0x27($a1)" "\n"
2206 "\t" " lwr $t7, 0x24($a1)" "\n"
2207 "\t" " lwl $t8, 0x2B($a1)" "\n"
2208 "\t" " lwr $t8, 0x28($a1)" "\n"
2209 "\t" " lwl $t9, 0x2F($a1)" "\n"
2210 "\t" " lwr $t9, 0x2C($a1)" "\n"
2211 "\t" " addiu $a3, $a3, -0x1" "\n"
2212 "\t" " swl $v0, 0x3($a0)" "\n"
2213 "\t" " swr $v0, 0x0($a0)" "\n"
2214 "\t" " swl $v1, 0x7($a0)" "\n"
2215 "\t" " swr $v1, 0x4($a0)" "\n"
2216 "\t" " swl $t0, 0xB($a0)" "\n"
2217 "\t" " swr $t0, 0x8($a0)" "\n"
2218 "\t" " swl $t1, 0xF($a0)" "\n"
2219 "\t" " swr $t1, 0xC($a0)" "\n"
2220 "\t" " swl $t2, 0x13($a0)" "\n"
2221 "\t" " swr $t2, 0x10($a0)" "\n"
2222 "\t" " swl $t3, 0x17($a0)" "\n"
2223 "\t" " swr $t3, 0x14($a0)" "\n"
2224 "\t" " swl $t4, 0x1B($a0)" "\n"
2225 "\t" " swr $t4, 0x18($a0)" "\n"
2226 "\t" " swl $t5, 0x1F($a0)" "\n"
2227 "\t" " swr $t5, 0x1C($a0)" "\n"
2228 "\t" " swl $t6, 0x23($a0)" "\n"
2229 "\t" " swr $t6, 0x20($a0)" "\n"
2230 "\t" " swl $t7, 0x27($a0)" "\n"
2231 "\t" " swr $t7, 0x24($a0)" "\n"
2232 "\t" " swl $t8, 0x2B($a0)" "\n"
2233 "\t" " swr $t8, 0x28($a0)" "\n"
2234 "\t" " swl $t9, 0x2F($a0)" "\n"
2235 "\t" " swr $t9, 0x2C($a0)" "\n"
2236 "\t" " addiu $a1, $a1, 0x30" "\n"
2237 "\t" " bnez $a3, .Loptimized_memcpy_5" "\n"
2238 "\t" " addiu $a0, $a0, 0x30" "\n"
2239 "\t" " j .Loptimized_memcpy_12" "\n"
2240 "\t" " nop" "\n"
2241 "\t" ".Loptimized_memcpy_6:" "\n"
2242 "\t" " andi $a3, $a0, 0x3" "\n"
2243 "\t" " beqz $a3, .Loptimized_memcpy_9" "\n"
2244 "\t" " nop" "\n"
2245 "\t" " srl $a3, $a2, 2" "\n"
2246 "\t" " addiu $at, $zero, 0xC" "\n"
2247 "\t" " div $zero, $a3, $at" "\n"
2248 "\t" " mflo $a3" "\n"
2249 "\t" " mfhi $v1" "\n"
2250 "\t" " beqz $v1, .Loptimized_memcpy_8" "\n"
2251 "\t" " nop" "\n"
2252 "\t" ".Loptimized_memcpy_7:" "\n"
2253 "\t" " lw $v0, 0x0($a1)" "\n"
2254 "\t" " addiu $v1, $v1, -0x1" "\n"
2255 "\t" " swl $v0, 0x3($a0)" "\n"
2256 "\t" " swr $v0, 0x0($a0)" "\n"
2257 "\t" " addiu $a1, $a1, 0x4" "\n"
2258 "\t" " bnez $v1, .Loptimized_memcpy_7" "\n"
2259 "\t" " addiu $a0, $a0, 0x4" "\n"
2260 "\t" " beqz $a3, .Loptimized_memcpy_12" "\n"
2261 "\t" " nop" "\n"
2262 "\t" ".Loptimized_memcpy_8:" "\n"
2263 "\t" " lw $v0, 0x0($a1)" "\n"
2264 "\t" " lw $v1, 0x4($a1)" "\n"
2265 "\t" " lw $t0, 0x8($a1)" "\n"
2266 "\t" " lw $t1, 0xC($a1)" "\n"
2267 "\t" " lw $t2, 0x10($a1)" "\n"
2268 "\t" " lw $t3, 0x14($a1)" "\n"
2269 "\t" " lw $t4, 0x18($a1)" "\n"
2270 "\t" " lw $t5, 0x1C($a1)" "\n"
2271 "\t" " lw $t6, 0x20($a1)" "\n"
2272 "\t" " lw $t7, 0x24($a1)" "\n"
2273 "\t" " lw $t8, 0x28($a1)" "\n"
2274 "\t" " lw $t9, 0x2C($a1)" "\n"
2275 "\t" " addiu $a3, $a3, -0x1" "\n"
2276 "\t" " swl $v0, 0x3($a0)" "\n"
2277 "\t" " swr $v0, 0x0($a0)" "\n"
2278 "\t" " swl $v1, 0x7($a0)" "\n"
2279 "\t" " swr $v1, 0x4($a0)" "\n"
2280 "\t" " swl $t0, 0xB($a0)" "\n"
2281 "\t" " swr $t0, 0x8($a0)" "\n"
2282 "\t" " swl $t1, 0xF($a0)" "\n"
2283 "\t" " swr $t1, 0xC($a0)" "\n"
2284 "\t" " swl $t2, 0x13($a0)" "\n"
2285 "\t" " swr $t2, 0x10($a0)" "\n"
2286 "\t" " swl $t3, 0x17($a0)" "\n"
2287 "\t" " swr $t3, 0x14($a0)" "\n"
2288 "\t" " swl $t4, 0x1B($a0)" "\n"
2289 "\t" " swr $t4, 0x18($a0)" "\n"
2290 "\t" " swl $t5, 0x1F($a0)" "\n"
2291 "\t" " swr $t5, 0x1C($a0)" "\n"
2292 "\t" " swl $t6, 0x23($a0)" "\n"
2293 "\t" " swr $t6, 0x20($a0)" "\n"
2294 "\t" " swl $t7, 0x27($a0)" "\n"
2295 "\t" " swr $t7, 0x24($a0)" "\n"
2296 "\t" " swl $t8, 0x2B($a0)" "\n"
2297 "\t" " swr $t8, 0x28($a0)" "\n"
2298 "\t" " swl $t9, 0x2F($a0)" "\n"
2299 "\t" " swr $t9, 0x2C($a0)" "\n"
2300 "\t" " addiu $a1, $a1, 0x30" "\n"
2301 "\t" " bnez $a3, .Loptimized_memcpy_8" "\n"
2302 "\t" " addiu $a0, $a0, 0x30" "\n"
2303 "\t" " j .Loptimized_memcpy_12" "\n"
2304 "\t" " nop" "\n"
2305 "\t" ".Loptimized_memcpy_9:" "\n"
2306 "\t" " srl $a3, $a2, 2" "\n"
2307 "\t" " addiu $at, $zero, 0xC" "\n"
2308 "\t" " div $zero, $a3, $at" "\n"
2309 "\t" " mflo $a3" "\n"
2310 "\t" " mfhi $v1" "\n"
2311 "\t" " beqz $v1, .Loptimized_memcpy_11" "\n"
2312 "\t" " nop" "\n"
2313 "\t" ".Loptimized_memcpy_10:" "\n"
2314 "\t" " lwl $v0, 0x3($a1)" "\n"
2315 "\t" " lwr $v0, 0x0($a1)" "\n"
2316 "\t" " addiu $v1, $v1, -0x1" "\n"
2317 "\t" " sw $v0, 0x0($a0)" "\n"
2318 "\t" " addiu $a1, $a1, 0x4" "\n"
2319 "\t" " bnez $v1, .Loptimized_memcpy_10" "\n"
2320 "\t" " addiu $a0, $a0, 0x4" "\n"
2321 "\t" " beqz $a3, .Loptimized_memcpy_12" "\n"
2322 "\t" " nop" "\n"
2323 "\t" ".Loptimized_memcpy_11:" "\n"
2324 "\t" " lwl $v0, 0x3($a1)" "\n"
2325 "\t" " lwr $v0, 0x0($a1)" "\n"
2326 "\t" " lwl $v1, 0x7($a1)" "\n"
2327 "\t" " lwr $v1, 0x4($a1)" "\n"
2328 "\t" " lwl $t0, 0xB($a1)" "\n"
2329 "\t" " lwr $t0, 0x8($a1)" "\n"
2330 "\t" " lwl $t1, 0xF($a1)" "\n"
2331 "\t" " lwr $t1, 0xC($a1)" "\n"
2332 "\t" " lwl $t2, 0x13($a1)" "\n"
2333 "\t" " lwr $t2, 0x10($a1)" "\n"
2334 "\t" " lwl $t3, 0x17($a1)" "\n"
2335 "\t" " lwr $t3, 0x14($a1)" "\n"
2336 "\t" " lwl $t4, 0x1B($a1)" "\n"
2337 "\t" " lwr $t4, 0x18($a1)" "\n"
2338 "\t" " lwl $t5, 0x1F($a1)" "\n"
2339 "\t" " lwr $t5, 0x1C($a1)" "\n"
2340 "\t" " lwl $t6, 0x23($a1)" "\n"
2341 "\t" " lwr $t6, 0x20($a1)" "\n"
2342 "\t" " lwl $t7, 0x27($a1)" "\n"
2343 "\t" " lwr $t7, 0x24($a1)" "\n"
2344 "\t" " lwl $t8, 0x2B($a1)" "\n"
2345 "\t" " lwr $t8, 0x28($a1)" "\n"
2346 "\t" " lwl $t9, 0x2F($a1)" "\n"
2347 "\t" " lwr $t9, 0x2C($a1)" "\n"
2348 "\t" " addiu $a3, $a3, -0x1" "\n"
2349 "\t" " sw $v0, 0x0($a0)" "\n"
2350 "\t" " sw $v1, 0x4($a0)" "\n"
2351 "\t" " sw $t0, 0x8($a0)" "\n"
2352 "\t" " sw $t1, 0xC($a0)" "\n"
2353 "\t" " sw $t2, 0x10($a0)" "\n"
2354 "\t" " sw $t3, 0x14($a0)" "\n"
2355 "\t" " sw $t4, 0x18($a0)" "\n"
2356 "\t" " sw $t5, 0x1C($a0)" "\n"
2357 "\t" " sw $t6, 0x20($a0)" "\n"
2358 "\t" " sw $t7, 0x24($a0)" "\n"
2359 "\t" " sw $t8, 0x28($a0)" "\n"
2360 "\t" " sw $t9, 0x2C($a0)" "\n"
2361 "\t" " addiu $a1, $a1, 0x30" "\n"
2362 "\t" " bnez $a3, .Loptimized_memcpy_11" "\n"
2363 "\t" " addiu $a0, $a0, 0x30" "\n"
2364 "\t" ".Loptimized_memcpy_12:" "\n"
2365 "\t" " andi $v1, $a2, 0x3" "\n"
2366 "\t" " beqz $v1, .Loptimized_memcpy_14" "\n"
2367 "\t" " nop" "\n"
2368 "\t" ".Loptimized_memcpy_13:" "\n"
2369 "\t" " lb $v0, 0x0($a1)" "\n"
2370 "\t" " addiu $v1, $v1, -0x1" "\n"
2371 "\t" " sb $v0, 0x0($a0)" "\n"
2372 "\t" " addiu $a1, $a1, 0x1" "\n"
2373 "\t" " bnez $v1, .Loptimized_memcpy_13" "\n"
2374 "\t" " addiu $a0, $a0, 0x1" "\n"
2375 "\t" ".Loptimized_memcpy_14:" "\n"
2376 "\t" " addu $v0, $a2, $zero" "\n"
2377 "\t" " jr $ra" "\n"
2378 "\t" " nop" "\n"
2379 "\t" ".set pop" "\n"
2380);
2381// clang-format on
int sceCdRV(u32 lsn, u32 sectors, void *buf, sceCdRMode *mode, int arg5, void *cb)
Definition cdvdman.c:5620
int sceCdReadDiskID(unsigned int *id)
int CpuResumeIntr(int state)
Definition intrman.c:227
int QueryIntrContext(void)
int DisableIntr(int irq, int *res)
Definition intrman.c:395
int CpuSuspendIntr(int *state)
Definition intrman.c:205
int sceCdBreak(void)
Definition cdi.c:25
int sceCdReadModelID(unsigned int *id)
int sceCdSearchFile(sceCdlFILE *file, const char *name)
Definition cdi.c:114
int sceCdGetError(void)
Definition cdi.c:40
int sceCdPowerOff(u32 *result)
Definition cdvdman.c:5780
int sceCdDoesUniqueKeyExist(u32 *status)
int sceCdGetToc(u8 *toc)
Definition cdi.c:57
int sceCdInit(int mode)
Definition cdi.c:64
int sceCdReadDvdDualInfo(int *on_dual, unsigned int *layer1_start)
Definition cdvdman.c:3843
int sceCdStatus(void)
Definition cdi.c:152
int sceCdReadGUID(u64 *guid)
int sceCdChangeThreadPriority(int priority)
Definition cdvdfsv.c:270
int sceCdDiskReady(int mode)
Definition cdi.c:30
int sceCdPause(void)
Definition cdi.c:93
int sceCdRM(char *buffer, u32 *status)
Definition cdvdman.c:5692
u32 sceCdPosToInt(sceCdlLOCCD *p)
Definition cdvdman.c:2168
int sceCdLayerSearchFile(sceCdlFILE *fp, const char *path, int layer)
Definition cdvdman.c:2038
int sceCdReadClock(sceCdCLOCK *clock)
Definition cdvdman.c:5821
u32 sceCdGetReadPos(void)
Definition cdi.c:45
int sceCdGetDiskType(void)
Definition cdi.c:35
int sceCdMmode(int media)
Definition cdi.c:86
int sceCdSync(int mode)
Definition cdi.c:109
int sceCdApplySCmd(u8 cmdNum, const void *inBuff, u16 inBuffSize, void *outBuff)
Definition cdvdman.c:4363
int sceCdSeek(u32 lbn)
Definition cdi.c:142
int sceCdSetTimeout(int param, int timeout)
Definition cdvdman.c:1914
int sceCdRI(u8 *buffer, u32 *result)
Definition cdvdman.c:5681
@ SCECdDETCT
@ SCECdDVDV
@ SCECdDVDVR
@ SCECdPS2DVD
@ SCECdErEOM
@ SCECdErIPI
@ SCECdErREADCF
@ SCECdErREADCFR
int sceCdApplyNCmd(u8 cmdNum, const void *inBuff, u16 inBuffSize)
Definition cdvdman.c:4645
int sceCdStandby(void)
Definition cdi.c:147
int sceCdRE(unsigned int lsn, unsigned int sectors, void *buf, sceCdRMode *mode)
Definition cdvdman.c:5363
int sceCdStop(void)
Definition cdi.c:157
int sceCdTrayReq(int param, u32 *traychk)
Definition cdi.c:162
int sceCdCtrlADout(int mode, u32 *status)
Definition cdvdman.c:5810
u16 newflags
Definition loadcore.h:36