diff --git a/Config.c b/Config.c index 0e65f9d..562b103 100644 --- a/Config.c +++ b/Config.c @@ -59,6 +59,14 @@ inline u32 ConfigGetConfig( u32 Config ) { return !!(DMLCfg->Config & Config); } +inline void ConfigSetConfig( u32 Config ) +{ + DMLCfg->Config |= Config; +} +inline void ConfigClearConfig( u32 Config ) +{ + DMLCfg->Config &= ~Config; +} u32 ConfigGetVideMode( void ) { return DMLCfg->VideoMode; diff --git a/Config.h b/Config.h index f01a740..5e68af3 100644 --- a/Config.h +++ b/Config.h @@ -90,6 +90,8 @@ enum VideoModes void ConfigInit( DML_CFG *Cfg ); u32 ConfigGetConfig( u32 Config ); +void ConfigSetConfig( u32 Config ); +void ConfigClearConfig( u32 Config ); u32 ConfigGetVideMode( void ); char *ConfigGetGamePath( void ); diff --git a/DVD.c b/DVD.c index 7790e8d..d12d8af 100644 --- a/DVD.c +++ b/DVD.c @@ -20,13 +20,14 @@ u32 FCState[FILECACHE_MAX]; s32 DVDSelectGame( void ) { char *str = (char*)malloca( 256, 32 ); + u32 i=0; if( ConfigGetConfig(DML_CFG_GAME_PATH) ) { sprintf( str, "%s", ConfigGetGamePath() ); } else { - dbgprintf("No game path was supplied!\n"); + dbgprintf("DIP:No game path was supplied!\n"); free(str); return -1; } @@ -39,13 +40,40 @@ s32 DVDSelectGame( void ) //Try to switch to FST mode if( !FSTInit() ) { - dbgprintf("Failed to open:\"%s\" fres:%d\n", str, fres ); + dbgprintf("DIP:Failed to open:\"%s\" fres:%d\n", str, fres ); free(str); return -2; } } else { + f_close( &GameFile ); + + dbgprintf("DIP:Current Gamepath:\"%s\"\n", str ); + + //search the string backwards for '/' + for( i=strlen(str); i > 0; --i ) + if( str[i] == '/' ) + break; + i++; + + if( ConfigGetConfig(DML_CFG_BOOT_DISC2) ) + { + sprintf( str+i, "disc2.iso" ); + } else { + sprintf( str+i, "game.iso" ); + } + + dbgprintf("DIP:New Gamepath:\"%s\"\n", str ); + + fres = f_open( &GameFile, str, FA_READ ); + if( fres != FR_OK ) + { + dbgprintf("DIP:Failed to open:\"%s\" fres:%d\n", str, fres ); + free(str); + return -3; + } + f_lseek( &GameFile, 0 ); f_read( &GameFile, (void*)0, 0x20, &read ); diff --git a/Patches.c b/Patches.c index 5ff9e17..8217f95 100644 --- a/Patches.c +++ b/Patches.c @@ -597,6 +597,10 @@ void DoCardPatches( char *ptr, u32 size, u32 SectionOffset ) return; +} +void InitPatches( void ) +{ + } void DoPatches( char *ptr, u32 size, u32 SectionOffset ) { @@ -648,15 +652,15 @@ void DoPatches( char *ptr, u32 size, u32 SectionOffset ) for( i=0; i < size; i+=4 ) { if( (PatchCount & 2) == 0 ) - if( (read32( (u32)ptr + i )&0xFC00FFFF) == 0x5400077A && - (read32( (u32)ptr + i + 4 )&0xFC00FFFF) == 0x28000000 && - read32( (u32)ptr + i + 8 ) == 0x41820008 && - (read32( (u32)ptr + i +12 )&0xFC00FFFF) == 0x64002000 + if( (read32( (u32)ptr + i ) & 0xFC00FFFF) == 0x5400077A && + (read32( (u32)ptr + i + 4 ) & 0xFC00FFFF) == 0x28000000 && + read32( (u32)ptr + i + 8 ) == 0x41820008 && + (read32( (u32)ptr + i +12 ) & 0xFC00FFFF) == 0x64002000 ) { dbgprintf("Patch:Found [__OSDispatchInterrupt]: 0x%08X 0x%08X\n", (u32)ptr + i + 0 + SectionOffset, (u32)ptr + i + 0x1A8 + SectionOffset ); - write32( (u32)ptr + i + 0, (read32( (u32)ptr + i + 0 ) & 0xFFFF0000) | 0x0463 ); + write32( (u32)ptr + i + 0, (read32( (u32)ptr + i + 0 ) & 0xFFFF0000) | 0x0463 ); write32( (u32)ptr + i + 0x1A8, (read32( (u32)ptr + i + 0x1A8 ) & 0xFFFF0000) | 0x0463 ); PatchCount |= 2; @@ -909,12 +913,73 @@ void DoPatches( char *ptr, u32 size, u32 SectionOffset ) } } + if( (PatchCount & 256) == 0 ) //DVDLowStopMotor + { + if( read32( (u32)ptr + i ) == 0x3C00E300 ) + { + u32 Offset = (u32)ptr + i; + + dbgprintf("Patch:[DVDLowStopMotor] 0x%08X\n", Offset + SectionOffset ); + + value = *(vu32*)(Offset-12); + value&= 0xFFFF0000; + value|= 0x0000C000; + *(vu32*)(Offset-12) = value; + + value = *(vu32*)(Offset-8); + value&= 0xFFFF0000; + value|= 0x00002F00; + *(vu32*)(Offset-8) = value; + + value = *(vu32*)(Offset+4); + value&= 0xFFFF0000; + value|= 0x00002F08; + *(vu32*)(Offset+4) = value; + + PatchCount |= 256; + } + } + + if( (PatchCount & 512) == 0 ) //DVDLowReadDiskID + { + if( (read32( (u32)ptr + i ) & 0xFFFF ) == 0xA800 && (read32( (u32)ptr + i + 4 ) & 0xFFFF ) == 0x40 ) + { + u32 Offset = (u32)ptr + i; + + dbgprintf("Patch:[DVDLowReadDiskID] 0x%08X\n", Offset + SectionOffset ); + + value = *(vu32*)(Offset); + value&= 0xFFFF0000; + value|= 0x0000A700; + *(vu32*)(Offset) = value; + + value = *(vu32*)(Offset+0x20); + value&= 0xFFFF0000; + value|= 0x0000C000; + *(vu32*)(Offset+0x20) = value; + + value = *(vu32*)(Offset+0x24); + value&= 0xFFFF0000; + value|= 0x00002F00; + *(vu32*)(Offset+0x24) = value; + + value = *(vu32*)(Offset+0x2C); + value&= 0xFFFF0000; + value|= 0x00002F08; + *(vu32*)(Offset+0x2C) = value; + + write32( 0x01576D4, 0x38600000 ); + + PatchCount |= 512; + } + } + if( ConfigGetConfig(DML_CFG_CHEATS) || ConfigGetConfig( DML_CFG_DEBUGGER ) ) { - if( PatchCount == 255 ) + if( PatchCount == 1023 ) break; } else { - if( PatchCount == 239 ) + if( PatchCount == 1007 ) break; } } diff --git a/dip.c b/dip.c index 532b302..7ce2a11 100644 --- a/dip.c +++ b/dip.c @@ -15,6 +15,7 @@ u32 DOLSize = 0; u32 DOLOffset = 0; s32 ELFNumberOfSections = 0; u32 FSTMode = 0; +u32 DiscChangeIRQ = 0; extern DML_CFG *DMLCfg; @@ -104,6 +105,39 @@ u32 DIUpdateRegisters( void ) switch( read32(DI_SCMD_0) >> 24 ) { + case 0xE3: + { + dbgprintf("DIP:DVDLowStopMotor()\n"); + + u32 CDiscNumber = (read32(4) << 16 ) >> 24; + dbgprintf("DIP:Current disc number:%u\n", CDiscNumber + 1 ); + + if( CDiscNumber ) + { + ConfigClearConfig(DML_CFG_BOOT_DISC2); + } else { + ConfigSetConfig(DML_CFG_BOOT_DISC2); + } + + f_close( &GameFile ); + + dbgprintf("DVDSelectGame():%d\n", DVDSelectGame() ); + + DiscChangeIRQ = 1; + + while( read32(DI_SCONTROL) & 1 ) + clear32( DI_SCONTROL, 1 ); + + set32( DI_SSTATUS, 0x3A ); + + write32( 0x0d80000C, (1<<0) | (1<<4) ); + write32( HW_PPCIRQFLAG, read32(HW_PPCIRQFLAG) ); + write32( HW_ARMIRQFLAG, read32(HW_ARMIRQFLAG) ); + set32( 0x0d80000C, (1<<2) ); + + write32( HW_TIMER, 0 ); + + } break; case 0xA7: case 0xA9: //dbgprintf("DIP:Async!\n"); diff --git a/global.h b/global.h index 8904f6f..5efd29f 100644 --- a/global.h +++ b/global.h @@ -15,7 +15,7 @@ #define PADHOOK 1 #define CONFIG_VERSION 0x00000002 -#define DML_VERSION 0x00020005 +#define DML_VERSION 0x00020006 #define DI_SUCCESS 1 #define DI_ERROR 2 diff --git a/main.c b/main.c index 03ed686..0894819 100644 --- a/main.c +++ b/main.c @@ -22,6 +22,8 @@ Copyright (C) 2010-2012 crediar #include "dip.h" #include "Patches.h" +extern u32 DiscChangeIRQ; + char __aeabi_unwind_cpp_pr0[0]; void Syscall( u32 a, u32 b, u32 c, u32 d ) @@ -113,7 +115,6 @@ void SysShutdown( void ) } u32 fail; -FIL Log; int main( int argc, char *argv[] ) { @@ -239,6 +240,27 @@ int main( int argc, char *argv[] ) PADLock = 0; } + if( DiscChangeIRQ ) + if( read32(HW_TIMER) * 128 / 243000000 > 2 ) + { + // dbgprintf("DIP:IRQ mon!\n"); + + //DVDGetDriveStatus + //write32( 0x01576D4, 0x38600000 ); + + while( read32(DI_SCONTROL) & 1 ) + clear32( DI_SCONTROL, 1 ); + + set32( DI_SSTATUS, 0x3A ); + + write32( 0x0d80000C, (1<<0) | (1<<4) ); + write32( HW_PPCIRQFLAG, read32(HW_PPCIRQFLAG) ); + write32( HW_ARMIRQFLAG, read32(HW_ARMIRQFLAG) ); + set32( 0x0d80000C, (1<<2) ); + + DiscChangeIRQ = 0; + } + if( (((read32(0x12FC) >> 16) & 0x1030) == 0x1030 ) ) { SysReset();