From 23a47828f4e274b24bf1a2c120471acba32402c7 Mon Sep 17 00:00:00 2001 From: "SND\\edgbla_cp" Date: Wed, 13 Oct 2010 16:17:20 +0000 Subject: SIO_CYCLES (BaudReg * 8). git-svn-id: https://pcsxr.svn.codeplex.com/svn/pcsxr@58374 e17a0e51-4ae3-4d35-97c3-1a29b211df97 --- libpcsxcore/sio.c | 1005 ++++++++++++++++++++++++++--------------------------- 1 file changed, 500 insertions(+), 505 deletions(-) diff --git a/libpcsxcore/sio.c b/libpcsxcore/sio.c index d0d21df8..22d96f9c 100644 --- a/libpcsxcore/sio.c +++ b/libpcsxcore/sio.c @@ -46,16 +46,16 @@ #define SIO_RESET 0x0040 // *** FOR WORKS ON PADS AND MEMORY CARDS ***** - - -void LoadDongle( char *str ); -void SaveDongle( char *str ); - - -#define BUFFER_SIZE 0x1010 - -static unsigned char buf[ BUFFER_SIZE ]; - + + +void LoadDongle( char *str ); +void SaveDongle( char *str ); + + +#define BUFFER_SIZE 0x1010 + +static unsigned char buf[ BUFFER_SIZE ]; + unsigned char cardh[4] = { 0x00, 0x00, 0x5a, 0x5d }; // Transfer Ready and the Buffer is Empty @@ -70,80 +70,75 @@ static unsigned int parp; static unsigned int mcdst, rdwr; static unsigned char adrH, adrL; static unsigned int padst; -static unsigned int gsdonglest; +static unsigned int gsdonglest; char Mcd1Data[MCD_SIZE], Mcd2Data[MCD_SIZE]; - -#define DONGLE_SIZE 0x40 * 0x1000 - -unsigned int DongleBank; -unsigned char DongleData[ DONGLE_SIZE ]; -static int DongleInit; - - -#if 0 -// Breaks Twisted Metal 2 intro -#define SIO_INT(eCycle) { \ - if (!Config.Sio) { \ - psxRegs.interrupt |= (1 << PSXINT_SIO); \ - psxRegs.intCycle[PSXINT_SIO].cycle = eCycle; \ - psxRegs.intCycle[PSXINT_SIO].sCycle = psxRegs.cycle; \ - } \ - \ - StatReg &= ~RX_RDY; \ - StatReg &= ~TX_RDY; \ -} -#endif - + +#define DONGLE_SIZE 0x40 * 0x1000 + +unsigned int DongleBank; +unsigned char DongleData[ DONGLE_SIZE ]; +static int DongleInit; + + +#if 0 +// Breaks Twisted Metal 2 intro #define SIO_INT(eCycle) { \ if (!Config.Sio) { \ psxRegs.interrupt |= (1 << PSXINT_SIO); \ psxRegs.intCycle[PSXINT_SIO].cycle = eCycle; \ psxRegs.intCycle[PSXINT_SIO].sCycle = psxRegs.cycle; \ - } \ + } \ + \ + StatReg &= ~RX_RDY; \ + StatReg &= ~TX_RDY; \ } +#endif + +#define SIO_INT(eCycle) { \ + if (!Config.Sio) { \ + psxRegs.interrupt |= (1 << PSXINT_SIO); \ + psxRegs.intCycle[PSXINT_SIO].cycle = eCycle; \ + psxRegs.intCycle[PSXINT_SIO].sCycle = psxRegs.cycle; \ + } \ +} + - -//#define SIO_CYCLES (BaudReg * 8) - // clk cycle byte // 4us * 8bits = (PSXCLK / 1000000) * 32; (linuzappz) -// TODO: add SioModePrescaler and BaudReg - -// rely on this for now - someone's actual testing -#define SIO_CYCLES (PSXCLK / 57600) - -//PCSX 1.9.91 -//#define SIO_CYCLES 200 - -//PCSX 1.9.91 -//#define SIO_CYCLES 270 - -// ePSXe 1.6.0 +// TODO: add SioModePrescaler +#define SIO_CYCLES (BaudReg * 8) + +// rely on this for now - someone's actual testing +//#define SIO_CYCLES (PSXCLK / 57600) +//PCSX 1.9.91 +//#define SIO_CYCLES 200 +//PCSX 1.9.91 +//#define SIO_CYCLES 270 +// ePSXe 1.6.0 //#define SIO_CYCLES 535 - -// ePSXe 1.7.0 -//#define SIO_CYCLES 635 - -unsigned char reverse_8( unsigned char bits ) -{ - unsigned char tmp; - int lcv; - - tmp = 0; - for( lcv = 0; lcv < 8; lcv++ ) - { - tmp >>= 1; - tmp |= (bits & 0x80); - - bits <<= 1; - } - - return tmp; -} - - +// ePSXe 1.7.0 +//#define SIO_CYCLES 635 + +unsigned char reverse_8( unsigned char bits ) +{ + unsigned char tmp; + int lcv; + + tmp = 0; + for( lcv = 0; lcv < 8; lcv++ ) + { + tmp >>= 1; + tmp |= (bits & 0x80); + + bits <<= 1; + } + + return tmp; +} + + void sioWrite8(unsigned char value) { #ifdef PAD_LOG PAD_LOG("sio write8 %x\n", value); @@ -276,363 +271,363 @@ void sioWrite8(unsigned char value) { return; } - - /* - GameShark CDX - - ae - be - ef - 04 + [00] - ae - be - ef - 01 + 00 + [00] * $1000 - ae - be - ef - 01 + 42 + [00] * $1000 - ae - be - ef - 03 + 01,01,1f,e3,85,ae,d1,28 + [00] * 4 - */ - switch (gsdonglest) { - // main command loop - case 1: - SIO_INT( SIO_CYCLES ); - - // GS CDX - // - unknown output - - // reset device when fail? - if( value == 0xae ) - { - StatReg |= RX_RDY; - - parp = 0; - bufcount = parp; - } - - - // GS CDX - else if( value == 0xbe ) - { - StatReg |= RX_RDY; - - parp = 0; - bufcount = parp; - - - buf[0] = reverse_8( 0xde ); - } - - - // GS CDX - else if( value == 0xef ) - { - StatReg |= RX_RDY; - - parp = 0; - bufcount = parp; - - - buf[0] = reverse_8( 0xad ); - } - - - // GS CDX [1 in + $1000 out + $1 out] - else if( value == 0x01 ) - { - StatReg |= RX_RDY; - - parp = 0; - bufcount = parp; - - - // $00 = 0000 0000 - // - (reverse) 0000 0000 - buf[0] = 0x00; - gsdonglest = 2; - } - - - // GS CDX [1 in + $1000 in + $1 out] - else if( value == 0x02 ) - { - StatReg |= RX_RDY; - - parp = 0; - bufcount = parp; - - - // $00 = 0000 0000 - // - (reverse) 0000 0000 - buf[0] = 0x00; - gsdonglest = 3; - } - - - // GS CDX [8 in, 4 out] - else if( value == 0x03 ) - { - StatReg |= RX_RDY; - - parp = 0; - bufcount = parp; - - // $00 = 0000 0000 - // - (reverse) 0000 0000 - buf[0] = 0x00; - - gsdonglest = 4; - } - - - // GS CDX [out 1] - else if( value == 0x04 ) - { - StatReg |= RX_RDY; - - parp = 0; - bufcount = parp; - - - // $00 = 0000 0000 - // - (reverse) 0000 0000 - buf[0] = 0x00; - gsdonglest = 5; - } - else - { - // ERROR!! - StatReg |= RX_RDY; - - parp = 0; - bufcount = parp; - buf[0] = 0xff; - - gsdonglest = 0; - } - - return; - - - // be - ef - 01 - case 2: { - unsigned char checksum; - unsigned int lcv; - - SIO_INT( SIO_CYCLES ); - StatReg |= RX_RDY; - - - // read 1 byte - DongleBank = buf[ 0 ]; - - - // write data + checksum - checksum = 0; - for( lcv = 0; lcv < 0x1000; lcv++ ) - { - unsigned char data; - - data = DongleData[ DongleBank * 0x1000 + lcv ]; - - buf[ lcv+1 ] = reverse_8( data ); - checksum += data; - } - - - parp = 0; - bufcount = 0x1001; - buf[ 0x1001 ] = reverse_8( checksum ); - - - gsdonglest = 255; - return; - } - - - // be - ef - 02 - case 3: - SIO_INT( SIO_CYCLES ); - StatReg |= RX_RDY; - - // command start - if( parp < 0x1000+1 ) - { - // read 1 byte - buf[ parp ] = value; - parp++; - } - - if( parp == 0x1001 ) - { - unsigned char checksum; - unsigned int lcv; - - DongleBank = buf[0]; - memcpy( DongleData + DongleBank * 0x1000, buf+1, 0x1000 ); - - // save to file - SaveDongle( "memcards/CDX_Dongle.bin" ); - - - // write 8-bit checksum - checksum = 0; - for( lcv = 1; lcv < 0x1001; lcv++ ) - { - checksum += buf[ lcv ]; - } - - parp = 0; - bufcount = 1; - buf[1] = reverse_8( checksum ); - - - // flush result - gsdonglest = 255; - } - return; - - - // be - ef - 03 - case 4: - SIO_INT( SIO_CYCLES ); - StatReg |= RX_RDY; - - // command start - if( parp < 8 ) - { - // read 2 (?,?) + 4 (DATA?) + 2 (CRC?) - buf[ parp ] = value; - parp++; - } - - if( parp == 8 ) - { - // now write 4 bytes via -FOUR- $00 writes - parp = 8; - bufcount = 12; - - - // TODO: Solve CDX algorithm - - - // GS CDX [magic key] - if( buf[2] == 0x12 && buf[3] == 0x34 && - buf[4] == 0x56 && buf[5] == 0x78 ) - { - buf[9] = reverse_8( 0x3e ); - buf[10] = reverse_8( 0xa0 ); - buf[11] = reverse_8( 0x40 ); - buf[12] = reverse_8( 0x29 ); - } - - // GS CDX [address key #2 = 6ec] - else if( buf[2] == 0x1f && buf[3] == 0xe3 && - buf[4] == 0x45 && buf[5] == 0x60 ) - { - buf[9] = reverse_8( 0xee ); - buf[10] = reverse_8( 0xdd ); - buf[11] = reverse_8( 0x71 ); - buf[12] = reverse_8( 0xa8 ); - } - - // GS CDX [address key #3 = ???] - else if( buf[2] == 0x1f && buf[3] == 0xe3 && - buf[4] == 0x72 && buf[5] == 0xe3 ) - { - // unsolved!! - - // Used here: 80090348 / 80090498 - - // dummy value - MSB - buf[9] = reverse_8( 0xfa ); - buf[10] = reverse_8( 0xde ); - buf[11] = reverse_8( 0x21 ); - buf[12] = reverse_8( 0x97 ); - } - - // GS CDX [address key #4 = a00] - else if( buf[2] == 0x1f && buf[3] == 0xe3 && - buf[4] == 0x85 && buf[5] == 0xae ) - { - buf[9] = reverse_8( 0xee ); - buf[10] = reverse_8( 0xdd ); - buf[11] = reverse_8( 0x7d ); - buf[12] = reverse_8( 0x44 ); - } - - // GS CDX [address key #5 = 9ec] - else if( buf[2] == 0x17 && buf[3] == 0xe3 && - buf[4] == 0xb5 && buf[5] == 0x60 ) - { - buf[9] = reverse_8( 0xee ); - buf[10] = reverse_8( 0xdd ); - buf[11] = reverse_8( 0x7e ); - buf[12] = reverse_8( 0xa8 ); - } - - else - { - // dummy value - MSB - buf[9] = reverse_8( 0xfa ); - buf[10] = reverse_8( 0xde ); - buf[11] = reverse_8( 0x21 ); - buf[12] = reverse_8( 0x97 ); - } - - // flush bytes -> done - gsdonglest = 255; - } - return; - - - // be - ef - 04 - case 5: - if( value == 0x00 ) - { - SIO_INT( SIO_CYCLES ); - StatReg |= RX_RDY; - - - // read 1 byte - parp = 0; - bufcount = parp; - - // size of dongle card? - buf[ 0 ] = reverse_8( DONGLE_SIZE / 0x1000 ); - - - // done already - gsdonglest = 0; - } - return; - - - // flush bytes -> done - case 255: - if( value == 0x00 ) - { - //SIO_INT( SIO_CYCLES ); - SIO_INT(1); - StatReg |= RX_RDY; - - parp++; - if( parp == bufcount ) - { - gsdonglest = 0; - -#ifdef GSDONGLE_LOG - PAD_LOG("(gameshark dongle) DONE!!\n" ); -#endif - } - } - else - { - // ERROR!! - StatReg |= RX_RDY; - - parp = 0; - bufcount = parp; - buf[0] = 0xff; - - gsdonglest = 0; - } - return; - } - - + + /* + GameShark CDX + + ae - be - ef - 04 + [00] + ae - be - ef - 01 + 00 + [00] * $1000 + ae - be - ef - 01 + 42 + [00] * $1000 + ae - be - ef - 03 + 01,01,1f,e3,85,ae,d1,28 + [00] * 4 + */ + switch (gsdonglest) { + // main command loop + case 1: + SIO_INT( SIO_CYCLES ); + + // GS CDX + // - unknown output + + // reset device when fail? + if( value == 0xae ) + { + StatReg |= RX_RDY; + + parp = 0; + bufcount = parp; + } + + + // GS CDX + else if( value == 0xbe ) + { + StatReg |= RX_RDY; + + parp = 0; + bufcount = parp; + + + buf[0] = reverse_8( 0xde ); + } + + + // GS CDX + else if( value == 0xef ) + { + StatReg |= RX_RDY; + + parp = 0; + bufcount = parp; + + + buf[0] = reverse_8( 0xad ); + } + + + // GS CDX [1 in + $1000 out + $1 out] + else if( value == 0x01 ) + { + StatReg |= RX_RDY; + + parp = 0; + bufcount = parp; + + + // $00 = 0000 0000 + // - (reverse) 0000 0000 + buf[0] = 0x00; + gsdonglest = 2; + } + + + // GS CDX [1 in + $1000 in + $1 out] + else if( value == 0x02 ) + { + StatReg |= RX_RDY; + + parp = 0; + bufcount = parp; + + + // $00 = 0000 0000 + // - (reverse) 0000 0000 + buf[0] = 0x00; + gsdonglest = 3; + } + + + // GS CDX [8 in, 4 out] + else if( value == 0x03 ) + { + StatReg |= RX_RDY; + + parp = 0; + bufcount = parp; + + // $00 = 0000 0000 + // - (reverse) 0000 0000 + buf[0] = 0x00; + + gsdonglest = 4; + } + + + // GS CDX [out 1] + else if( value == 0x04 ) + { + StatReg |= RX_RDY; + + parp = 0; + bufcount = parp; + + + // $00 = 0000 0000 + // - (reverse) 0000 0000 + buf[0] = 0x00; + gsdonglest = 5; + } + else + { + // ERROR!! + StatReg |= RX_RDY; + + parp = 0; + bufcount = parp; + buf[0] = 0xff; + + gsdonglest = 0; + } + + return; + + + // be - ef - 01 + case 2: { + unsigned char checksum; + unsigned int lcv; + + SIO_INT( SIO_CYCLES ); + StatReg |= RX_RDY; + + + // read 1 byte + DongleBank = buf[ 0 ]; + + + // write data + checksum + checksum = 0; + for( lcv = 0; lcv < 0x1000; lcv++ ) + { + unsigned char data; + + data = DongleData[ DongleBank * 0x1000 + lcv ]; + + buf[ lcv+1 ] = reverse_8( data ); + checksum += data; + } + + + parp = 0; + bufcount = 0x1001; + buf[ 0x1001 ] = reverse_8( checksum ); + + + gsdonglest = 255; + return; + } + + + // be - ef - 02 + case 3: + SIO_INT( SIO_CYCLES ); + StatReg |= RX_RDY; + + // command start + if( parp < 0x1000+1 ) + { + // read 1 byte + buf[ parp ] = value; + parp++; + } + + if( parp == 0x1001 ) + { + unsigned char checksum; + unsigned int lcv; + + DongleBank = buf[0]; + memcpy( DongleData + DongleBank * 0x1000, buf+1, 0x1000 ); + + // save to file + SaveDongle( "memcards/CDX_Dongle.bin" ); + + + // write 8-bit checksum + checksum = 0; + for( lcv = 1; lcv < 0x1001; lcv++ ) + { + checksum += buf[ lcv ]; + } + + parp = 0; + bufcount = 1; + buf[1] = reverse_8( checksum ); + + + // flush result + gsdonglest = 255; + } + return; + + + // be - ef - 03 + case 4: + SIO_INT( SIO_CYCLES ); + StatReg |= RX_RDY; + + // command start + if( parp < 8 ) + { + // read 2 (?,?) + 4 (DATA?) + 2 (CRC?) + buf[ parp ] = value; + parp++; + } + + if( parp == 8 ) + { + // now write 4 bytes via -FOUR- $00 writes + parp = 8; + bufcount = 12; + + + // TODO: Solve CDX algorithm + + + // GS CDX [magic key] + if( buf[2] == 0x12 && buf[3] == 0x34 && + buf[4] == 0x56 && buf[5] == 0x78 ) + { + buf[9] = reverse_8( 0x3e ); + buf[10] = reverse_8( 0xa0 ); + buf[11] = reverse_8( 0x40 ); + buf[12] = reverse_8( 0x29 ); + } + + // GS CDX [address key #2 = 6ec] + else if( buf[2] == 0x1f && buf[3] == 0xe3 && + buf[4] == 0x45 && buf[5] == 0x60 ) + { + buf[9] = reverse_8( 0xee ); + buf[10] = reverse_8( 0xdd ); + buf[11] = reverse_8( 0x71 ); + buf[12] = reverse_8( 0xa8 ); + } + + // GS CDX [address key #3 = ???] + else if( buf[2] == 0x1f && buf[3] == 0xe3 && + buf[4] == 0x72 && buf[5] == 0xe3 ) + { + // unsolved!! + + // Used here: 80090348 / 80090498 + + // dummy value - MSB + buf[9] = reverse_8( 0xfa ); + buf[10] = reverse_8( 0xde ); + buf[11] = reverse_8( 0x21 ); + buf[12] = reverse_8( 0x97 ); + } + + // GS CDX [address key #4 = a00] + else if( buf[2] == 0x1f && buf[3] == 0xe3 && + buf[4] == 0x85 && buf[5] == 0xae ) + { + buf[9] = reverse_8( 0xee ); + buf[10] = reverse_8( 0xdd ); + buf[11] = reverse_8( 0x7d ); + buf[12] = reverse_8( 0x44 ); + } + + // GS CDX [address key #5 = 9ec] + else if( buf[2] == 0x17 && buf[3] == 0xe3 && + buf[4] == 0xb5 && buf[5] == 0x60 ) + { + buf[9] = reverse_8( 0xee ); + buf[10] = reverse_8( 0xdd ); + buf[11] = reverse_8( 0x7e ); + buf[12] = reverse_8( 0xa8 ); + } + + else + { + // dummy value - MSB + buf[9] = reverse_8( 0xfa ); + buf[10] = reverse_8( 0xde ); + buf[11] = reverse_8( 0x21 ); + buf[12] = reverse_8( 0x97 ); + } + + // flush bytes -> done + gsdonglest = 255; + } + return; + + + // be - ef - 04 + case 5: + if( value == 0x00 ) + { + SIO_INT( SIO_CYCLES ); + StatReg |= RX_RDY; + + + // read 1 byte + parp = 0; + bufcount = parp; + + // size of dongle card? + buf[ 0 ] = reverse_8( DONGLE_SIZE / 0x1000 ); + + + // done already + gsdonglest = 0; + } + return; + + + // flush bytes -> done + case 255: + if( value == 0x00 ) + { + //SIO_INT( SIO_CYCLES ); + SIO_INT(1); + StatReg |= RX_RDY; + + parp++; + if( parp == bufcount ) + { + gsdonglest = 0; + +#ifdef GSDONGLE_LOG + PAD_LOG("(gameshark dongle) DONE!!\n" ); +#endif + } + } + else + { + // ERROR!! + StatReg |= RX_RDY; + + parp = 0; + bufcount = parp; + buf[0] = 0xff; + + gsdonglest = 0; + } + return; + } + + switch (value) { case 0x01: // start pad StatReg |= RX_RDY; // Transfer is Ready @@ -687,28 +682,28 @@ void sioWrite8(unsigned char value) { mcdst = 1; rdwr = 0; SIO_INT(SIO_CYCLES); - return; - - case 0xae: // GameShark CDX - start dongle - StatReg |= RX_RDY; - gsdonglest = 1; - - parp = 0; - bufcount = parp; - - if( !DongleInit ) - { - LoadDongle( "memcards/CDX_Dongle.bin" ); - - DongleInit = 1; - } - - SIO_INT( SIO_CYCLES ); - return; - - default: // no hardware found - StatReg |= RX_RDY; - return; + return; + + case 0xae: // GameShark CDX - start dongle + StatReg |= RX_RDY; + gsdonglest = 1; + + parp = 0; + bufcount = parp; + + if( !DongleInit ) + { + LoadDongle( "memcards/CDX_Dongle.bin" ); + + DongleInit = 1; + } + + SIO_INT( SIO_CYCLES ); + return; + + default: // no hardware found + StatReg |= RX_RDY; + return; } } @@ -803,13 +798,13 @@ void sioInterrupt() { // SysPrintf("Sio Interrupt\n"); StatReg |= IRQ; psxHu32ref(0x1070) |= SWAPu32(0x80); - -#if 0 - // Rhapsody: fixes input problems - // Twisted Metal 2: breaks intro - StatReg |= TX_RDY; - StatReg |= RX_RDY; -#endif + +#if 0 + // Rhapsody: fixes input problems + // Twisted Metal 2: breaks intro + StatReg |= TX_RDY; + StatReg |= RX_RDY; +#endif } void LoadMcd(int mcd, char *str) { @@ -1226,51 +1221,51 @@ int sioFreeze(gzFile f, int Mode) { return 0; } - - -void LoadDongle( char *str ) -{ - FILE *f; - - f = fopen(str, "r+b"); - if (f != NULL) { - fread( DongleData, 1, DONGLE_SIZE, f ); - fclose( f ); - } - else { - u32 *ptr, lcv; - - ptr = (unsigned int *) DongleData; - - // create temp data - ptr[0] = (u32) 0x02015447; - ptr[1] = (u32) 7; - ptr[2] = (u32) 1; - ptr[3] = (u32) 0; - - for( lcv=4; lcv<0x6c / 4; lcv++ ) - { - ptr[ lcv ] = 0; - } - - ptr[ lcv ] = (u32) 0x02000100; - lcv++; - - while( lcv < 0x1000/4 ) - { - ptr[ lcv ] = (u32) 0xffffffff; - lcv++; - } - } -} - -void SaveDongle( char *str ) -{ - FILE *f; - - f = fopen(str, "wb"); - if (f != NULL) { - fwrite( DongleData, 1, DONGLE_SIZE, f ); - fclose( f ); - } -} + + +void LoadDongle( char *str ) +{ + FILE *f; + + f = fopen(str, "r+b"); + if (f != NULL) { + fread( DongleData, 1, DONGLE_SIZE, f ); + fclose( f ); + } + else { + u32 *ptr, lcv; + + ptr = (unsigned int *) DongleData; + + // create temp data + ptr[0] = (u32) 0x02015447; + ptr[1] = (u32) 7; + ptr[2] = (u32) 1; + ptr[3] = (u32) 0; + + for( lcv=4; lcv<0x6c / 4; lcv++ ) + { + ptr[ lcv ] = 0; + } + + ptr[ lcv ] = (u32) 0x02000100; + lcv++; + + while( lcv < 0x1000/4 ) + { + ptr[ lcv ] = (u32) 0xffffffff; + lcv++; + } + } +} + +void SaveDongle( char *str ) +{ + FILE *f; + + f = fopen(str, "wb"); + if (f != NULL) { + fwrite( DongleData, 1, DONGLE_SIZE, f ); + fclose( f ); + } +} -- cgit v1.2.3