i_main.c (35906B)
1 2 #include <ultra64.h> 3 #include <PR/ramrom.h> /* needed for argument passing into the app */ 4 #include <assert.h> 5 6 #include "i_main.h" 7 #include "doomdef.h" 8 #include "st_main.h" 9 10 // text for debug 11 #include "graph.h" 12 13 /* 14 * Symbol genererated by "makerom" to indicate the end of the code segment 15 * in virtual (and physical) memory 16 */ 17 extern char _codeSegmentEnd[]; 18 19 /* 20 * Symbols generated by "makerom" to tell us where the static segment is 21 * in ROM. 22 */ 23 24 /* 25 * Stacks for the threads as well as message queues for synchronization 26 * This stack is ridiculously large, and could also be reclaimed once 27 * the main thread is started. 28 */ 29 u64 bootStack[STACKSIZE/sizeof(u64)]; 30 31 extern u32 cfb[2][SCREEN_WD*SCREEN_HT]; // 8036A000 32 33 extern int globallump; // 800A68f8 r_local.h 34 extern int globalcm; // 800A68fC r_local.h 35 36 //"\x80\x81\x82\x83\x84\x85\x86\x87\x88\x89\x8a\x8b\x8c\x8d\x8e\x8f\x90\x91" 37 //static char sysmbols[] = {0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87, 0x88, 0x89, 0x8a, 0x8b, 0x8c, 0x8d, 0x8e, 0x8f, 0x90, 0x91}; 38 39 //---------- 40 41 #define SYS_THREAD_ID_IDLE 1 42 #define SYS_THREAD_ID_MAIN 2 43 #define SYS_THREAD_ID_TICKER 3 44 45 #define SYS_IDLE_STACKSIZE 0x2020 46 OSThread idle_thread; // 800A4A18 47 u64 idle_stack[SYS_IDLE_STACKSIZE/sizeof(u64)]; // 800979E0 48 49 #define SYS_MAIN_STACKSIZE 0xA000 50 OSThread main_thread; // 800A4BC8 51 u64 main_stack[SYS_MAIN_STACKSIZE/sizeof(u64)]; // 80099A00 52 53 #define SYS_TICKER_STACKSIZE 0x1000 54 OSThread sys_ticker_thread; // 800A4D78 55 u64 sys_ticker_stack[SYS_TICKER_STACKSIZE/sizeof(u64)]; // 800A3A00 56 57 #define SYS_MSGBUF_SIZE_PI 128 58 OSMesgQueue msgque_Pi; // 800A4FA0 59 OSMesg msgbuf_Pi[SYS_MSGBUF_SIZE_PI]; // 800A4FD0 60 61 #define SYS_FIFO_SIZE 512 62 63 #if __GNUC__ /* for GNU compiler */ 64 u64 fifo_buff[2][SYS_FIFO_SIZE] __attribute__((aligned (16))); /* buffer for RDP DL */ // 800633E0 65 u64 sys_rcp_stack[SP_DRAM_STACK_SIZE64] __attribute__((aligned (16))); /* used for matrix stack */ // 800915E0 66 #else /* for SGI compiler */ 67 u64 fifo_buff[2][SYS_FIFO_SIZE]; /* buffer for RDP DL */ // 800633E0 68 u64 sys_rcp_stack[SP_DRAM_STACK_SIZE64]; /* used for matrix stack */ // 800915E0 69 #endif 70 71 #define SYS_YIELD_SIZE OS_YIELD_DATA_SIZE 72 u64 gfx_yield_buff[SYS_YIELD_SIZE]; // 800919E0 73 74 OSTask vid_rsptask[2] = // 8005A590 75 { 76 { 77 M_GFXTASK, /* task type */ 78 NULL, /* task flags */ 79 (u64*) rspbootTextStart, /* boot ucode pointer (fill in later) */ 80 0, /* boot ucode size (fill in later) */ 81 (u64*) gspF3DEX_NoN_fifoTextStart, /* task ucode pointer (fill in later) */ 82 SP_UCODE_SIZE, /* task ucode size */ 83 (u64*) gspF3DEX_NoN_fifoDataStart, /* task ucode data pointer (fill in later) */ 84 SP_UCODE_DATA_SIZE, /* task ucode data size */ 85 &sys_rcp_stack[0], /* task dram stack pointer */ 86 SP_DRAM_STACK_SIZE8, /* task dram stack size */ 87 &fifo_buff[0][0], /* task fifo buffer start ptr */ 88 &fifo_buff[0][0]+SYS_FIFO_SIZE, /* task fifo buffer end ptr */ 89 NULL, /* task data pointer (fill in later) */ 90 0, /* task data size (fill in later) */ 91 &gfx_yield_buff[0], /* task yield buffer ptr (not used here) */ 92 SYS_YIELD_SIZE /* task yield buffer size (not used here) */ 93 }, 94 { 95 M_GFXTASK, /* task type */ 96 NULL, /* task flags */ 97 (u64*) rspbootTextStart, /* boot ucode pointer (fill in later) */ 98 0, /* boot ucode size (fill in later) */ 99 (u64*) gspF3DEX_NoN_fifoTextStart, /* task ucode pointer (fill in later) */ 100 SP_UCODE_SIZE, /* task ucode size */ 101 (u64*) gspF3DEX_NoN_fifoDataStart, /* task ucode data pointer (fill in later) */ 102 SP_UCODE_DATA_SIZE, /* task ucode data size */ 103 &sys_rcp_stack[0], /* task dram stack pointer */ 104 SP_DRAM_STACK_SIZE8, /* task dram stack size */ 105 &fifo_buff[1][0], /* task fifo buffer start ptr */ 106 &fifo_buff[1][0]+SYS_FIFO_SIZE, /* task fifo buffer end ptr */ 107 NULL, /* task data pointer (fill in later) */ 108 0, /* task data size (fill in later) */ 109 &gfx_yield_buff[0], /* task yield buffer ptr (not used here) */ 110 SYS_YIELD_SIZE /* task yield buffer size (not used here) */ 111 } 112 }; 113 114 Vp vid_viewport = // 8005A610 115 { 116 SCREEN_WD*2, SCREEN_HT*2, G_MAXZ, 0, /* scale */ 117 SCREEN_WD*2, SCREEN_HT*2, 0, 0, /* translate */ 118 }; 119 120 OSMesgQueue romcopy_msgque; // 800A4F70 121 OSMesg romcopy_msgbuf; // 800A51D0 122 123 OSMesgQueue sys_msgque_joy; // 800A4F88 124 OSMesg sys_msg_joy; // 800A51D4 125 126 #define SYS_MSGBUF_SIZE_VID 16 127 OSMesgQueue sys_msgque_vbi; // 800A4FB8 128 OSMesg sys_msgbuf_vbi[SYS_MSGBUF_SIZE_VID]; // 800A51E0 129 130 #define SYS_MSGBUF_SIZE_VID2 2 131 OSMesgQueue sys_msgque_vbi2; // 800A4F28 132 OSMesg sys_msgbuf_vbi2[SYS_MSGBUF_SIZE_VID2]; // 800A51D8 133 134 OSMesgQueue sys_msgque_vbi3; // 800A4F40 135 OSMesg sys_msgbuf_vbi3[SYS_MSGBUF_SIZE_VID2]; // 800A5220 136 137 OSMesgQueue sys_msgque_vbi4; // 800A4F58 138 OSMesg sys_msgbuf_vbi4[SYS_MSGBUF_SIZE_VID2]; // 800A5228 139 140 OSContStatus gamepad_status[MAXCONTROLLERS]; // 800a5230 141 OSContPad *gamepad_data; // 800A5240 142 143 OSTask *vid_task; // 800A5244 144 u32 vid_side; // 800A5248 145 146 u32 video_hStart; // 800A524c 147 u32 video_vStart1; // 800A5250 148 u32 video_vStart2; // 800A5254 149 150 u32 GfxIndex; // 800A5258 151 u32 VtxIndex; // 800A525C 152 153 u8 gamepad_bit_pattern; // 800A5260 // one bit for each controller 154 155 // Controller Pak 156 OSPfs ControllerPak; // 800A5270 157 OSPfsState FileState[16]; // 800A52D8 158 s32 File_Num; // 800A54D8 159 s32 Pak_Size; // 800A54DC 160 u8 *Pak_Data; // 800A54E0 161 s32 Pak_Memory; // 800A54E4 162 163 char Pak_Table[256] = // 8005A620 164 { 165 '\0',// 0 166 ' ', ' ', ' ', ' ', ' ',// 1 167 ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ',// 6 168 '0', '1', '2', '3', '4', '5', '6', '7', '8', '9',// 16 169 'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j',// 26 170 'k', 'l', 'm', 'n', 'o', 'p', 'q', 'r', 's', 't',// 36 171 'u', 'v', 'w', 'x', 'y', 'z', '!', '"', '#','\'',// 46 172 '*', '+', ',', '-', '.', '/', ':', '=', '?', '@',// 56 173 ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ',// 66 174 ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ',// 76 175 ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ',// 86 176 ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ',// 96 177 ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ',// 106 178 ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ',// 116 179 ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ',// 126 180 ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ',// 136 181 ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ',// 146 182 ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ',// 156 183 ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ',// 166 184 ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ',// 176 185 ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ',// 186 186 ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ',// 196 187 ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ',// 206 188 ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ',// 216 189 ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ',// 226 190 ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ',// 236 191 ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ' // 246 192 }; 193 194 char Game_Name[16] = // 8005A790 195 { 196 0x1D, 0x28, 0x28, 0x26, 0x0F, 0x16, 0x14, 0x00, // (doom 64) byte index from Pak_Table 197 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 198 }; 199 200 boolean disabledrawing = false; // 8005A720 201 202 s32 vsync = 0; // 8005A724 203 s32 drawsync2 = 0; // 8005A728 204 s32 drawsync1 = 0; // 8005A72C 205 u32 NextFrameIdx = 0; // 8005A730 206 207 s32 ControllerPakStatus = 1; // 8005A738 208 s32 gamepad_system_busy = 0; // 8005A73C 209 s32 FilesUsed = -1; // 8005A740 210 u32 SystemTickerStatus = 0; // 8005a744 211 212 Gfx Gfx_base[2][MAX_GFX]; // 800653E0 213 Mtx Mtx_base[2][MAX_MTX]; // 800793E0 214 Vtx Vtx_base[2][MAX_VTX]; // 800795E0 215 216 Gfx *GFX1; // 800A4A00 217 Gfx *GFX2; // 800A4A04 218 219 Vtx *VTX1; // 800A4A08 220 Vtx *VTX2; // 800A4A0C 221 222 Mtx *MTX1; // 800A4A10 223 Mtx *MTX2; // 800A4A14 224 225 Gfx *GfxBlocks[8] = {0,0,0,0,0,0,0,0}; // 8005A748 226 Vtx *VtxBlocks[8] = {0,0,0,0,0,0,0,0}; // 8005A768 227 228 extern OSTask * wess_work(void); 229 230 void I_Start(void) // 80005620 231 { 232 /* Re-initialize U64 operating system... */ 233 osInitialize(); 234 235 /* Create and start idle thread... */ 236 osCreateThread(&idle_thread, SYS_THREAD_ID_IDLE, I_IdleGameThread, (void *)0, 237 idle_stack + SYS_IDLE_STACKSIZE/sizeof(u64), 10); 238 osStartThread(&idle_thread); 239 } 240 241 void I_IdleGameThread(void *arg) // 8000567C 242 { 243 /* Create and start the Pi manager... */ 244 osCreatePiManager( (OSPri)OS_PRIORITY_PIMGR, &msgque_Pi, msgbuf_Pi, 245 SYS_MSGBUF_SIZE_PI ); 246 247 /* Create main thread... */ 248 osCreateThread(&main_thread, SYS_THREAD_ID_MAIN, I_Main, (void *)0, 249 main_stack + SYS_MAIN_STACKSIZE/sizeof(u64), 10); 250 osStartThread(&main_thread); 251 252 osSetThreadPri(&idle_thread, (OSPri)OS_PRIORITY_IDLE); 253 254 /* Idle loop... */ 255 do { 256 osYieldThread(); 257 } while(TRUE); 258 } 259 260 void I_Main(void *arg) // 80005710 261 { 262 D_DoomMain(); 263 } 264 265 void I_SystemTicker(void *arg) // 80005730 266 { 267 int vbi_msg; 268 int vidside; 269 int side, stat, ret; 270 int current_fbuf, next_fbuf; 271 OSTask *wess; 272 OSTask *rspTask; 273 OSTask *rspTaskPrev; 274 275 //char str[64]; 276 277 rspTask = NULL; 278 rspTaskPrev = NULL; 279 side = 1; 280 281 while(true) 282 { 283 osRecvMesg(&sys_msgque_vbi, (OSMesg *)&vbi_msg, OS_MESG_BLOCK); 284 285 //sprintf(str, "SystemTickerStatus %d",SystemTickerStatus); 286 //printstr(WHITE, 0, 13, str); 287 //sprintf(str, "vbi_msg %d",vbi_msg); 288 //printstr(WHITE, 0, 14, str); 289 //sprintf(str, "vidside %d",vidside); 290 //printstr(WHITE, 0, 15, str); 291 292 switch (vbi_msg) 293 { 294 case VID_MSG_RSP: // end of signal processing 295 { 296 //sprintf(str, "VID_MSG_RSP"); 297 //printstr(WHITE, 0, 28, str); 298 299 if(rspTask->t.type == M_AUDTASK) 300 { 301 SystemTickerStatus &= ~32; 302 303 if (SystemTickerStatus & 4)//OS_SC_YIELDED 304 { 305 SystemTickerStatus &= ~4; 306 SystemTickerStatus |= 1; 307 308 rspTask = rspTaskPrev; 309 osWritebackDCacheAll(); 310 osSpTaskLoad(rspTask); 311 osSpTaskStartGo(rspTask); 312 } 313 else 314 { 315 if ((SystemTickerStatus & 24) == 0) 316 { 317 ret = osRecvMesg(&sys_msgque_vbi3, (OSMesg *)&vbi_msg, OS_MESG_NOBLOCK); 318 rspTask = (OSTask*)vbi_msg; 319 320 if(ret != -1) 321 { 322 if(rspTask == vid_rsptask) 323 vidside = 0; 324 else 325 vidside = 1; 326 327 SystemTickerStatus |= 1; 328 329 osWritebackDCacheAll(); 330 osSpTaskLoad(rspTask); 331 osSpTaskStartGo(rspTask); 332 } 333 } 334 } 335 } 336 else 337 { 338 SystemTickerStatus &= ~1; 339 340 if(SystemTickerStatus & 2)//OS_SC_YIELD 341 { 342 SystemTickerStatus &= ~2; 343 344 if (osSpTaskYielded(rspTask)) 345 { 346 rspTaskPrev = rspTask; 347 348 SystemTickerStatus |= 4;//OS_SC_YIELDED 349 350 osRecvMesg(&sys_msgque_vbi4, (OSMesg *)&vbi_msg, OS_MESG_NOBLOCK); 351 rspTask = (OSTask*)vbi_msg; 352 353 SystemTickerStatus |= 32; 354 355 osWritebackDCacheAll(); 356 osSpTaskLoad(rspTask); 357 osSpTaskStartGo(rspTask); 358 } 359 } 360 else 361 { 362 if ((SystemTickerStatus & 16) == 0) 363 SystemTickerStatus |= 8; 364 365 ret = osRecvMesg(&sys_msgque_vbi4, (OSMesg *)&vbi_msg, OS_MESG_NOBLOCK); 366 rspTask = (OSTask*)vbi_msg; 367 368 if(ret!= -1) 369 { 370 SystemTickerStatus |= 32; 371 372 osWritebackDCacheAll(); 373 osSpTaskLoad(rspTask); 374 osSpTaskStartGo(rspTask); 375 } 376 } 377 } 378 } 379 break; 380 381 case VID_MSG_RDP: // end of display processing 382 { 383 //sprintf(str, "VID_MSG_RDP"); 384 //printstr(WHITE, 0, 28, str); 385 386 SystemTickerStatus &= ~8; 387 SystemTickerStatus |= 16; 388 389 osViSwapBuffer(cfb[vidside]); 390 } 391 break; 392 393 case VID_MSG_PRENMI: 394 { 395 //sprintf(str, "VID_MSG_PRENMI"); 396 //printstr(WHITE, 0, 28, str); 397 disabledrawing = true; 398 S_StopAll(); 399 osViBlack(TRUE); 400 I_MoveDisplay(0,0); 401 } 402 break; 403 404 case VID_MSG_VBI: 405 { 406 //sprintf(str, "VID_MSG_VBI || vsync(%d) || side(%d)", vsync, side); 407 //printstr(WHITE, 0, 28, str); 408 409 vsync += 1; 410 411 if (sys_msgque_vbi4.validCount) 412 { 413 if (SystemTickerStatus & 1) 414 { 415 SystemTickerStatus |= 2; // GFX_YIELDED 416 osSpTaskYield(); 417 } 418 else 419 { 420 if ((SystemTickerStatus & 32) == 0) 421 { 422 osRecvMesg(&sys_msgque_vbi4, (OSMesg *)&vbi_msg, OS_MESG_NOBLOCK); 423 rspTask = (OSTask*)vbi_msg; 424 425 SystemTickerStatus |= 32; 426 427 osWritebackDCacheAll(); 428 osSpTaskLoad(rspTask); 429 osSpTaskStartGo(rspTask); 430 } 431 } 432 } 433 434 if (side & 1) 435 { 436 if (gamepad_system_busy) 437 { 438 osContGetReadData(gamepad_data); 439 gamepad_system_busy = 0; 440 } 441 442 // next audio function task 443 wess = wess_work(); 444 if (wess) 445 osSendMesg(&sys_msgque_vbi4,(OSMesg) wess, OS_MESG_NOBLOCK); 446 } 447 side++; 448 449 if (SystemTickerStatus & 16) 450 { 451 if ((u32)(vsync - drawsync2) < 2) continue; 452 453 current_fbuf = (int)osViGetCurrentFramebuffer(); 454 next_fbuf = (int)osViGetNextFramebuffer(); 455 456 if (next_fbuf != current_fbuf) continue; 457 458 SystemTickerStatus &= ~16; 459 460 if (demoplayback || demorecording) 461 { 462 vsync = drawsync2 + 2; 463 } 464 465 //sprintf(str, "vsync %d | side %d",vsync, side); 466 //printstr(WHITE, 0, 29, str); 467 468 drawsync1 = vsync - drawsync2; 469 drawsync2 = vsync; 470 471 if ((ControllerPakStatus != 0) && (gamepad_system_busy == 0)) 472 { 473 osContStartReadData(&sys_msgque_joy); 474 gamepad_system_busy = 1; 475 } 476 477 osSendMesg(&sys_msgque_vbi2, (OSMesg)VID_MSG_KICKSTART, OS_MESG_NOBLOCK); 478 } 479 480 if(SystemTickerStatus == 0) 481 { 482 ret = osRecvMesg(&sys_msgque_vbi3, (OSMesg *)&vbi_msg, OS_MESG_NOBLOCK); 483 rspTask = (OSTask*)vbi_msg; 484 485 //sprintf(str, "ret %d", ret); 486 //printstr(WHITE, 0, 17, str); 487 488 if(ret != -1) 489 { 490 //sprintf(str, "rspTask->t.type %d",rspTask->t.type); 491 //printstr(WHITE, 0, 14, str); 492 //sprintf(str, "rspTask->t.type %x",(u64*)rspTask->t.ucode); 493 //printstr(WHITE, 0, 15, str); 494 495 if(rspTask == vid_rsptask) 496 vidside = 0; 497 else 498 vidside = 1; 499 500 SystemTickerStatus |= 1; 501 502 osWritebackDCacheAll(); 503 osSpTaskLoad(rspTask); 504 osSpTaskStartGo(rspTask); 505 } 506 } 507 } 508 break; 509 } 510 } 511 } 512 513 extern void S_Init(void); 514 515 void I_Init(void) // 80005C50 516 { 517 OSViMode *ViMode; 518 519 vid_rsptask[0].t.ucode_boot_size = (int)rspbootTextEnd - (int)rspbootTextStart; // set ucode size (waste but who cares) 520 vid_rsptask[1].t.ucode_boot_size = (int)rspbootTextEnd - (int)rspbootTextStart; // set ucode size (waste but who cares) 521 522 osCreateMesgQueue( &romcopy_msgque, &romcopy_msgbuf, 1 ); 523 524 osCreateMesgQueue( &sys_msgque_vbi, sys_msgbuf_vbi, SYS_MSGBUF_SIZE_VID ); 525 526 osCreateMesgQueue(&sys_msgque_vbi2, sys_msgbuf_vbi2, SYS_MSGBUF_SIZE_VID2);//&sys_msgque_jam, sys_msgbuf_jam 527 osCreateMesgQueue(&sys_msgque_vbi3, sys_msgbuf_vbi3, SYS_MSGBUF_SIZE_VID2);//&sys_msgque_ser, sys_msgbuf_ser 528 osCreateMesgQueue(&sys_msgque_vbi4, sys_msgbuf_vbi4, SYS_MSGBUF_SIZE_VID2);//&sys_msgque_tmr, sys_msgbuf_tmr 529 530 if(osTvType == OS_TV_PAL) 531 { 532 ViMode = &osViModeTable[OS_VI_PAL_LPN2]; 533 } 534 else if(osTvType == OS_TV_NTSC) 535 { 536 ViMode = &osViModeTable[OS_VI_NTSC_LPN2]; 537 } 538 else if(osTvType == OS_TV_MPAL) 539 { 540 ViMode = &osViModeTable[OS_VI_MPAL_LPN2]; 541 } 542 543 video_hStart = ViMode->comRegs.hStart; 544 video_vStart1 = ViMode->fldRegs[0].vStart; 545 video_vStart2 = ViMode->fldRegs[1].vStart; 546 547 // Create and start the Vi manager and init the video mode... 548 549 osCreateViManager( OS_PRIORITY_VIMGR ); 550 osViSetMode(ViMode); 551 osViBlack(TRUE); 552 553 osViSetSpecialFeatures(OS_VI_GAMMA_OFF|OS_VI_GAMMA_DITHER_OFF|OS_VI_DIVOT_OFF|OS_VI_DITHER_FILTER_OFF); 554 555 osViSetXScale(1.0); 556 osViSetYScale(1.0); 557 558 D_memset(cfb, 0, ((SCREEN_WD*SCREEN_HT)*sizeof(u32))*2); 559 osViSwapBuffer(cfb); 560 561 if (osViGetCurrentFramebuffer() != cfb) { 562 do { 563 } while (osViGetCurrentFramebuffer() != cfb); 564 } 565 566 osViBlack(FALSE); 567 568 osSetEventMesg( OS_EVENT_SP, &sys_msgque_vbi, (OSMesg)VID_MSG_RSP ); 569 osSetEventMesg( OS_EVENT_DP, &sys_msgque_vbi, (OSMesg)VID_MSG_RDP ); 570 osSetEventMesg( OS_EVENT_PRENMI, &sys_msgque_vbi, (OSMesg)VID_MSG_PRENMI ); 571 572 osViSetEvent( &sys_msgque_vbi, (OSMesg)VID_MSG_VBI, 1 ); // last parm: 2 indicates 30 FPS (1=60) 573 574 vid_side = 1; 575 576 /* Serial/Joy queue */ 577 578 osCreateMesgQueue(&sys_msgque_joy, &sys_msg_joy, 1); 579 osSetEventMesg(OS_EVENT_SI, &sys_msgque_joy, &sys_msg_joy); 580 581 osContInit(&sys_msgque_joy, &gamepad_bit_pattern, gamepad_status); 582 583 gamepad_data = (OSContPad *)idle_stack; 584 585 if ((gamepad_bit_pattern & 1) != 0) 586 { 587 osContStartReadData(&sys_msgque_joy); 588 osRecvMesg(&sys_msgque_joy, NULL, OS_MESG_BLOCK); 589 osContGetReadData(gamepad_data); 590 } 591 592 S_Init(); 593 594 /* Create and start ticker thread... */ 595 osCreateThread(&sys_ticker_thread, SYS_THREAD_ID_TICKER, I_SystemTicker, (void *)0, 596 sys_ticker_stack + SYS_TICKER_STACKSIZE/sizeof(u64), 11); 597 osStartThread(&sys_ticker_thread); 598 599 osJamMesg(&sys_msgque_vbi2, (OSMesg)VID_MSG_KICKSTART, OS_MESG_NOBLOCK); 600 } 601 602 #include "stdarg.h" 603 604 void I_Error(char *error, ...) // 80005F30 605 { 606 char buffer[256]; 607 va_list args; 608 va_start (args, error); 609 D_vsprintf (buffer, error, args); 610 va_end (args); 611 612 while (true) 613 { 614 I_ClearFrame(); 615 616 gDPPipeSync(GFX1++); 617 gDPSetCycleType(GFX1++, G_CYC_FILL); 618 gDPSetRenderMode(GFX1++,G_RM_NOOP,G_RM_NOOP2); 619 gDPSetColorImage(GFX1++, G_IM_FMT_RGBA, G_IM_SIZ_32b, SCREEN_WD, OS_K0_TO_PHYSICAL(cfb[vid_side])); 620 gDPSetFillColor(GFX1++, GPACK_RGBA5551(0,0,0,0) << 16 | GPACK_RGBA5551(0,0,0,0)) ; 621 gDPFillRectangle(GFX1++, 0, 0, SCREEN_WD-1, SCREEN_HT-1); 622 623 ST_Message(err_text_x, err_text_y, buffer, 0xffffffff); 624 I_DrawFrame(); 625 } 626 } 627 628 typedef struct 629 { 630 int pad_data; 631 } pad_t; 632 633 int I_GetControllerData(void) // 800060D0 634 { 635 return ((pad_t*)gamepad_data)->pad_data; 636 } 637 638 void I_CheckGFX(void) // 800060E8 639 { 640 memblock_t *block; 641 642 Gfx **Gfx_Blocks; 643 Vtx **Vtx_Blocks; 644 645 int i, index; 646 int block_idx; 647 648 index = (int)((int)GFX1 - (int)GFX2) / sizeof(Gfx); 649 650 if (index > MAX_GFX) 651 I_Error("I_CheckGFX: GFX Overflow by %d\n",index); 652 653 if ((index < (MAX_GFX-1024)) == 0) 654 { 655 Gfx_Blocks = GfxBlocks; 656 block_idx = -1; 657 658 for(i = 0; i < 8; i++) 659 { 660 block = (memblock_t *)((byte *)*Gfx_Blocks - sizeof(memblock_t)); 661 662 if (*Gfx_Blocks) 663 { 664 if(((u32)block->lockframe < NextFrameIdx - 1) == 0) 665 { 666 Gfx_Blocks++; 667 continue; 668 } 669 670 block->lockframe = NextFrameIdx; 671 GFX2 = (Gfx *)*Gfx_Blocks; 672 goto move_gfx; 673 } 674 675 block_idx = i; 676 } 677 678 if (block_idx < 0) 679 I_Error("I_CheckGFX: GFX Cache overflow"); 680 681 GFX2 = (Gfx *)Z_Malloc(MAX_GFX * sizeof(Gfx), PU_CACHE, &GfxBlocks[block_idx]); 682 683 move_gfx: 684 gSPBranchList(GFX1,GFX2); 685 GFX1 = GFX2; 686 GfxIndex += index; 687 } 688 689 index = (int)((int)VTX1 - (int)VTX2) / sizeof(Vtx); 690 691 if (index > MAX_VTX) 692 I_Error("I_CheckVTX: VTX Overflow by %d\n",index); 693 694 if ((index < (MAX_VTX-615)) == 0) 695 { 696 Vtx_Blocks = VtxBlocks; 697 block_idx = -1; 698 699 for(i = 0; i < 8; i++) 700 { 701 block = (memblock_t *)((byte *)*Vtx_Blocks - sizeof(memblock_t)); 702 703 if (*Vtx_Blocks) 704 { 705 if(((u32)block->lockframe < NextFrameIdx - 1) == 0) 706 { 707 Vtx_Blocks++; 708 continue; 709 } 710 711 block->lockframe = NextFrameIdx; 712 VTX2 = (Vtx *)*Vtx_Blocks; 713 goto move_vtx; 714 } 715 716 block_idx = i; 717 } 718 719 if (block_idx < 0) 720 I_Error("I_CheckGFX: VTX Cache overflow"); 721 722 VTX2 = (Vtx *)Z_Malloc(MAX_VTX * sizeof(Vtx), PU_CACHE, &VtxBlocks[block_idx]); 723 724 move_vtx: 725 VTX1 = VTX2; 726 VtxIndex += index; 727 } 728 } 729 730 void I_ClearFrame(void) // 8000637C 731 { 732 NextFrameIdx += 1; 733 734 GFX1 = Gfx_base[vid_side]; 735 GFX2 = GFX1; 736 GfxIndex = 0; 737 738 VTX1 = Vtx_base[vid_side]; 739 VTX2 = VTX1; 740 VtxIndex = 0; 741 742 MTX1 = Mtx_base[vid_side]; 743 744 vid_task = &vid_rsptask[vid_side]; 745 746 vid_task->t.ucode = (u64 *) gspF3DEX_NoN_fifoTextStart; 747 vid_task->t.ucode_data = (u64 *) gspF3DEX_NoN_fifoDataStart; 748 749 gMoveWd(GFX1++, G_MW_SEGMENT, G_MWO_SEGMENT_0, 0); 750 751 gDPSetColorImage(GFX1++, G_IM_FMT_RGBA, G_IM_SIZ_32b, SCREEN_WD, OS_K0_TO_PHYSICAL(cfb[vid_side])); 752 gDPSetScissor(GFX1++, G_SC_NON_INTERLACE, 0, 0, SCREEN_WD, SCREEN_HT); 753 754 // [GEC] New Cheat Codes 755 if (players[0].cheats & CF_FILTER) { 756 gDPSetTextureFilter(GFX1++, G_TF_POINT); // <- Nearest texture 757 } 758 else { 759 gDPSetTextureFilter(GFX1++, G_TF_BILERP); // <- Bilinear texture 760 } 761 762 gSPViewport(GFX1++, &vid_viewport); 763 764 gSPClearGeometryMode(GFX1++, -1); 765 gSPSetGeometryMode(GFX1++, G_SHADE|G_SHADING_SMOOTH|G_FOG ); 766 767 globallump = -1; 768 globalcm = 0; 769 } 770 771 void I_DrawFrame(void) // 80006570 772 { 773 int index; 774 775 gDPFullSync(GFX1++); 776 gSPEndDisplayList(GFX1++); 777 778 index = (int)((int)GFX1 - (int)GFX2) / sizeof(Gfx); 779 if (index > MAX_GFX) 780 I_Error("I_DrawFrame: GFX Overflow by %d\n\n",index); 781 782 index = (int)((int)VTX1 - (int)VTX2) / sizeof(Vtx); 783 if (index > MAX_VTX) 784 I_Error("I_DrawFrame: VTX Overflow by %d\n",index); 785 786 vid_task->t.data_ptr = (u64 *) Gfx_base[vid_side]; 787 vid_task->t.data_size = (u32)((((int)((int)GFX1 - (int)GFX2) / sizeof(Gfx)) + GfxIndex) * sizeof(Gfx)); 788 789 osSendMesg(&sys_msgque_vbi3,(OSMesg) vid_task, OS_MESG_NOBLOCK); 790 osRecvMesg(&sys_msgque_vbi2, NULL, OS_MESG_BLOCK);//retraceMessageQ 791 vid_side ^= 1; 792 } 793 794 void I_GetScreenGrab(void) // 800066C0 795 { 796 if ((SystemTickerStatus & ~32) || (sys_msgque_vbi3.validCount != 0)) { 797 osRecvMesg(&sys_msgque_vbi2, (OSMesg *)0, OS_MESG_BLOCK); 798 osJamMesg(&sys_msgque_vbi2, (OSMesg)VID_MSG_KICKSTART, OS_MESG_NOBLOCK); 799 } 800 } 801 802 long LongSwap(long dat) // 80006724 803 { 804 return (u32)dat >> 0x18 | dat >> 8 & 0xff00U | (dat & 0xff00U) << 8 | dat << 0x18; 805 } 806 807 short LittleShort(short dat) // 80006750 808 { 809 return ((((dat << 8) | (dat >> 8 & 0xff)) << 16) >> 16); 810 } 811 812 short BigShort(short dat) // 80006770 813 { 814 return ((dat << 8) | (dat >> 8 & 0xff)) & 0xffff; 815 } 816 817 void I_MoveDisplay(int x,int y) // 80006790 818 { 819 int ViMode; 820 821 ViMode = osViGetCurrentMode(); 822 823 osViModeTable[ViMode].comRegs.hStart = 824 (int)(((int)video_hStart >> 0x10 & 65535) + x) % 65535 << 0x10 | 825 (int)((video_hStart & 65535) + x) % 65535; 826 827 osViModeTable[ViMode].fldRegs[0].vStart = 828 (int)(((int)video_vStart1 >> 0x10 & 65535) + y) % 65535 << 0x10 | 829 (int)((video_vStart1 & 65535) + y) % 65535; 830 831 osViModeTable[ViMode].fldRegs[1].vStart = 832 (int)(((int)video_vStart2 >> 0x10 & 65535) + y) % 65535 << 0x10 | 833 (int)((video_vStart2 & 65535) + y) % 65535; 834 } 835 836 void I_WIPE_MeltScreen(void) // 80006964 837 { 838 u32 *fb; 839 int y1; 840 int tpos; 841 int yscroll; 842 int height; 843 844 fb = Z_Malloc((SCREEN_WD*SCREEN_HT)*sizeof(u32), PU_STATIC, NULL); 845 846 I_GetScreenGrab(); 847 D_memcpy(&cfb[vid_side][0], &cfb[vid_side ^ 1][0], (SCREEN_WD*SCREEN_HT)*sizeof(u32)); 848 849 yscroll = 1; 850 while( true ) 851 { 852 y1 = 0; 853 D_memcpy(fb, &cfb[vid_side ^ 1][0], (SCREEN_WD*SCREEN_HT)*sizeof(u32)); 854 855 I_ClearFrame(); 856 857 gDPSetCycleType(GFX1++, G_CYC_1CYCLE); 858 gDPSetTextureLUT(GFX1++, G_TT_NONE); 859 gDPSetTexturePersp(GFX1++, G_TP_NONE); 860 gDPSetAlphaCompare(GFX1++, G_AC_THRESHOLD); 861 gDPSetBlendColor(GFX1++, 0, 0, 0, 0); 862 gDPSetCombineMode(GFX1++, G_CC_D64COMB19, G_CC_D64COMB19); 863 gDPSetRenderMode(GFX1++, G_RM_XLU_SURF, G_RM_XLU_SURF2); 864 gDPSetPrimColor(GFX1++, 0, 0, 15, 0, 0, 22); // 0x0f000016 865 866 height = SCREEN_HT - (yscroll >> 2); 867 tpos = 0; 868 if (height > 0) 869 { 870 do 871 { 872 gDPSetTextureImage(GFX1++, G_IM_FMT_RGBA, G_IM_SIZ_32b , SCREEN_WD, fb); 873 gDPSetTile(GFX1++, G_IM_FMT_RGBA, G_IM_SIZ_32b, 874 (SCREEN_WD >> 2), 0, G_TX_LOADTILE, 0, 0, 0, 0, 0, 0, 0); 875 876 gDPLoadSync(GFX1++); 877 gDPLoadTile(GFX1++, G_TX_LOADTILE, 878 (0 << 2), (tpos << 2), 879 ((SCREEN_WD-1) << 2), (((tpos+3)-1) << 2)); 880 881 gDPPipeSync(GFX1++); 882 gDPSetTile(GFX1++, G_IM_FMT_RGBA, G_IM_SIZ_32b, 883 (SCREEN_WD >> 2), 0, G_TX_RENDERTILE, 0, 0, 0, 0, 0, 0, 0); 884 885 gDPSetTileSize(GFX1++, G_TX_RENDERTILE, 886 (0 << 2), (tpos << 2), 887 ((SCREEN_WD-1) << 2), (((tpos+3)-1) << 2)); 888 889 gSPTextureRectangle(GFX1++, 890 (0 << 2), (y1 << 2) + yscroll, 891 (SCREEN_WD << 2), ((y1 + 3) << 2) + yscroll, 892 G_TX_RENDERTILE, 893 (0 << 5), (tpos << 5), 894 (1 << 10), (1 << 10)); 895 896 y1 += 2; 897 tpos += 2; 898 } while (y1 < height); 899 } 900 901 yscroll += 2; 902 if (yscroll >= 160) break; 903 I_DrawFrame(); 904 } 905 906 Z_Free(fb); 907 I_WIPE_FadeOutScreen(); 908 } 909 910 void I_WIPE_FadeOutScreen(void) // 80006D34 911 { 912 u32 *fb; 913 int y1, tpos, outcnt; 914 915 fb = Z_Malloc((SCREEN_WD*SCREEN_HT)*sizeof(u32), PU_STATIC, NULL); 916 917 I_GetScreenGrab(); 918 D_memcpy(fb, &cfb[vid_side ^ 1][0], (SCREEN_WD*SCREEN_HT)*sizeof(u32)); 919 920 outcnt = 248; 921 do 922 { 923 I_ClearFrame(); 924 925 gDPSetCycleType(GFX1++, G_CYC_1CYCLE); 926 gDPSetTextureLUT(GFX1++, G_TT_NONE); 927 gDPSetTexturePersp(GFX1++, G_TP_NONE); 928 gDPSetAlphaCompare(GFX1++, G_AC_NONE); 929 gDPSetCombineMode(GFX1++, G_CC_D64COMB06, G_CC_D64COMB06); 930 gDPSetRenderMode(GFX1++,G_RM_OPA_SURF,G_RM_OPA_SURF2); 931 gDPSetPrimColor(GFX1++, 0, 0, outcnt, outcnt, outcnt, 0); 932 933 tpos = 0; 934 y1 = 0; 935 do 936 { 937 gDPSetTextureImage(GFX1++, G_IM_FMT_RGBA, G_IM_SIZ_32b , SCREEN_WD, fb); 938 gDPSetTile(GFX1++, G_IM_FMT_RGBA, G_IM_SIZ_32b, 939 (SCREEN_WD >> 2), 0, G_TX_LOADTILE, 0, 0, 0, 0, 0, 0, 0); 940 941 gDPLoadSync(GFX1++); 942 gDPLoadTile(GFX1++, G_TX_LOADTILE, 943 (0 << 2), (tpos << 2), 944 ((SCREEN_WD-1) << 2), (((tpos+3)-1) << 2)); 945 946 gDPPipeSync(GFX1++); 947 gDPSetTile(GFX1++, G_IM_FMT_RGBA, G_IM_SIZ_32b, 948 (SCREEN_WD >> 2), 0, G_TX_RENDERTILE, 0, 0, 0, 0, 0, 0, 0); 949 950 gDPSetTileSize(GFX1++, G_TX_RENDERTILE, 951 (0 << 2), (tpos << 2), 952 ((SCREEN_WD-1) << 2), (((tpos+3)-1) << 2)); 953 954 gSPTextureRectangle(GFX1++, 955 (0 << 2), (y1 << 2), 956 (SCREEN_WD << 2), ((y1+3) << 2), 957 G_TX_RENDERTILE, 958 (0 << 5), (tpos << 5), 959 (1 << 10), (1 << 10)); 960 961 tpos += 3; 962 y1 += 3; 963 } while (y1 != SCREEN_HT); 964 965 I_DrawFrame(); 966 outcnt -= 8; 967 } while (outcnt >= 0); 968 969 I_GetScreenGrab(); 970 Z_Free(fb); 971 } 972 973 974 int I_CheckControllerPak(void) // 800070B0 975 { 976 int ret, file; 977 OSPfsState *fState; 978 s32 MaxFiles [2]; 979 u8 validpaks; 980 981 ControllerPakStatus = 0; 982 983 if (gamepad_system_busy != 0) 984 { 985 do { 986 osYieldThread(); 987 } while (gamepad_system_busy != 0); 988 } 989 990 FilesUsed = -1; 991 ret = PFS_ERR_NOPACK; 992 993 osPfsIsPlug(&sys_msgque_joy, &validpaks); 994 995 /* does the current controller have a memory pak? */ 996 if (validpaks & 1) 997 { 998 ret = osPfsInit(&sys_msgque_joy, &ControllerPak, NULL); 999 1000 if ((ret != PFS_ERR_NOPACK) && 1001 (ret != PFS_ERR_ID_FATAL) && 1002 (ret != PFS_ERR_DEVICE) && 1003 (ret != PFS_ERR_CONTRFAIL)) 1004 { 1005 ret = osPfsNumFiles(&ControllerPak, MaxFiles, &FilesUsed); 1006 1007 if (ret == PFS_ERR_INCONSISTENT) 1008 ret = osPfsChecker(&ControllerPak); 1009 1010 if (ret == 0) 1011 { 1012 Pak_Memory = 123; 1013 fState = FileState; 1014 file = 0; 1015 do 1016 { 1017 ret = osPfsFileState(&ControllerPak, file, fState); 1018 file += 1; 1019 1020 if (ret != 0) 1021 fState->file_size = 0; 1022 1023 Pak_Memory -= (fState->file_size >> 8); 1024 fState += 1; 1025 } while (file != 16); 1026 ret = 0; 1027 } 1028 } 1029 } 1030 1031 ControllerPakStatus = 1; 1032 1033 return ret; 1034 } 1035 1036 int I_DeletePakFile(int filenumb) // 80007224 1037 { 1038 int ret; 1039 OSPfsState *fState; 1040 1041 ControllerPakStatus = 0; 1042 1043 if (gamepad_system_busy != 0) 1044 { 1045 do { 1046 osYieldThread(); 1047 } while (gamepad_system_busy != 0); 1048 } 1049 1050 fState = &FileState[filenumb]; 1051 1052 if (fState->file_size == 0) { 1053 ret = 0; 1054 } 1055 else 1056 { 1057 ret = osPfsDeleteFile(&ControllerPak, 1058 FileState[filenumb].company_code, 1059 FileState[filenumb].game_code, 1060 FileState[filenumb].game_name, 1061 FileState[filenumb].ext_name); 1062 1063 if (ret == PFS_ERR_INCONSISTENT) 1064 ret = osPfsChecker(&ControllerPak); 1065 1066 if (ret == 0) 1067 { 1068 Pak_Memory += (fState->file_size >> 8); 1069 fState->file_size = 0; 1070 } 1071 } 1072 1073 ControllerPakStatus = 1; 1074 1075 return ret; 1076 } 1077 1078 int I_SavePakFile(int filenumb, int flag, byte *data, int size) // 80007308 1079 { 1080 int ret; 1081 1082 ControllerPakStatus = 0; 1083 1084 if (gamepad_system_busy != 0) 1085 { 1086 do { 1087 osYieldThread(); 1088 } while (gamepad_system_busy != 0); 1089 } 1090 1091 ret = osPfsReadWriteFile(&ControllerPak, filenumb, (u8)flag, 0, size, (u8*)data); 1092 1093 if (ret == PFS_ERR_INCONSISTENT) 1094 ret = osPfsChecker(&ControllerPak); 1095 1096 ControllerPakStatus = 1; 1097 1098 return ret; 1099 } 1100 1101 #define COMPANY_CODE 0x3544 // 5D 1102 #define GAME_CODE 0x4e444d45 // NDME 1103 1104 int I_ReadPakFile(void) // 800073B8 1105 { 1106 int ret; 1107 u8 *ext_name; 1108 1109 ControllerPakStatus = 0; 1110 1111 if (gamepad_system_busy != 0) 1112 { 1113 do { 1114 osYieldThread(); 1115 } while (gamepad_system_busy != 0); 1116 } 1117 1118 Pak_Data = NULL; 1119 Pak_Size = 0; 1120 ext_name = NULL; 1121 1122 ret = osPfsFindFile(&ControllerPak, COMPANY_CODE, GAME_CODE, Game_Name, ext_name, &File_Num); 1123 1124 if (ret == 0) 1125 { 1126 Pak_Size = FileState[File_Num].file_size; 1127 Pak_Data = (byte *)Z_Malloc(Pak_Size, PU_STATIC, NULL); 1128 ret = osPfsReadWriteFile(&ControllerPak, File_Num, PFS_READ, 0, Pak_Size, Pak_Data); 1129 } 1130 1131 ControllerPakStatus = 1; 1132 1133 return ret; 1134 } 1135 1136 int I_CreatePakFile(void) // 800074D4 1137 { 1138 int ret; 1139 u8 ExtName [8]; 1140 1141 ControllerPakStatus = 0; 1142 1143 if (gamepad_system_busy != 0) 1144 { 1145 do { 1146 osYieldThread(); 1147 } while (gamepad_system_busy != 0); 1148 } 1149 1150 if (Pak_Memory < 2) 1151 Pak_Size = 256; 1152 else 1153 Pak_Size = 512; 1154 1155 Pak_Data = (byte *)Z_Malloc(Pak_Size, PU_STATIC, NULL); 1156 D_memset(Pak_Data, 0, Pak_Size); 1157 1158 *(int*)ExtName = 0; 1159 1160 ret = osPfsAllocateFile(&ControllerPak, COMPANY_CODE, GAME_CODE, Game_Name, ExtName, Pak_Size, &File_Num); 1161 1162 if (ret == PFS_ERR_INCONSISTENT) 1163 ret = osPfsChecker(&ControllerPak); 1164 1165 if (ret == 0) 1166 ret = osPfsReadWriteFile(&ControllerPak, File_Num, PFS_WRITE, 0, Pak_Size, Pak_Data); 1167 1168 ControllerPakStatus = 1; 1169 1170 return ret; 1171 }