X-Git-Url: http://shamusworld.gotdns.org/cgi-bin/gitweb.cgi?a=blobdiff_plain;f=src%2Ffile.cpp;h=8c1a7038842a56e2cfa34b707fe075b76018ec34;hb=de3c95ef6322202f6b06c769f2ea7856a20db35d;hp=58d22e78ba5f34a221cfc32fd7e226ec9e1b2152;hpb=f7cb31e9b5827ba24796b0829ed2e2942fe41048;p=virtualjaguar diff --git a/src/file.cpp b/src/file.cpp index 58d22e7..8c1a703 100644 --- a/src/file.cpp +++ b/src/file.cpp @@ -3,6 +3,14 @@ // // File support // by James L. Hammons +// (C) 2010 Underground Software +// +// JLH = James L. Hammons +// +// Who When What +// --- ---------- ------------------------------------------------------------- +// JLH 01/16/2010 Created this log ;-) +// JLH 02/28/2010 Added functions to look inside .ZIP files and handle contents // #include "file.h" @@ -13,12 +21,14 @@ #include "eeprom.h" #include "jaguar.h" #include "log.h" +#include "memory.h" #include "unzip.h" #include "zlib.h" // Private function prototypes static int gzfilelength(gzFile gd); +static bool CheckExtension(const char * filename, const char * ext); // // Generic ROM loading @@ -27,7 +37,7 @@ uint32 JaguarLoadROM(uint8 * rom, char * path) { // We really should have some kind of sanity checking for the ROM size here to prevent // a buffer overflow... !!! FIX !!! -#warning !!! FIX !!! Should have sanity checking for ROM size to prevent buffer overflow! +#warning "!!! FIX !!! Should have sanity checking for ROM size to prevent buffer overflow!" uint32 romSize = 0; WriteLog("JaguarLoadROM: Attempting to load file '%s'...", path); @@ -96,7 +106,7 @@ else bool JaguarLoadFile(char * path) { // jaguarRomSize = JaguarLoadROM(mem, path); - jaguarRomSize = JaguarLoadROM(jaguarMainRom, path); + jaguarROMSize = JaguarLoadROM(jaguarMainROM, path); /*//This is not *nix friendly for some reason... // if (!UserSelectFile(path, newPath)) @@ -107,7 +117,7 @@ bool JaguarLoadFile(char * path) exit(0); }*/ - if (jaguarRomSize == 0) + if (jaguarROMSize == 0) { // WriteLog("VJ: Could not load ROM from file \"%s\"...\nAborting!\n", newPath); WriteLog("GUI: Could not load ROM from file \"%s\"...\nAborting load!\n", path); @@ -117,8 +127,8 @@ bool JaguarLoadFile(char * path) return false; // This is a start... } - jaguarMainRomCRC32 = crc32_calcCheckSum(jaguarMainRom, jaguarRomSize); - WriteLog("CRC: %08X\n", (unsigned int)jaguarMainRomCRC32); + jaguarMainROMCRC32 = crc32_calcCheckSum(jaguarMainROM, jaguarROMSize); + WriteLog("CRC: %08X\n", (unsigned int)jaguarMainROMCRC32); EepromInit(); jaguarRunAddress = 0x802000; @@ -129,12 +139,12 @@ bool JaguarLoadFile(char * path) if (strcasecmp(ext, ".rom") == 0) { // File extension ".ROM": Alpine image that loads/runs at $802000 - WriteLog("GUI: Setting up homebrew (ROM)... Run address: 00802000, length: %08X\n", jaguarRomSize); + WriteLog("GUI: Setting up homebrew (ROM)... Run address: 00802000, length: %08X\n", jaguarROMSize); - for(int i=jaguarRomSize-1; i>=0; i--) - jaguarMainRom[0x2000 + i] = jaguarMainRom[i]; + for(int i=jaguarROMSize-1; i>=0; i--) + jaguarMainROM[0x2000 + i] = jaguarMainROM[i]; - memset(jaguarMainRom, 0xFF, 0x2000); + memset(jaguarMainROM, 0xFF, 0x2000); /* memcpy(jaguar_mainRam, jaguar_mainRom, jaguarRomSize); memset(jaguar_mainRom, 0xFF, 0x600000); memcpy(jaguar_mainRom + 0x2000, jaguar_mainRam, jaguarRomSize); @@ -184,8 +194,8 @@ Let's try setting up the illegal instruction vector for a stubulated jaguar... // Try setting the vector to say, $1000 and putting an instruction there that loops forever: // This kludge works! Yeah! - SET32(jaguarMainRam, 0x10, 0x00001000); - SET16(jaguarMainRam, 0x1000, 0x60FE); // Here: bra Here + SET32(jaguarMainRAM, 0x10, 0x00001000); + SET16(jaguarMainRAM, 0x1000, 0x60FE); // Here: bra Here } else if (strcasecmp(ext, ".abs") == 0) { @@ -237,18 +247,18 @@ Starting Address for executable = 0x00802000 Start of Text Segment = 0x00802000 Start of Data Segment = 0x00803dd0 */ - if (jaguarMainRom[0] == 0x60 && jaguarMainRom[1] == 0x1B) + if (jaguarMainROM[0] == 0x60 && jaguarMainROM[1] == 0x1B) { - uint32 loadAddress = GET32(jaguarMainRom, 0x16), //runAddress = GET32(jaguar_mainRom, 0x2A), - codeSize = GET32(jaguarMainRom, 0x02) + GET32(jaguarMainRom, 0x06); + uint32 loadAddress = GET32(jaguarMainROM, 0x16), //runAddress = GET32(jaguar_mainRom, 0x2A), + codeSize = GET32(jaguarMainROM, 0x02) + GET32(jaguarMainROM, 0x06); WriteLog("GUI: Setting up homebrew (ABS-1)... Run address: %08X, length: %08X\n", loadAddress, codeSize); if (loadAddress < 0x800000) - memcpy(jaguarMainRam + loadAddress, jaguarMainRom + 0x24, codeSize); + memcpy(jaguarMainRAM + loadAddress, jaguarMainROM + 0x24, codeSize); else { for(int i=codeSize-1; i>=0; i--) - jaguarMainRom[(loadAddress - 0x800000) + i] = jaguarMainRom[i + 0x24]; + jaguarMainROM[(loadAddress - 0x800000) + i] = jaguarMainROM[i + 0x24]; /* memcpy(jaguar_mainRam, jaguar_mainRom + 0x24, codeSize); memset(jaguar_mainRom, 0xFF, 0x600000); memcpy(jaguar_mainRom + (loadAddress - 0x800000), jaguar_mainRam, codeSize); @@ -257,18 +267,18 @@ Start of Data Segment = 0x00803dd0 jaguarRunAddress = loadAddress; } - else if (jaguarMainRom[0] == 0x01 && jaguarMainRom[1] == 0x50) + else if (jaguarMainROM[0] == 0x01 && jaguarMainROM[1] == 0x50) { - uint32 loadAddress = GET32(jaguarMainRom, 0x28), runAddress = GET32(jaguarMainRom, 0x24), - codeSize = GET32(jaguarMainRom, 0x18) + GET32(jaguarMainRom, 0x1C); + uint32 loadAddress = GET32(jaguarMainROM, 0x28), runAddress = GET32(jaguarMainROM, 0x24), + codeSize = GET32(jaguarMainROM, 0x18) + GET32(jaguarMainROM, 0x1C); WriteLog("GUI: Setting up homebrew (ABS-2)... Run address: %08X, length: %08X\n", runAddress, codeSize); if (loadAddress < 0x800000) - memcpy(jaguarMainRam + loadAddress, jaguarMainRom + 0xA8, codeSize); + memcpy(jaguarMainRAM + loadAddress, jaguarMainROM + 0xA8, codeSize); else { for(int i=codeSize-1; i>=0; i--) - jaguarMainRom[(loadAddress - 0x800000) + i] = jaguarMainRom[i + 0xA8]; + jaguarMainROM[(loadAddress - 0x800000) + i] = jaguarMainROM[i + 0xA8]; /* memcpy(jaguar_mainRam, jaguar_mainRom + 0xA8, codeSize); memset(jaguar_mainRom, 0xFF, 0x600000); memcpy(jaguar_mainRom + (loadAddress - 0x800000), jaguar_mainRam, codeSize); @@ -279,7 +289,7 @@ Start of Data Segment = 0x00803dd0 } else { - WriteLog("GUI: Couldn't find correct ABS format: %02X %02X\n", jaguarMainRom[0], jaguarMainRom[1]); + WriteLog("GUI: Couldn't find correct ABS/COF format: %02X %02X\n", jaguarMainROM[0], jaguarMainROM[1]); return false; } } @@ -288,9 +298,9 @@ Start of Data Segment = 0x00803dd0 // File extension ".JAG": Atari server file with header //NOTE: The bytes 'JAGR' should also be at position $1C... // Also, there's *always* a $601A header at position $00... - if (jaguarMainRom[0] == 0x60 && jaguarMainRom[1] == 0x1A) + if (jaguarMainROM[0] == 0x60 && jaguarMainROM[1] == 0x1A) { - uint32 loadAddress = GET32(jaguarMainRom, 0x22), runAddress = GET32(jaguarMainRom, 0x2A); + uint32 loadAddress = GET32(jaguarMainROM, 0x22), runAddress = GET32(jaguarMainROM, 0x2A); //This is not always right! Especially when converted via bin2jag1!!! //We should have access to the length of the furshlumiger file that was loaded anyway! //Now, we do! ;-) @@ -299,8 +309,8 @@ Start of Data Segment = 0x00803dd0 //jaguarRunAddress // WriteLog("Jaguar: Setting up PD ROM... Run address: %08X, length: %08X\n", runAddress, progLength); // memcpy(jaguar_mainRam + loadAddress, jaguar_mainRom + 0x2E, progLength); - WriteLog("GUI: Setting up homebrew (JAG)... Run address: %08X, length: %08X\n", runAddress, jaguarRomSize - 0x2E); - memcpy(jaguarMainRam + loadAddress, jaguarMainRom + 0x2E, jaguarRomSize - 0x2E); + WriteLog("GUI: Setting up homebrew (JAG)... Run address: %08X, length: %08X\n", runAddress, jaguarROMSize - 0x2E); + memcpy(jaguarMainRAM + loadAddress, jaguarMainROM + 0x2E, jaguarROMSize - 0x2E); // SET32(jaguar_mainRam, 4, runAddress); jaguarRunAddress = runAddress; } @@ -337,3 +347,80 @@ static int gzfilelength(gzFile gd) gzrewind(gd); return length; } + +// +// Compare extension to passed in filename. If equal, return true; otherwise false. +// +static bool CheckExtension(const char * filename, const char * ext) +{ + const char * filenameExt = strrchr(filename, '.'); // Get the file's extension (if any) + return (strcasecmp(filenameExt, ext) == 0 ? true : false); +} + +// +// Get file from .ZIP +// Returns the size of the file inside the .ZIP file that we're looking at +// +uint32 GetFileFromZIP(const char * zipFile, FileType type, uint8 * &buffer) +{ +#warning "!!! FIX !!! Should have sanity checking for ROM size to prevent buffer overflow!" + const char ftStrings[5][32] = { "Software", "EEPROM", "Label", "Box Art", "Controller Overlay" }; + ZIP * zip = openzip(0, 0, zipFile); + + if (zip == NULL) + { + WriteLog("FILE: Could not open file '%s'!\n", zipFile); + return 0; + } + + while (readzip(zip)) + { + zipent * ze = &zip->ent; + bool found = false; + + if ((type == FT_LABEL) && (CheckExtension(ze->name, ".png") || CheckExtension(ze->name, ".jpg") || CheckExtension(ze->name, ".gif"))) + { + found = true; + WriteLog("FILE: Found image file '%s'.\n", ze->name); + } + + if ((type == FT_SOFTWARE) && (CheckExtension(ze->name, ".j64") || CheckExtension(ze->name, ".rom") || CheckExtension(ze->name, ".abs") || CheckExtension(ze->name, ".cof"))) + { + found = true; + WriteLog("FILE: Found software file '%s'.\n", ze->name); + } + + if ((type == FT_EEPROM) && (CheckExtension(ze->name, ".eep") || CheckExtension(ze->name, ".eeprom"))) + { + found = true; + WriteLog("FILE: Found EEPROM file '%s'.\n", ze->name); + } + + if (found) + { + WriteLog("FILE: Uncompressing..."); + buffer = new uint8[ze->uncompressed_size]; + + if (readuncompresszip(zip, ze, (char *)buffer) == 0) + { + WriteLog("success! (%u bytes)\n", ze->uncompressed_size); + return ze->uncompressed_size; + } + else + { + WriteLog("FAILED!\n"); + delete[] buffer; + return 0; + } + } + } + + closezip(zip); + + WriteLog("FILE: Failed to find file of type %s...\n", ftStrings[type]); + // Didn't find what we're looking for... + return 0; +} + +//ParseFileType, etc. +