From 0f1c10230a736a5cb3821f1fdc09a96249b936ac Mon Sep 17 00:00:00 2001 From: Gregory Hainaut Date: Mon, 15 Aug 2016 14:09:01 +0200 Subject: [PATCH] CDVD: catch MEC/NVM file exception It will stop the emulation and open a nice box with an error message instead of terminate PCSX2 --- pcsx2/CDVD/CDVD.cpp | 1191 ++++++++++++++++++++++--------------------- 1 file changed, 599 insertions(+), 592 deletions(-) diff --git a/pcsx2/CDVD/CDVD.cpp b/pcsx2/CDVD/CDVD.cpp index 213305352e..aab02885a9 100644 --- a/pcsx2/CDVD/CDVD.cpp +++ b/pcsx2/CDVD/CDVD.cpp @@ -1420,620 +1420,627 @@ static __fi void fail_pol_cal() static void cdvdWrite16(u8 rt) // SCOMMAND { -// cdvdTN diskInfo; -// cdvdTD trackInfo; -// int i, lbn, type, min, sec, frm, address; - int address; - u8 tmp; + try { + // cdvdTN diskInfo; + // cdvdTD trackInfo; + // int i, lbn, type, min, sec, frm, address; + int address; + u8 tmp; - CDVD_LOG("cdvdWrite16: SCMD %s (%x) (ParamP = %x)", sCmdName[rt], rt, cdvd.ParamP); + CDVD_LOG("cdvdWrite16: SCMD %s (%x) (ParamP = %x)", sCmdName[rt], rt, cdvd.ParamP); - cdvd.sCommand = rt; - cdvd.Result[0] = 0; // assume success -- failures will overwrite this with an error code. + cdvd.sCommand = rt; + cdvd.Result[0] = 0; // assume success -- failures will overwrite this with an error code. - switch (rt) { -// case 0x01: // GetDiscType - from cdvdman (0:1) -// SetResultSize(1); -// cdvd.Result[0] = 0; -// break; + switch (rt) { + // case 0x01: // GetDiscType - from cdvdman (0:1) + // SetResultSize(1); + // cdvd.Result[0] = 0; + // break; - case 0x02: // CdReadSubQ (0:11) - SetResultSize(11); - cdvd.Result[0] = cdvdReadSubQ(cdvd.Sector, (cdvdSubQ*)&cdvd.Result[1]); - break; + case 0x02: // CdReadSubQ (0:11) + SetResultSize(11); + cdvd.Result[0] = cdvdReadSubQ(cdvd.Sector, (cdvdSubQ*)&cdvd.Result[1]); + break; - case 0x03: // Mecacon-command - switch (cdvd.Param[0]) - { - case 0x00: // get mecha version (1:4) - SetResultSize(4); - cdvdGetMechaVer(&cdvd.Result[0]); - break; + case 0x03: // Mecacon-command + switch (cdvd.Param[0]) + { + case 0x00: // get mecha version (1:4) + SetResultSize(4); + cdvdGetMechaVer(&cdvd.Result[0]); + break; - case 0x44: // write console ID (9:1) - SetResultSize(1); - cdvdWriteConsoleID(&cdvd.Param[1]); - break; + case 0x44: // write console ID (9:1) + SetResultSize(1); + cdvdWriteConsoleID(&cdvd.Param[1]); + break; - case 0x45: // read console ID (1:9) - SetResultSize(9); - cdvdReadConsoleID(&cdvd.Result[1]); - break; + case 0x45: // read console ID (1:9) + SetResultSize(9); + cdvdReadConsoleID(&cdvd.Result[1]); + break; - case 0xFD: // _sceCdReadRenewalDate (1:6) BCD - SetResultSize(6); - cdvd.Result[0] = 0; - cdvd.Result[1] = 0x04;//year - cdvd.Result[2] = 0x12;//month - cdvd.Result[3] = 0x10;//day - cdvd.Result[4] = 0x01;//hour - cdvd.Result[5] = 0x30;//min - break; + case 0xFD: // _sceCdReadRenewalDate (1:6) BCD + SetResultSize(6); + cdvd.Result[0] = 0; + cdvd.Result[1] = 0x04;//year + cdvd.Result[2] = 0x12;//month + cdvd.Result[3] = 0x10;//day + cdvd.Result[4] = 0x01;//hour + cdvd.Result[5] = 0x30;//min + break; - default: - SetResultSize(1); - cdvd.Result[0] = 0x80; - Console.Warning("*Unknown Mecacon Command param[0]=%02X", cdvd.Param[0]); - break; - } - break; + default: + SetResultSize(1); + cdvd.Result[0] = 0x80; + Console.Warning("*Unknown Mecacon Command param[0]=%02X", cdvd.Param[0]); + break; + } + break; - case 0x05: // CdTrayReqState (0:1) - resets the tray open detection - - // Fixme: This function is believed to change some status flag - // when the Tray state (stored as "1" in cdvd.Status) is different between 2 successive calls. - // Cdvd.Status can be different than 1 here, yet we may still have to report an open status. - // Gonna have to investigate further. (rama) - - //Console.Warning("CdTrayReqState. cdvd.Status = %d", cdvd.Status); - SetResultSize(1); + case 0x05: // CdTrayReqState (0:1) - resets the tray open detection - if (cdvd.Status == CDVD_STATUS_TRAY_OPEN) - { - //Console.Warning( "reporting Open status" ); - cdvd.Result[0] = 1; - } - else - { - //Console.Warning( "reporting Close status" ); - cdvd.Result[0] = 0; // old behaviour was always this - } + // Fixme: This function is believed to change some status flag + // when the Tray state (stored as "1" in cdvd.Status) is different between 2 successive calls. + // Cdvd.Status can be different than 1 here, yet we may still have to report an open status. + // Gonna have to investigate further. (rama) - break; - - case 0x06: // CdTrayCtrl (1:1) - SetResultSize(1); - //Console.Warning( "CdTrayCtrl, param = %d", cdvd.Param[0]); - if(cdvd.Param[0] == 0) - cdvd.Result[0] = cdvdCtrlTrayOpen(); - else - cdvd.Result[0] = cdvdCtrlTrayClose(); - break; - - case 0x08: // CdReadRTC (0:8) - SetResultSize(8); - cdvd.Result[0] = 0; - cdvd.Result[1] = itob(cdvd.RTC.second); //Seconds - cdvd.Result[2] = itob(cdvd.RTC.minute); //Minutes - cdvd.Result[3] = itob(cdvd.RTC.hour); //Hours - cdvd.Result[4] = 0; //Nothing - cdvd.Result[5] = itob(cdvd.RTC.day); //Day - cdvd.Result[6] = itob(cdvd.RTC.month); //Month - cdvd.Result[7] = itob(cdvd.RTC.year); //Year - /*Console.WriteLn("RTC Read Sec %x Min %x Hr %x Day %x Month %x Year %x", cdvd.Result[1], cdvd.Result[2], - cdvd.Result[3], cdvd.Result[5], cdvd.Result[6], cdvd.Result[7]); - Console.WriteLn("RTC Read Real Sec %d Min %d Hr %d Day %d Month %d Year %d", cdvd.RTC.second, cdvd.RTC.minute, - cdvd.RTC.hour, cdvd.RTC.day, cdvd.RTC.month, cdvd.RTC.year);*/ - break; - - case 0x09: // sceCdWriteRTC (7:1) - SetResultSize(1); - cdvd.Result[0] = 0; - cdvd.RTC.pad = 0; - - cdvd.RTC.second = btoi(cdvd.Param[cdvd.ParamP-7]); - cdvd.RTC.minute = btoi(cdvd.Param[cdvd.ParamP-6]) % 60; - cdvd.RTC.hour = btoi(cdvd.Param[cdvd.ParamP-5]) % 24; - cdvd.RTC.day = btoi(cdvd.Param[cdvd.ParamP-3]); - cdvd.RTC.month = btoi(cdvd.Param[cdvd.ParamP-2] & 0x7f); - cdvd.RTC.year = btoi(cdvd.Param[cdvd.ParamP-1]); - /*Console.WriteLn("RTC write incomming Sec %x Min %x Hr %x Day %x Month %x Year %x", cdvd.Param[cdvd.ParamP-7], cdvd.Param[cdvd.ParamP-6], - cdvd.Param[cdvd.ParamP-5], cdvd.Param[cdvd.ParamP-3], cdvd.Param[cdvd.ParamP-2], cdvd.Param[cdvd.ParamP-1]); - Console.WriteLn("RTC Write Sec %d Min %d Hr %d Day %d Month %d Year %d", cdvd.RTC.second, cdvd.RTC.minute, - cdvd.RTC.hour, cdvd.RTC.day, cdvd.RTC.month, cdvd.RTC.year);*/ - //memcpy((u8*)&cdvd.RTC, cdvd.Param, 7); - break; - - case 0x0A: // sceCdReadNVM (2:3) - address = (cdvd.Param[0]<<8) | cdvd.Param[1]; - - if (address < 512) - { - SetResultSize(3); - cdvdReadNVM(&cdvd.Result[1], address*2, 2); - // swap bytes around - tmp = cdvd.Result[1]; - cdvd.Result[1] = cdvd.Result[2]; - cdvd.Result[2] = tmp; - } - else - { + //Console.Warning("CdTrayReqState. cdvd.Status = %d", cdvd.Status); SetResultSize(1); - cdvd.Result[0] = 0xff; - } - break; - case 0x0B: // sceCdWriteNVM (4:1) - SetResultSize(1); - address = (cdvd.Param[0]<<8) | cdvd.Param[1]; - - if (address < 512) - { - // swap bytes around - tmp = cdvd.Param[2]; - cdvd.Param[2] = cdvd.Param[3]; - cdvd.Param[3] = tmp; - cdvdWriteNVM(&cdvd.Param[2], address*2, 2); - } - else - { - cdvd.Result[0] = 0xff; - } - break; - -// case 0x0C: // sceCdSetHDMode (1:1) -// break; - - - case 0x0F: // sceCdPowerOff (0:1)- Call74 from Xcdvdman - SetResultSize(1); - cdvd.Result[0] = 0; - break; - - case 0x12: // sceCdReadILinkId (0:9) - SetResultSize(9); - cdvdReadILinkID(&cdvd.Result[1]); - break; - - case 0x13: // sceCdWriteILinkID (8:1) - SetResultSize(1); - cdvdWriteILinkID(&cdvd.Param[1]); - break; - - case 0x14: // CdCtrlAudioDigitalOut (1:1) - //parameter can be 2, 0, ... - SetResultSize(1); - cdvd.Result[0] = 0; //8 is a flag; not used - break; - - case 0x15: // sceCdForbidDVDP (0:1) - //Console.WriteLn("sceCdForbidDVDP"); - SetResultSize(1); - cdvd.Result[0] = 5; - break; - - case 0x16: // AutoAdjustCtrl - from cdvdman (1:1) - SetResultSize(1); - cdvd.Result[0] = 0; - break; - - case 0x17: // CdReadModelNumber (1:9) - from xcdvdman - SetResultSize(9); - cdvdReadModelNumber(&cdvd.Result[1], cdvd.Param[0]); - break; - - case 0x18: // CdWriteModelNumber (9:1) - from xcdvdman - SetResultSize(1); - cdvdWriteModelNumber(&cdvd.Param[1], cdvd.Param[0]); - break; - -// case 0x19: // sceCdForbidRead (0:1) - from xcdvdman -// break; - - case 0x1A: // sceCdBootCertify (4:1)//(4:16 in psx?) - SetResultSize(1);//on input there are 4 bytes: 1;?10;J;C for 18000; 1;60;E;C for 39002 from ROMVER - cdvd.Result[0] = 1;//i guess that means okay - break; - - case 0x1B: // sceCdCancelPOffRdy (0:1) - Call73 from Xcdvdman (1:1) - SetResultSize(1); - cdvd.Result[0] = 0; - break; - - case 0x1C: // sceCdBlueLEDCtl (1:1) - Call72 from Xcdvdman - SetResultSize(1); - cdvd.Result[0] = 0; - break; - -// case 0x1D: // cdvdman_call116 (0:5) - In V10 Bios -// break; - - case 0x1E: // sceRemote2Read (0:5) - // 00 14 AA BB CC -> remote key code - SetResultSize(5); - cdvd.Result[0] = 0x00; - cdvd.Result[1] = 0x14; - cdvd.Result[2] = 0x00; - cdvd.Result[3] = 0x00; - cdvd.Result[4] = 0x00; - break; - -// case 0x1F: // sceRemote2_7 (2:1) - cdvdman_call117 -// break; - - case 0x20: // sceRemote2_6 (0:3) // 00 01 00 - SetResultSize(3); - cdvd.Result[0] = 0x00; - cdvd.Result[1] = 0x01; - cdvd.Result[2] = 0x00; - break; - -// case 0x21: // sceCdWriteWakeUpTime (8:1) -// break; - - case 0x22: // sceCdReadWakeUpTime (0:10) - SetResultSize(10); - cdvd.Result[0] = 0; - cdvd.Result[1] = 0; - cdvd.Result[2] = 0; - cdvd.Result[3] = 0; - cdvd.Result[4] = 0; - cdvd.Result[5] = 0; - cdvd.Result[6] = 0; - cdvd.Result[7] = 0; - cdvd.Result[8] = 0; - cdvd.Result[9] = 0; - break; - - case 0x24: // sceCdRCBypassCtrl (1:1) - In V10 Bios - // FIXME: because PRId<0x23, the bit 0 of sio2 don't get updated 0xBF808284 - SetResultSize(1); - cdvd.Result[0] = 0; - break; - -// case 0x25: // cdvdman_call120 (1:1) - In V10 Bios -// break; - -// case 0x26: // cdvdman_call128 (0,3) - In V10 Bios -// break; - -// case 0x27: // cdvdman_call148 (0:13) - In V10 Bios -// break; - -// case 0x28: // cdvdman_call150 (1:1) - In V10 Bios -// break; - - case 0x29: //sceCdNoticeGameStart (1:1) - SetResultSize(1); - cdvd.Result[0] = 0; - break; - -// case 0x2C: //sceCdXBSPowerCtl (2:2) -// break; - -// case 0x2D: //sceCdXLEDCtl (2:2) -// break; - -// case 0x2E: //sceCdBuzzerCtl (0:1) -// break; - -// case 0x2F: //cdvdman_call167 (16:1) -// break; - -// case 0x30: //cdvdman_call169 (1:9) -// break; - - case 0x31: //sceCdSetMediumRemoval (1:1) - SetResultSize(1); - cdvd.Result[0] = 0; - break; - - case 0x32: //sceCdGetMediumRemoval (0:2) - SetResultSize(2); - cdvd.Result[0] = 0; - //cdvd.Result[0] = 0; // fixme: I'm pretty sure that the same variable shouldn't be set twice here. Perhaps cdvd.Result[1]? - break; - -// case 0x33: //sceCdXDVRPReset (1:1) -// break; - - case 0x36: //cdvdman_call189 [__sceCdReadRegionParams - made up name] (0:15) i think it is 16, not 15 - SetResultSize(15); - - cdvdGetMechaVer(&cdvd.Result[1]); - cdvdReadRegionParams(&cdvd.Result[3]);//size==8 - DevCon.WriteLn("REGION PARAMS = %s %s", mg_zones[cdvd.Result[1] & 7], &cdvd.Result[3]); - cdvd.Result[1] = 1 << cdvd.Result[1]; //encryption zone; see offset 0x1C in encrypted headers - ////////////////////////////////////////// - cdvd.Result[2] = 0; //?? -// cdvd.Result[3] == ROMVER[4] == *0xBFC7FF04 -// cdvd.Result[4] == OSDVER[4] == CAP Jjpn, Aeng, Eeng, Heng, Reng, Csch, Kkor? -// cdvd.Result[5] == OSDVER[5] == small -// cdvd.Result[6] == OSDVER[6] == small -// cdvd.Result[7] == OSDVER[7] == small -// cdvd.Result[8] == VERSTR[0x22] == *0xBFC7FF52 -// cdvd.Result[9] == DVDID J U O E A R C M -// cdvd.Result[10]== 0; //?? - cdvd.Result[11] = 0; //?? - cdvd.Result[12] = 0; //?? - ////////////////////////////////////////// - cdvd.Result[13] = 0; //0xFF - 77001 - cdvd.Result[14] = 0; //?? - break; - - case 0x37: //called from EECONF [sceCdReadMAC - made up name] (0:9) - SetResultSize(9); - cdvdReadMAC(&cdvd.Result[1]); - break; - - case 0x38: //used to fix the MAC back after accidentally trashed it :D [sceCdWriteMAC - made up name] (8:1) - SetResultSize(1); - cdvdWriteMAC(&cdvd.Param[0]); - break; - - case 0x3E: //[__sceCdWriteRegionParams - made up name] (15:1) [Florin: hum, i was expecting 14:1] - SetResultSize(1); - cdvdWriteRegionParams(&cdvd.Param[2]); - break; - - case 0x40: // CdOpenConfig (3:1) - SetResultSize(1); - cdvd.CReadWrite = cdvd.Param[0]; - cdvd.COffset = cdvd.Param[1]; - cdvd.CNumBlocks = cdvd.Param[2]; - cdvd.CBlockIndex= 0; - cdvd.Result[0] = 0; - break; - - case 0x41: // CdReadConfig (0:16) - SetResultSize(16); - cdvdReadConfig(&cdvd.Result[0]); - break; - - case 0x42: // CdWriteConfig (16:1) - SetResultSize(1); - cdvdWriteConfig(&cdvd.Param[0]); - break; - - case 0x43: // CdCloseConfig (0:1) - SetResultSize(1); - cdvd.CReadWrite = 0; - cdvd.COffset = 0; - cdvd.CNumBlocks = 0; - cdvd.CBlockIndex= 0; - cdvd.Result[0] = 0; - break; - - case 0x80: // secrman: __mechacon_auth_0x80 - SetResultSize(1);//in:1 - cdvd.mg_datatype = 0;//data - cdvd.Result[0] = 0; - break; - - case 0x81: // secrman: __mechacon_auth_0x81 - SetResultSize(1);//in:1 - cdvd.mg_datatype = 0;//data - cdvd.Result[0] = 0; - break; - - case 0x82: // secrman: __mechacon_auth_0x82 - SetResultSize(1);//in:16 - cdvd.Result[0] = 0; - break; - - case 0x83: // secrman: __mechacon_auth_0x83 - SetResultSize(1);//in:8 - cdvd.Result[0] = 0; - break; - - case 0x84: // secrman: __mechacon_auth_0x84 - SetResultSize(1+8+4);//in:0 - cdvd.Result[0] = 0; - - cdvd.Result[1] = 0x21; - cdvd.Result[2] = 0xdc; - cdvd.Result[3] = 0x31; - cdvd.Result[4] = 0x96; - cdvd.Result[5] = 0xce; - cdvd.Result[6] = 0x72; - cdvd.Result[7] = 0xe0; - cdvd.Result[8] = 0xc8; - - cdvd.Result[9] = 0x69; - cdvd.Result[10] = 0xda; - cdvd.Result[11] = 0x34; - cdvd.Result[12] = 0x9b; - break; - - case 0x85: // secrman: __mechacon_auth_0x85 - SetResultSize(1+4+8);//in:0 - cdvd.Result[0] = 0; - - cdvd.Result[1] = 0xeb; - cdvd.Result[2] = 0x01; - cdvd.Result[3] = 0xc7; - cdvd.Result[4] = 0xa9; - - cdvd.Result[ 5] = 0x3f; - cdvd.Result[ 6] = 0x9c; - cdvd.Result[ 7] = 0x5b; - cdvd.Result[ 8] = 0x19; - cdvd.Result[ 9] = 0x31; - cdvd.Result[10] = 0xa0; - cdvd.Result[11] = 0xb3; - cdvd.Result[12] = 0xa3; - break; - - case 0x86: // secrman: __mechacon_auth_0x86 - SetResultSize(1);//in:16 - cdvd.Result[0] = 0; - break; - - case 0x87: // secrman: __mechacon_auth_0x87 - SetResultSize(1);//in:8 - cdvd.Result[0] = 0; - break; - - case 0x8D: // sceMgWriteData - SetResultSize(1);//in:length<=16 - if (cdvd.mg_size + cdvd.ParamC > cdvd.mg_maxsize) - { - cdvd.Result[0] = 0x80; - } - else - { - memcpy(cdvd.mg_buffer + cdvd.mg_size, cdvd.Param, cdvd.ParamC); - cdvd.mg_size += cdvd.ParamC; - cdvd.Result[0] = 0; // 0 complete ; 1 busy ; 0x80 error - } - break; - - case 0x8E: // sceMgReadData - SetResultSize( std::min(16, cdvd.mg_size) ); - memcpy(cdvd.Result, cdvd.mg_buffer, cdvd.ResultC); - cdvd.mg_size -= cdvd.ResultC; - memcpy(cdvd.mg_buffer, cdvd.mg_buffer+cdvd.ResultC, cdvd.mg_size); - break; - - case 0x88: // secrman: __mechacon_auth_0x88 //for now it is the same; so, fall;) - case 0x8F: // secrman: __mechacon_auth_0x8F - SetResultSize(1);//in:0 - if (cdvd.mg_datatype == 1) // header data - { - u64* psrc, *pdst; - int bit_ofs, i; - - if ((cdvd.mg_maxsize != cdvd.mg_size)||(cdvd.mg_size < 0x20) || (cdvd.mg_size != *(u16*)&cdvd.mg_buffer[0x14])) + if (cdvd.Status == CDVD_STATUS_TRAY_OPEN) { - fail_pol_cal(); + //Console.Warning( "reporting Open status" ); + cdvd.Result[0] = 1; + } + else + { + //Console.Warning( "reporting Close status" ); + cdvd.Result[0] = 0; // old behaviour was always this + } + + break; + + case 0x06: // CdTrayCtrl (1:1) + SetResultSize(1); + //Console.Warning( "CdTrayCtrl, param = %d", cdvd.Param[0]); + if(cdvd.Param[0] == 0) + cdvd.Result[0] = cdvdCtrlTrayOpen(); + else + cdvd.Result[0] = cdvdCtrlTrayClose(); + break; + + case 0x08: // CdReadRTC (0:8) + SetResultSize(8); + cdvd.Result[0] = 0; + cdvd.Result[1] = itob(cdvd.RTC.second); //Seconds + cdvd.Result[2] = itob(cdvd.RTC.minute); //Minutes + cdvd.Result[3] = itob(cdvd.RTC.hour); //Hours + cdvd.Result[4] = 0; //Nothing + cdvd.Result[5] = itob(cdvd.RTC.day); //Day + cdvd.Result[6] = itob(cdvd.RTC.month); //Month + cdvd.Result[7] = itob(cdvd.RTC.year); //Year + /*Console.WriteLn("RTC Read Sec %x Min %x Hr %x Day %x Month %x Year %x", cdvd.Result[1], cdvd.Result[2], + cdvd.Result[3], cdvd.Result[5], cdvd.Result[6], cdvd.Result[7]); + Console.WriteLn("RTC Read Real Sec %d Min %d Hr %d Day %d Month %d Year %d", cdvd.RTC.second, cdvd.RTC.minute, + cdvd.RTC.hour, cdvd.RTC.day, cdvd.RTC.month, cdvd.RTC.year);*/ + break; + + case 0x09: // sceCdWriteRTC (7:1) + SetResultSize(1); + cdvd.Result[0] = 0; + cdvd.RTC.pad = 0; + + cdvd.RTC.second = btoi(cdvd.Param[cdvd.ParamP-7]); + cdvd.RTC.minute = btoi(cdvd.Param[cdvd.ParamP-6]) % 60; + cdvd.RTC.hour = btoi(cdvd.Param[cdvd.ParamP-5]) % 24; + cdvd.RTC.day = btoi(cdvd.Param[cdvd.ParamP-3]); + cdvd.RTC.month = btoi(cdvd.Param[cdvd.ParamP-2] & 0x7f); + cdvd.RTC.year = btoi(cdvd.Param[cdvd.ParamP-1]); + /*Console.WriteLn("RTC write incomming Sec %x Min %x Hr %x Day %x Month %x Year %x", cdvd.Param[cdvd.ParamP-7], cdvd.Param[cdvd.ParamP-6], + cdvd.Param[cdvd.ParamP-5], cdvd.Param[cdvd.ParamP-3], cdvd.Param[cdvd.ParamP-2], cdvd.Param[cdvd.ParamP-1]); + Console.WriteLn("RTC Write Sec %d Min %d Hr %d Day %d Month %d Year %d", cdvd.RTC.second, cdvd.RTC.minute, + cdvd.RTC.hour, cdvd.RTC.day, cdvd.RTC.month, cdvd.RTC.year);*/ + //memcpy((u8*)&cdvd.RTC, cdvd.Param, 7); + break; + + case 0x0A: // sceCdReadNVM (2:3) + address = (cdvd.Param[0]<<8) | cdvd.Param[1]; + + if (address < 512) + { + SetResultSize(3); + cdvdReadNVM(&cdvd.Result[1], address*2, 2); + // swap bytes around + tmp = cdvd.Result[1]; + cdvd.Result[1] = cdvd.Result[2]; + cdvd.Result[2] = tmp; + } + else + { + SetResultSize(1); + cdvd.Result[0] = 0xff; + } + break; + + case 0x0B: // sceCdWriteNVM (4:1) + SetResultSize(1); + address = (cdvd.Param[0]<<8) | cdvd.Param[1]; + + if (address < 512) + { + // swap bytes around + tmp = cdvd.Param[2]; + cdvd.Param[2] = cdvd.Param[3]; + cdvd.Param[3] = tmp; + cdvdWriteNVM(&cdvd.Param[2], address*2, 2); + } + else + { + cdvd.Result[0] = 0xff; + } + break; + + // case 0x0C: // sceCdSetHDMode (1:1) + // break; + + + case 0x0F: // sceCdPowerOff (0:1)- Call74 from Xcdvdman + SetResultSize(1); + cdvd.Result[0] = 0; + break; + + case 0x12: // sceCdReadILinkId (0:9) + SetResultSize(9); + cdvdReadILinkID(&cdvd.Result[1]); + break; + + case 0x13: // sceCdWriteILinkID (8:1) + SetResultSize(1); + cdvdWriteILinkID(&cdvd.Param[1]); + break; + + case 0x14: // CdCtrlAudioDigitalOut (1:1) + //parameter can be 2, 0, ... + SetResultSize(1); + cdvd.Result[0] = 0; //8 is a flag; not used + break; + + case 0x15: // sceCdForbidDVDP (0:1) + //Console.WriteLn("sceCdForbidDVDP"); + SetResultSize(1); + cdvd.Result[0] = 5; + break; + + case 0x16: // AutoAdjustCtrl - from cdvdman (1:1) + SetResultSize(1); + cdvd.Result[0] = 0; + break; + + case 0x17: // CdReadModelNumber (1:9) - from xcdvdman + SetResultSize(9); + cdvdReadModelNumber(&cdvd.Result[1], cdvd.Param[0]); + break; + + case 0x18: // CdWriteModelNumber (9:1) - from xcdvdman + SetResultSize(1); + cdvdWriteModelNumber(&cdvd.Param[1], cdvd.Param[0]); + break; + + // case 0x19: // sceCdForbidRead (0:1) - from xcdvdman + // break; + + case 0x1A: // sceCdBootCertify (4:1)//(4:16 in psx?) + SetResultSize(1);//on input there are 4 bytes: 1;?10;J;C for 18000; 1;60;E;C for 39002 from ROMVER + cdvd.Result[0] = 1;//i guess that means okay + break; + + case 0x1B: // sceCdCancelPOffRdy (0:1) - Call73 from Xcdvdman (1:1) + SetResultSize(1); + cdvd.Result[0] = 0; + break; + + case 0x1C: // sceCdBlueLEDCtl (1:1) - Call72 from Xcdvdman + SetResultSize(1); + cdvd.Result[0] = 0; + break; + + // case 0x1D: // cdvdman_call116 (0:5) - In V10 Bios + // break; + + case 0x1E: // sceRemote2Read (0:5) - // 00 14 AA BB CC -> remote key code + SetResultSize(5); + cdvd.Result[0] = 0x00; + cdvd.Result[1] = 0x14; + cdvd.Result[2] = 0x00; + cdvd.Result[3] = 0x00; + cdvd.Result[4] = 0x00; + break; + + // case 0x1F: // sceRemote2_7 (2:1) - cdvdman_call117 + // break; + + case 0x20: // sceRemote2_6 (0:3) // 00 01 00 + SetResultSize(3); + cdvd.Result[0] = 0x00; + cdvd.Result[1] = 0x01; + cdvd.Result[2] = 0x00; + break; + + // case 0x21: // sceCdWriteWakeUpTime (8:1) + // break; + + case 0x22: // sceCdReadWakeUpTime (0:10) + SetResultSize(10); + cdvd.Result[0] = 0; + cdvd.Result[1] = 0; + cdvd.Result[2] = 0; + cdvd.Result[3] = 0; + cdvd.Result[4] = 0; + cdvd.Result[5] = 0; + cdvd.Result[6] = 0; + cdvd.Result[7] = 0; + cdvd.Result[8] = 0; + cdvd.Result[9] = 0; + break; + + case 0x24: // sceCdRCBypassCtrl (1:1) - In V10 Bios + // FIXME: because PRId<0x23, the bit 0 of sio2 don't get updated 0xBF808284 + SetResultSize(1); + cdvd.Result[0] = 0; + break; + + // case 0x25: // cdvdman_call120 (1:1) - In V10 Bios + // break; + + // case 0x26: // cdvdman_call128 (0,3) - In V10 Bios + // break; + + // case 0x27: // cdvdman_call148 (0:13) - In V10 Bios + // break; + + // case 0x28: // cdvdman_call150 (1:1) - In V10 Bios + // break; + + case 0x29: //sceCdNoticeGameStart (1:1) + SetResultSize(1); + cdvd.Result[0] = 0; + break; + + // case 0x2C: //sceCdXBSPowerCtl (2:2) + // break; + + // case 0x2D: //sceCdXLEDCtl (2:2) + // break; + + // case 0x2E: //sceCdBuzzerCtl (0:1) + // break; + + // case 0x2F: //cdvdman_call167 (16:1) + // break; + + // case 0x30: //cdvdman_call169 (1:9) + // break; + + case 0x31: //sceCdSetMediumRemoval (1:1) + SetResultSize(1); + cdvd.Result[0] = 0; + break; + + case 0x32: //sceCdGetMediumRemoval (0:2) + SetResultSize(2); + cdvd.Result[0] = 0; + //cdvd.Result[0] = 0; // fixme: I'm pretty sure that the same variable shouldn't be set twice here. Perhaps cdvd.Result[1]? + break; + + // case 0x33: //sceCdXDVRPReset (1:1) + // break; + + case 0x36: //cdvdman_call189 [__sceCdReadRegionParams - made up name] (0:15) i think it is 16, not 15 + SetResultSize(15); + + cdvdGetMechaVer(&cdvd.Result[1]); + cdvdReadRegionParams(&cdvd.Result[3]);//size==8 + DevCon.WriteLn("REGION PARAMS = %s %s", mg_zones[cdvd.Result[1] & 7], &cdvd.Result[3]); + cdvd.Result[1] = 1 << cdvd.Result[1]; //encryption zone; see offset 0x1C in encrypted headers + ////////////////////////////////////////// + cdvd.Result[2] = 0; //?? + // cdvd.Result[3] == ROMVER[4] == *0xBFC7FF04 + // cdvd.Result[4] == OSDVER[4] == CAP Jjpn, Aeng, Eeng, Heng, Reng, Csch, Kkor? + // cdvd.Result[5] == OSDVER[5] == small + // cdvd.Result[6] == OSDVER[6] == small + // cdvd.Result[7] == OSDVER[7] == small + // cdvd.Result[8] == VERSTR[0x22] == *0xBFC7FF52 + // cdvd.Result[9] == DVDID J U O E A R C M + // cdvd.Result[10]== 0; //?? + cdvd.Result[11] = 0; //?? + cdvd.Result[12] = 0; //?? + ////////////////////////////////////////// + cdvd.Result[13] = 0; //0xFF - 77001 + cdvd.Result[14] = 0; //?? + break; + + case 0x37: //called from EECONF [sceCdReadMAC - made up name] (0:9) + SetResultSize(9); + cdvdReadMAC(&cdvd.Result[1]); + break; + + case 0x38: //used to fix the MAC back after accidentally trashed it :D [sceCdWriteMAC - made up name] (8:1) + SetResultSize(1); + cdvdWriteMAC(&cdvd.Param[0]); + break; + + case 0x3E: //[__sceCdWriteRegionParams - made up name] (15:1) [Florin: hum, i was expecting 14:1] + SetResultSize(1); + cdvdWriteRegionParams(&cdvd.Param[2]); + break; + + case 0x40: // CdOpenConfig (3:1) + SetResultSize(1); + cdvd.CReadWrite = cdvd.Param[0]; + cdvd.COffset = cdvd.Param[1]; + cdvd.CNumBlocks = cdvd.Param[2]; + cdvd.CBlockIndex= 0; + cdvd.Result[0] = 0; + break; + + case 0x41: // CdReadConfig (0:16) + SetResultSize(16); + cdvdReadConfig(&cdvd.Result[0]); + break; + + case 0x42: // CdWriteConfig (16:1) + SetResultSize(1); + cdvdWriteConfig(&cdvd.Param[0]); + break; + + case 0x43: // CdCloseConfig (0:1) + SetResultSize(1); + cdvd.CReadWrite = 0; + cdvd.COffset = 0; + cdvd.CNumBlocks = 0; + cdvd.CBlockIndex= 0; + cdvd.Result[0] = 0; + break; + + case 0x80: // secrman: __mechacon_auth_0x80 + SetResultSize(1);//in:1 + cdvd.mg_datatype = 0;//data + cdvd.Result[0] = 0; + break; + + case 0x81: // secrman: __mechacon_auth_0x81 + SetResultSize(1);//in:1 + cdvd.mg_datatype = 0;//data + cdvd.Result[0] = 0; + break; + + case 0x82: // secrman: __mechacon_auth_0x82 + SetResultSize(1);//in:16 + cdvd.Result[0] = 0; + break; + + case 0x83: // secrman: __mechacon_auth_0x83 + SetResultSize(1);//in:8 + cdvd.Result[0] = 0; + break; + + case 0x84: // secrman: __mechacon_auth_0x84 + SetResultSize(1+8+4);//in:0 + cdvd.Result[0] = 0; + + cdvd.Result[1] = 0x21; + cdvd.Result[2] = 0xdc; + cdvd.Result[3] = 0x31; + cdvd.Result[4] = 0x96; + cdvd.Result[5] = 0xce; + cdvd.Result[6] = 0x72; + cdvd.Result[7] = 0xe0; + cdvd.Result[8] = 0xc8; + + cdvd.Result[9] = 0x69; + cdvd.Result[10] = 0xda; + cdvd.Result[11] = 0x34; + cdvd.Result[12] = 0x9b; + break; + + case 0x85: // secrman: __mechacon_auth_0x85 + SetResultSize(1+4+8);//in:0 + cdvd.Result[0] = 0; + + cdvd.Result[1] = 0xeb; + cdvd.Result[2] = 0x01; + cdvd.Result[3] = 0xc7; + cdvd.Result[4] = 0xa9; + + cdvd.Result[ 5] = 0x3f; + cdvd.Result[ 6] = 0x9c; + cdvd.Result[ 7] = 0x5b; + cdvd.Result[ 8] = 0x19; + cdvd.Result[ 9] = 0x31; + cdvd.Result[10] = 0xa0; + cdvd.Result[11] = 0xb3; + cdvd.Result[12] = 0xa3; + break; + + case 0x86: // secrman: __mechacon_auth_0x86 + SetResultSize(1);//in:16 + cdvd.Result[0] = 0; + break; + + case 0x87: // secrman: __mechacon_auth_0x87 + SetResultSize(1);//in:8 + cdvd.Result[0] = 0; + break; + + case 0x8D: // sceMgWriteData + SetResultSize(1);//in:length<=16 + if (cdvd.mg_size + cdvd.ParamC > cdvd.mg_maxsize) + { + cdvd.Result[0] = 0x80; + } + else + { + memcpy(cdvd.mg_buffer + cdvd.mg_size, cdvd.Param, cdvd.ParamC); + cdvd.mg_size += cdvd.ParamC; + cdvd.Result[0] = 0; // 0 complete ; 1 busy ; 0x80 error + } + break; + + case 0x8E: // sceMgReadData + SetResultSize( std::min(16, cdvd.mg_size) ); + memcpy(cdvd.Result, cdvd.mg_buffer, cdvd.ResultC); + cdvd.mg_size -= cdvd.ResultC; + memcpy(cdvd.mg_buffer, cdvd.mg_buffer+cdvd.ResultC, cdvd.mg_size); + break; + + case 0x88: // secrman: __mechacon_auth_0x88 //for now it is the same; so, fall;) + case 0x8F: // secrman: __mechacon_auth_0x8F + SetResultSize(1);//in:0 + if (cdvd.mg_datatype == 1) // header data + { + u64* psrc, *pdst; + int bit_ofs, i; + + if ((cdvd.mg_maxsize != cdvd.mg_size)||(cdvd.mg_size < 0x20) || (cdvd.mg_size != *(u16*)&cdvd.mg_buffer[0x14])) + { + fail_pol_cal(); + break; + } + + std::string zoneStr; + for (i=0; i<8; i++) + { + if (cdvd.mg_buffer[0x1C] & (1<> 0) & 0xFF; + cdvd.Result[2] = (cdvd.mg_size >> 8) & 0xFF; break; } + case 0x92: // sceMgWriteDatainLength + SetResultSize(1);//in:2 + cdvd.mg_size = 0; + cdvd.mg_datatype = 0;//data (encrypted) + cdvd.mg_maxsize = cdvd.Param[0] | (((int)cdvd.Param[1])<<8); + cdvd.Result[0] = 0; // 0 complete ; 1 busy ; 0x80 error + break; - std::string zoneStr; - for (i=0; i<8; i++) + case 0x93: // sceMgWriteDataoutLength + SetResultSize(1);//in:2 + if (((cdvd.Param[0] | (((int)cdvd.Param[1])<<8)) == cdvd.mg_size) && (cdvd.mg_datatype == 0)) { - if (cdvd.mg_buffer[0x1C] & (1<ThrowException(Exception::RuntimeError() + .SetDiagMsg(L"Failed to read/write NMV/MEC file.") + .SetUserMsg(pxE( L"Failed to read/write NMV/MEC file. Check your bios setup/permission settings")) ); - - bit_ofs = mg_BIToffset(cdvd.mg_buffer); - - psrc = (u64*)&cdvd.mg_buffer[bit_ofs-0x20]; - - pdst = (u64*)cdvd.mg_kbit; - pdst[0] = psrc[0]; - pdst[1] = psrc[1]; - //memcpy(cdvd.mg_kbit, &cdvd.mg_buffer[bit_ofs-0x20], 0x10); - - pdst = (u64*)cdvd.mg_kcon; - pdst[0] = psrc[2]; - pdst[1] = psrc[3]; - //memcpy(cdvd.mg_kcon, &cdvd.mg_buffer[bit_ofs-0x10], 0x10); - - if ((cdvd.mg_buffer[bit_ofs+5] || cdvd.mg_buffer[bit_ofs+6] || cdvd.mg_buffer[bit_ofs+7]) || - (cdvd.mg_buffer[bit_ofs+4] * 16 + bit_ofs + 8 + 16 != *(u16*)&cdvd.mg_buffer[0x14])) - { - fail_pol_cal(); - break; - } - } - cdvd.Result[0] = 0; // 0 complete ; 1 busy ; 0x80 error - break; - - case 0x90: // sceMgWriteHeaderStart - SetResultSize(1);//in:5 - cdvd.mg_size = 0; - cdvd.mg_datatype = 1;//header data - Console.WriteLn("[MG] hcode=%d cnum=%d a2=%d length=0x%X", - cdvd.Param[0], cdvd.Param[3], cdvd.Param[4], cdvd.mg_maxsize = cdvd.Param[1] | (((int)cdvd.Param[2])<<8)); - - cdvd.Result[0] = 0; // 0 complete ; 1 busy ; 0x80 error - break; - - case 0x91: // sceMgReadBITLength - { - SetResultSize(3);//in:0 - int bit_ofs = mg_BIToffset(cdvd.mg_buffer); - memcpy(cdvd.mg_buffer, &cdvd.mg_buffer[bit_ofs], 8+16*cdvd.mg_buffer[bit_ofs+4]); - - cdvd.mg_maxsize = 0; // don't allow any write - cdvd.mg_size = 8+16*cdvd.mg_buffer[4];//new offset, i just moved the data - Console.WriteLn("[MG] BIT count=%d", cdvd.mg_buffer[4]); - - cdvd.Result[0] = (cdvd.mg_datatype == 1) ? 0 : 0x80; // 0 complete ; 1 busy ; 0x80 error - cdvd.Result[1] = (cdvd.mg_size >> 0) & 0xFF; - cdvd.Result[2] = (cdvd.mg_size >> 8) & 0xFF; - break; - } - case 0x92: // sceMgWriteDatainLength - SetResultSize(1);//in:2 - cdvd.mg_size = 0; - cdvd.mg_datatype = 0;//data (encrypted) - cdvd.mg_maxsize = cdvd.Param[0] | (((int)cdvd.Param[1])<<8); - cdvd.Result[0] = 0; // 0 complete ; 1 busy ; 0x80 error - break; - - case 0x93: // sceMgWriteDataoutLength - SetResultSize(1);//in:2 - if (((cdvd.Param[0] | (((int)cdvd.Param[1])<<8)) == cdvd.mg_size) && (cdvd.mg_datatype == 0)) - { - cdvd.mg_maxsize = 0; // don't allow any write - cdvd.Result[0] = 0; // 0 complete ; 1 busy ; 0x80 error - } - else - { - cdvd.Result[0] = 0x80; - } - break; - - case 0x94: // sceMgReadKbit - read first half of BIT key - SetResultSize(1+8);//in:0 - cdvd.Result[0] = 0; - - ((int*)(cdvd.Result+1))[0] = ((int*)cdvd.mg_kbit)[0]; - ((int*)(cdvd.Result+1))[1] = ((int*)cdvd.mg_kbit)[1]; - //memcpy(cdvd.Result+1, cdvd.mg_kbit, 8); - break; - - case 0x95: // sceMgReadKbit2 - read second half of BIT key - SetResultSize(1+8);//in:0 - cdvd.Result[0] = 0; - ((int*)(cdvd.Result+1))[0] = ((int*)(cdvd.mg_kbit+8))[0]; - ((int*)(cdvd.Result+1))[1] = ((int*)(cdvd.mg_kbit+8))[1]; - //memcpy(cdvd.Result+1, cdvd.mg_kbit+8, 8); - break; - - case 0x96: // sceMgReadKcon - read first half of content key - SetResultSize(1+8);//in:0 - cdvd.Result[0] = 0; - ((int*)(cdvd.Result+1))[0] = ((int*)cdvd.mg_kcon)[0]; - ((int*)(cdvd.Result+1))[1] = ((int*)cdvd.mg_kcon)[1]; - //memcpy(cdvd.Result+1, cdvd.mg_kcon, 8); - break; - - case 0x97: // sceMgReadKcon2 - read second half of content key - SetResultSize(1+8);//in:0 - cdvd.Result[0] = 0; - ((int*)(cdvd.Result+1))[0] = ((int*)(cdvd.mg_kcon+8))[0]; - ((int*)(cdvd.Result+1))[1] = ((int*)(cdvd.mg_kcon+8))[1]; - //memcpy(cdvd.Result+1, cdvd.mg_kcon+8, 8); - break; - - default: - // fake a 'correct' command - SetResultSize(1); //in:0 - cdvd.Result[0] = 0; // 0 complete ; 1 busy ; 0x80 error - Console.WriteLn("SCMD Unknown %x", rt); - break; - } // end switch - - //Console.WriteLn("SCMD - 0x%x\n", rt); - cdvd.ParamP = 0; - cdvd.ParamC = 0; + } } static __fi void cdvdWrite17(u8 rt) { // SDATAIN