Playing around with reading gameboy roms, and maybe emulation
at main 3.0 kB view raw
1mod cartridge_header; 2mod enums; 3 4use crate::cartridge_header::CartridgeHeader; 5use crate::enums::DestinationCode; 6use std::fs::File; 7use std::io::Read; 8 9// https://github.com/ISSOtm/gb-bootroms/blob/2dce25910043ce2ad1d1d3691436f2c7aabbda00/src/dmg.asm#L259-L269 10// Each tile is encoded using 2 (!) bytes 11// The tiles are represented below 12// XX.. .XX. XX.. .... .... .... .... .... .... ...X X... .... 13// XXX. .XX. XX.. .... ..XX .... .... .... .... ...X X... .... 14// XXX. .XX. .... .... .XXX X... .... .... .... ...X X... .... 15// XX.X .XX. XX.X X.XX ..XX ..XX XX.. XX.X X... XXXX X..X XXX. 16// XX.X .XX. XX.X XX.X X.XX .XX. .XX. XXX. XX.X X..X X.XX ..XX 17// XX.. XXX. XX.X X..X X.XX .XXX XXX. XX.. XX.X X..X X.XX ..XX 18// XX.. XXX. XX.X X..X X.XX .XX. .... XX.. XX.X X..X X.XX ..XX 19// XX.. .XX. XX.X X..X X.XX ..XX XXX. XX.. XX.. XXXX X..X XXX. 20const NINTENDO_LOGO: [u8; 48] = [ 21 0x0CE, 0x0ED, 0x066, 0x066, 0x0CC, 0x00D, 0x000, 0x00B, 0x003, 0x073, 0x000, 0x083, 0x000, 22 0x00C, 0x000, 0x00D, 0x000, 0x008, 0x011, 0x01F, 0x088, 0x089, 0x000, 0x00E, 0x0DC, 0x0CC, 23 0x06E, 0x0E6, 0x0DD, 0x0DD, 0x0D9, 0x099, 0x0BB, 0x0BB, 0x067, 0x063, 0x06E, 0x00E, 0x0EC, 24 0x0CC, 0x0DD, 0x0DC, 0x099, 0x09F, 0x0BB, 0x0B9, 0x033, 0x03E, 25]; 26 27// const ROM_NAME: &str = "OtherLegallyObtainedRom.gb"; 28const ROM_NAME: &str = "LegallyObtainedRom.gb"; 29 30fn main() -> std::io::Result<()> { 31 let mut rom_file = File::open(ROM_NAME)?; 32 let mut rom_buffer: Vec<u8> = Vec::new(); 33 rom_file.read_to_end(&mut rom_buffer)?; 34 let cart_header = match CartridgeHeader::parse(&*rom_buffer) { 35 Ok(header) => header, 36 Err(_err) => { 37 return Err(std::io::Error::new( 38 std::io::ErrorKind::Other, 39 "Rom failed to parse", 40 )); 41 } 42 }; 43 44 let title: String = String::from_iter(cart_header.title); 45 println!("Title: {}", title); 46 let manufacturer_code = String::from_iter(cart_header.manufacturer_code); 47 println!("Manufacturer Code: {}", manufacturer_code); 48 49 match cart_header.old_licensee_code { 50 Some(code) => println!("Uses Old Licensee Code: {:#X}", code), 51 None => println!( 52 "Uses New Licensee Code: {}", 53 String::from_iter(cart_header.license_code) 54 ), 55 } 56 57 println!("CGB Flag: {:?}", cart_header.cgb_flag); 58 println!("Supports SGB: {:?}", cart_header.support_gb); 59 println!("Cartridge Type: {:?}", cart_header.cart_type); 60 println!("ROM Size: {:?}", cart_header.rom_size); 61 println!("RAM Size: {:?}", cart_header.ram_size); 62 match cart_header.destination_code { 63 DestinationCode::Japan => println!("Destination Code: Japan"), 64 DestinationCode::NotJapan => println!("Destination Code: Not Japan"), 65 } 66 println!("Version: {:?}", cart_header.version); 67 println!("Header Checksum: {:#X}", cart_header.header_checksum); 68 println!("Global Checksum: {:#X}", cart_header.global_checksum); 69 70 Ok(()) 71}