From a81fbd2df6bb7c4bcfa18d58b265ba1daefcf421 Mon Sep 17 00:00:00 2001 From: Andy Miles <35545964+andy-miles@users.noreply.github.com> Date: Thu, 1 Aug 2024 11:45:44 -0700 Subject: [PATCH] Atari 5200 Updates 1. Added CRC database lookup for ROM dump validation and file renaming 2. Added delays to improve successful ROM dumping. Especially helps with 2-chip ROMs 3. Fixed database mapper config for Star Trek (not a 2-chip ROM) --- Cart_Reader/5200.ino | 90 ++++++---- Cart_Reader/Cart_Reader.ino | 4 +- sd/5200.txt | 333 ++++++++++++++++++++---------------- 3 files changed, 246 insertions(+), 181 deletions(-) diff --git a/Cart_Reader/5200.ino b/Cart_Reader/5200.ino index 2b881d4f..fb4f0ec8 100644 --- a/Cart_Reader/5200.ino +++ b/Cart_Reader/5200.ino @@ -54,6 +54,12 @@ #define DISABLE_8000 PORTH |= (1 << 6) // ROM SELECT 8000-BFFF #define ENABLE_8000 PORTH &= ~(1 << 6) +struct a5200_DB_entry { + char crc32[9]; + byte gameMapper; + byte gameSize; +}; + //****************************************** // Supported Mappers //****************************************** @@ -166,37 +172,14 @@ uint8_t readData_5200(uint16_t addr) // Add Input Pullup { PORTF = addr & 0xFF; // A0-A7 PORTK = (addr >> 8) & 0xFF; // A8-A13 - NOP; - NOP; - NOP; - NOP; - NOP; + cycleDelay(5); // DDRC = 0x00; // Set to Input PORTC = 0xFF; // Input Pullup - NOP; - NOP; - NOP; - NOP; - NOP; - // Extended Delay for Vanguard - NOP; - NOP; - NOP; - NOP; - NOP; - NOP; - NOP; - NOP; - NOP; - NOP; + cycleDelay(15); // Standard + extended delay for Vanguard uint8_t ret = PINC; - NOP; - NOP; - NOP; - NOP; - NOP; + cycleDelay(5); return ret; } @@ -249,11 +232,14 @@ void readROM_5200() { // Lower Half of 32K is at 0x4000 if (a5200size == 3) { // 32K ENABLE_4000; + cycleDelay(15); readSegment_5200(0x4000, 0x8000); // +16K = 32K DISABLE_4000; + cycleDelay(15); } // 4K/8K/16K + Upper Half of 32K ENABLE_8000; + cycleDelay(15); if (a5200size > 1) readSegment_5200(0x8000, 0xA000); // +8K = 16K if (a5200size > 0) @@ -261,32 +247,41 @@ void readROM_5200() { // Base 4K readSegment_5200(0xB000, 0xC000); // 4K DISABLE_8000; + cycleDelay(15); break; case 1: // Two Chip 16KB ENABLE_4000; + cycleDelay(15); readSegment_5200(0x4000, 0x6000); // 8K DISABLE_4000; + cycleDelay(15); ENABLE_8000; + cycleDelay(15); readSegment_5200(0x8000, 0xA000); // +8K = 16K DISABLE_8000; + cycleDelay(15); break; case 2: // Bounty Bob Strikes Back 40KB [UNTESTED] ENABLE_4000; + cycleDelay(15); // First 16KB (4KB x 4) readBankBountyBob_5200(0x4000); // Second 16KB (4KB x 4) readBankBountyBob_5200(0x5000); DISABLE_4000; + cycleDelay(15); ENABLE_8000; + cycleDelay(15); readSegment_5200(0x8000, 0xA000); // +8K = 40K DISABLE_8000; + cycleDelay(15); break; } myFile.close(); - printCRC(fileName, NULL, 0); + compareCRC("5200.txt", 0, 1, 0); println_Msg(FS(FSTRING_EMPTY)); // Prints string out of the common strings array either with or without newline @@ -421,6 +416,35 @@ void checkStatus_5200() { #endif } +//****************************************** +// READ MAPPER +//****************************************** + +void readDbEntry(FsFile& database, void* entry) { + struct a5200_DB_entry* castEntry = (a5200_DB_entry*)entry; + + // Read expected CRC32 as a string + for (int i = 0; i < 8; ++i) { + castEntry->crc32[i] = database.read(); + } + castEntry->crc32[8] = '\0'; + database.seekCur(1); // Skip comma delimiter + + // Read mapper + castEntry->gameMapper = database.read() - 48; + + // if next char is not a comma, expect an additional digit + char temp = database.read(); + if (temp != ',') { + castEntry->gameMapper = (castEntry->gameMapper * 10) + (temp - 48); + database.seekCur(1); // Skip over comma + } + + // Read rom size + castEntry->gameSize = database.read() - 48; + database.seekCur(2); // Skip rest of line +} + //****************************************** // SET MAPPER //****************************************** @@ -473,7 +497,7 @@ void setCart_5200() { //go to root sd.chdir(); - struct database_entry_mapper_size entry; + struct a5200_DB_entry entry; // Select starting letter byte myLetter = starting_letter(); @@ -482,7 +506,7 @@ void setCart_5200() { if (myFile.open("5200.txt", O_READ)) { seek_first_letter_in_database(myFile, myLetter); - if(checkCartSelection(myFile, &readDataLineMapperSize, &entry)) { + if(checkCartSelection(myFile, &readDbEntry, &entry)) { EEPROM_writeAnything(7, entry.gameMapper); EEPROM_writeAnything(8, entry.gameSize); } @@ -490,4 +514,12 @@ void setCart_5200() { print_FatalError(FS(FSTRING_DATABASE_FILE_NOT_FOUND)); } } + +// While not precise in terms of exact cycles for NOP due to the for-loop +// overhead, it simplifies the code while still achieving a similar result. +void cycleDelay(byte cycleCount) { + for (byte i = 0; i < cycleCount; ++i) { + NOP; + } +} #endif diff --git a/Cart_Reader/Cart_Reader.ino b/Cart_Reader/Cart_Reader.ino index d93bfcfb..396f017e 100644 --- a/Cart_Reader/Cart_Reader.ino +++ b/Cart_Reader/Cart_Reader.ino @@ -459,7 +459,7 @@ uint32_t calculateCRC(char* fileName, char* folder, unsigned long offset) { /****************************************** CRC Functions for Atari, Fairchild, Ody2, Arc, etc. modules *****************************************/ -#if (defined(ENABLE_ODY2) || defined(ENABLE_ARC) || defined(ENABLE_FAIRCHILD) || defined(ENABLE_MSX) || defined(ENABLE_POKE) || defined(ENABLE_2600) || defined(ENABLE_5200) || defined(ENABLE_7800) || defined(ENABLE_C64) || defined(ENABLE_VECTREX) || defined(ENABLE_NES) || defined(ENABLE_LYNX) || defined(ENABLE_ATARI8) || defined(ENABLE_BALLY) || defined(ENABLE_LEAP) || defined(ENABLE_LJ) || defined(ENABLE_LJPRO) || defined(ENABLE_PV1000) || defined(ENABLE_PYUUTA) || defined(ENABLE_RCA) || defined(ENABLE_TI99) || defined(ENABLE_TRS80) || defined(ENABLE_VIC20) || defined(ENABLE_VSMILE)) +#if (defined(ENABLE_ODY2) || defined(ENABLE_ARC) || defined(ENABLE_FAIRCHILD) || defined(ENABLE_MSX) || defined(ENABLE_POKE) || defined(ENABLE_2600) || defined(ENABLE_7800) || defined(ENABLE_C64) || defined(ENABLE_VECTREX) || defined(ENABLE_NES) || defined(ENABLE_LYNX) || defined(ENABLE_ATARI8) || defined(ENABLE_BALLY) || defined(ENABLE_LEAP) || defined(ENABLE_LJ) || defined(ENABLE_LJPRO) || defined(ENABLE_PV1000) || defined(ENABLE_PYUUTA) || defined(ENABLE_RCA) || defined(ENABLE_TI99) || defined(ENABLE_TRS80) || defined(ENABLE_VIC20) || defined(ENABLE_VSMILE)) void printCRC(char* checkFile, uint32_t* crcCopy, unsigned long offset) { uint32_t crc = calculateCRC(checkFile, folder, offset); @@ -751,7 +751,7 @@ void readDataLineSingleDigit(FsFile& database, void* byteData) { #endif #if ( \ - defined(ENABLE_ODY2) || defined(ENABLE_5200) || defined(ENABLE_7800) || defined(ENABLE_C64) || defined(ENABLE_JAGUAR) || \ + defined(ENABLE_ODY2) || defined(ENABLE_7800) || defined(ENABLE_C64) || defined(ENABLE_JAGUAR) || \ defined(ENABLE_VIC20)|| defined(ENABLE_ATARI8)\ ) struct database_entry_mapper_size { diff --git a/sd/5200.txt b/sd/5200.txt index b590f775..789ad66f 100644 --- a/sd/5200.txt +++ b/sd/5200.txt @@ -1,225 +1,258 @@ -Activision Decathlon -0,2 +Activision Decathlon, The (USA).a52 +F43E7CD0,0,2 -Astro Chase -1,2 +Astro Chase (USA).a52 +4019ECEC,1,2 -Atari PAM - Pete's Test -0,1 +Atari PAM - Pete's Test (USA).a52 +28278CD6,0,1 -Atari PAM Diagnostics -1,2 +Atari PAM Diagnostics (USA) (v2.0).a52 +E8B130C4,1,2 -Atari PAM System Test -0,1 +Atari PAM Diagnostics (USA) (v2.3).a52 +CE07D9AD,1,2 -Ballblazer -0,3 +Atari PAM System Test (USA) (v1.02).a52 +7EA86E87,0,1 -Beamrider -0,2 +Ballblazer (USA).a52 +DEF2A207,0,3 -BerZerk -0,2 +Beamrider (USA).a52 +9BAE58DC,0,2 -Blue Print -0,2 +BerZerk (USA).a52 +BE3CD348,0,2 -Boogie -0,0 +Blue Print (USA).a52 +0624E6E7,0,2 -Bounty Bob Strikes Back! -2,4 +Boogie (USA) (Demo).a52 +3BD5FDD6,0,0 -Buck Rogers -1,2 +Bounty Bob Strikes Back! (USA).a52 +7873C6DD,2,4 -Centipede -1,2 +Buck Rogers - Planet of Zoom (USA) (Alt).a52 +20DF4927,1,2 -Choplifter! -0,2 +Buck Rogers - Planet of Zoom (USA).a52 +04807705,1,2 -Congo Bongo -1,2 +Carol Shaw's River Raid (USA).a52 +09FC7648,0,1 -Countermeasure -1,2 +Castle Blast (USA) (Unl).a52 +7C988054,0,3 -Defender -1,2 +Castle Crisis (USA) (Unl).a52 +D50E4061,0,3 -Dig Dug -1,2 +Centipede (USA).a52 +536A70FE,1,2 -Dreadnaught Factor -0,1 +Choplifter! (USA).a52 +9AD53BBC,0,2 -Frogger -0,1 +Congo Bongo (USA).a52 +F1F42BBD,1,2 -Frogger II -1,2 +Countermeasure (USA).a52 +FD541C80,1,2 -Galaxian -0,1 +David Crane's Pitfall II - Lost Caverns (USA).a52 +4B910461,0,2 -Gorf -0,1 +Defender (USA).a52 +BD52623B,1,2 -Gremlins -0,3 +Dig Dug (USA).a52 +6A687F9C,1,2 -Gyruss -1,2 +Dreadnaught Factor, The (USA).a52 +460DEF2D,0,1 -H.E.R.O. -0,2 +Frogger (USA).a52 +AE7E3444,0,1 -James Bond 007 -1,2 +Frogger II - Threeedeep! (USA).a52 +0AF19345,1,2 -Joust -1,2 +Galaxian (USA) (Alt).a52 +3A6E6133,0,1 -Jungle Hunt -1,2 +Galaxian (USA).a52 +3EF4A23F,0,1 -Kaboom! -0,0 +Gorf (USA).a52 +E955DB74,0,1 -Kangaroo -1,2 +Gremlins (USA).a52 +063EC2C4,0,3 -Keystone Kapers -0,1 +Gyruss (USA) (Alt).a52 +4241582D,1,2 -K-Razy Shoot-Out -0,1 +Gyruss.a52 +CFD4A7F9,1,2 -Mario Bros. -0,3 +H.E.R.O. (USA).a52 +18A73AF3,0,2 -MegaMania -0,1 +James Bond 007 (USA).a52 +D9AE4518,1,2 -Meteorites -0,2 +Joust (USA).a52 +BFD30C01,1,2 -Miner 2049er -0,2 +Jungle Hunt (USA).a52 +2C676662,1,2 -Missile Command -0,1 +Kaboom! (USA).a52 +420F5D0B,0,0 -Montezuma's Revenge -1,2 +Kangaroo (USA).a52 +ECFA624F,1,2 -Moon Patrol -0,2 +Keystone Kapers (USA).a52 +8FE3BB2C,0,1 -Mountain King -0,1 +Koffi - Yellow Kopter (USA) (Unl).a52 +917BE656,0,3 -Mr. Do!'s Castle -0,1 +K-Razy Shoot-Out (USA).a52 +EE702214,0,1 -Ms. Pac-Man -1,2 +Mario Bros. (USA) (Alt).a52 +6B3F1179,0,3 -Pac-Man -1,2 +Mario Bros. (USA).a52 +873742F1,0,3 -Pengo -0,3 +MegaMania (USA).a52 +240A1E1A,0,1 -Pitfall II -0,2 +Meteorites (USA).a52 +AB8E035B,0,2 -Pitfall! -0,1 +Miner 2049er Starring Bounty Bob (USA).a52 +7DF1ADFB,0,2 -Pole Position -1,2 +Missile Command (USA).a52 +44D3FF6F,0,1 -Popeye -1,2 +Montezuma's Revenge - Featuring Panama Joe (USA).a52 +2A640143,1,2 -Q-bert -0,1 +Moon Patrol (USA).a52 +D0B2F285,0,2 -QIX -1,2 +Mountain King (USA).a52 +0F24243C,0,1 -Quest for Quintana Roo -0,2 +Mr. Do!'s Castle (USA).a52 +AA55F9BE,0,1 -RealSports Baseball -0,3 +Ms. Pac-Man (USA).a52 +752F5EFD,1,2 -RealSports Basketball -0,3 +Pac-Man (USA).a52 +8873EF51,1,2 -RealSports Football -1,2 +Pengo (USA).a52 +E4F8BA8C,0,3 -RealSports Soccer -1,2 +Pitfall! (USA).a52 +B2887833,0,1 -RealSports Tennis -1,2 +Pole Position (USA).a52 +ABC2D1E4,1,2 -Rescue on Fractalus! -0,3 +Popeye (USA).a52 +A18A9A40,1,2 -River Raid -0,1 +Q-bert (USA).a52 +3FE4A401,0,1 -Robotron 2084 -0,2 +QIX (USA).a52 +AEA6D2C2,1,2 -Space Dungeon -1,2 +Quest for Quintana Roo (USA).a52 +B5F3402B,0,2 -Space Invaders -0,1 +RealSports Baseball (USA).a52 +44166592,0,3 -Space Shuttle -0,2 +RealSports Basketball (USA).a52 +DD217276,0,3 -Star Raiders -1,2 +RealSports Football (USA).a52 +4336C2CC,1,2 -Star Trek -1,2 +RealSports Soccer (USA).a52 +ECBD1853,1,2 -Star Wars - Return of the Jedi -0,1 +RealSports Tennis (USA).a52 +10F33C90,1,2 -Star Wars - The Arcade Game -1,2 +Rescue on Fractalus! (USA).a52 +762C591B,0,3 -Super Breakout -0,0 +Robotron 2084 (USA).a52 +4252ABD9,0,2 -Super Cobra -0,1 +Space Dungeon (USA).a52 +B68D61E8,1,2 -Vanguard -0,3 +Space Invaders (USA).a52 +DE5C354A,0,1 -Wizard of Wor -0,2 +Space Shuttle - A Journey Into Space (USA).a52 +387365DC,0,2 -Yellow Submarine -0,0 +Star Raiders (USA) (Alt).a52 +4BAC5DD9,1,2 -Zaxxon -0,3 +Star Raiders (USA).a52 +7D819A9F,1,2 -Zenji -0,1 +Star Trek - Strategic Operations Simulator (USA) (Alt).a52 +33B70206,0,2 -Zone Ranger -0,2 +Star Trek - Strategic Operations Simulator (USA).a52 +69F23548,0,2 + +Star Wars - Return of the Jedi - Death Star Battle (USA).a52 +0675F0A5,0,1 + +Star Wars - The Arcade Game (USA).a52 +75F566DF,1,2 + +Super Breakout (USA).a52 +A0642110,0,0 + +Super Cobra (USA).a52 +97DEBCD2,0,1 + +Tempest (USA) (AtariAge).a52 +A6400E17,0,3 + +Vanguard (USA).a52 +CAAEA0A4,0,3 + +Wizard of Wor (USA).a52 +D6F7DDFD,0,2 + +Yellow Submarine (USA) (Demo).a52 +F47BC091,0,0 + +Zaxxon (USA).a52 +741746D1,0,3 + +Zenji (USA).a52 +DA228530,0,1 + +Zone Ranger (USA).a52 +2959D827,0,2