Merge branch 'master' into 'master'
Fix overdumping 16KB nrom/cnrom, snes autodetection issues Closes #18 and #17 See merge request InfiniteNesLives/INL-retro-progdump!25
This commit is contained in:
commit
3e052ced37
|
|
@ -110,6 +110,8 @@ local function dump_prgrom( file, rom_size_KB, debug )
|
||||||
|
|
||||||
--same as NROM
|
--same as NROM
|
||||||
local KB_per_read = 32
|
local KB_per_read = 32
|
||||||
|
if rom_size_KB < KB_per_read then KB_per_read = rom_size_KB end
|
||||||
|
|
||||||
local num_reads = rom_size_KB / KB_per_read
|
local num_reads = rom_size_KB / KB_per_read
|
||||||
local read_count = 0
|
local read_count = 0
|
||||||
local addr_base = 0x08 -- $8000
|
local addr_base = 0x08 -- $8000
|
||||||
|
|
|
||||||
|
|
@ -95,9 +95,10 @@ end
|
||||||
--dump the PRG ROM
|
--dump the PRG ROM
|
||||||
local function dump_prgrom( file, rom_size_KB, debug )
|
local function dump_prgrom( file, rom_size_KB, debug )
|
||||||
|
|
||||||
--PRG-ROM dump all 32KB, most of this code is overkill for NROM.
|
|
||||||
-- but follows same format as banked mappers
|
|
||||||
local KB_per_read = 32
|
local KB_per_read = 32
|
||||||
|
-- Handle 16KB nroms.
|
||||||
|
if rom_size_KB < KB_per_read then KB_per_read = rom_size_KB end
|
||||||
|
|
||||||
local num_reads = rom_size_KB / KB_per_read
|
local num_reads = rom_size_KB / KB_per_read
|
||||||
local read_count = 0
|
local read_count = 0
|
||||||
local addr_base = 0x08 -- $8000
|
local addr_base = 0x08 -- $8000
|
||||||
|
|
|
||||||
|
|
@ -22,7 +22,10 @@ local hardware_type = {
|
||||||
[0x00] = "ROM Only",
|
[0x00] = "ROM Only",
|
||||||
[0x01] = "ROM and RAM",
|
[0x01] = "ROM and RAM",
|
||||||
[0x02] = "ROM and Save RAM",
|
[0x02] = "ROM and Save RAM",
|
||||||
[0x03] = "ROM and DSP1"
|
[0x03] = "ROM and DSP1",
|
||||||
|
[0x43] = "ROM and S-DD1",
|
||||||
|
[0xF3] = "ROM and CX4",
|
||||||
|
|
||||||
}
|
}
|
||||||
--[[
|
--[[
|
||||||
TODO: Investigate these configurations.
|
TODO: Investigate these configurations.
|
||||||
|
|
@ -249,30 +252,8 @@ function hexfmt(val)
|
||||||
return string.format("0x%04X", val)
|
return string.format("0x%04X", val)
|
||||||
end
|
end
|
||||||
|
|
||||||
-- Function that determines if cartridge is lorom or hirom.
|
local function isempty(s)
|
||||||
function detect_mapping()
|
return s == nil or s == ""
|
||||||
local mapping = "unknown"
|
|
||||||
local map_mode_addr = 0xFFD5
|
|
||||||
local addr_rom_type = 0xFFD6
|
|
||||||
local addr_rom_size = 0xFFD7
|
|
||||||
local addr_sram_size = 0xFFD8
|
|
||||||
local addr_destination_code = 0xFFD9
|
|
||||||
|
|
||||||
dict.snes("SNES_SET_BANK", 0x00)
|
|
||||||
local maybe_map_mode = dict.snes("SNES_ROM_RD", map_mode_addr)
|
|
||||||
local valid_hirom_rom_type = hardware_type[dict.snes("SNES_ROM_RD", addr_rom_type)]
|
|
||||||
local valid_hirom_rom_size = rom_ubound[dict.snes("SNES_ROM_RD", addr_rom_size)]
|
|
||||||
local valid_hirom_sram_size = ram_size_tbl[dict.snes("SNES_ROM_RD", addr_sram_size)]
|
|
||||||
local valid_hirom_destination_code = destination_code[dict.snes("SNES_ROM_RD", addr_destination_code)]
|
|
||||||
local maybe_hirom = (maybe_map_mode & 1)
|
|
||||||
|
|
||||||
if (valid_hirom_rom_type and valid_hirom_rom_size and valid_hirom_sram_size and
|
|
||||||
valid_hirom_destination_code and maybe_hirom) then
|
|
||||||
mapping = hirom_name
|
|
||||||
else
|
|
||||||
mapping = lorom_name
|
|
||||||
end
|
|
||||||
return mapping
|
|
||||||
end
|
end
|
||||||
|
|
||||||
function seq_read(base_addr, n)
|
function seq_read(base_addr, n)
|
||||||
|
|
@ -339,11 +320,8 @@ function print_header(internal_header)
|
||||||
print("Checksum:\t\t" .. hexfmt(internal_header["checksum"]))
|
print("Checksum:\t\t" .. hexfmt(internal_header["checksum"]))
|
||||||
end
|
end
|
||||||
|
|
||||||
function get_header()
|
function get_header(map_adjust)
|
||||||
local map_adjust = 0 -- Might be set to 0x8000 depending on mapping.
|
local mapping = "unknown"
|
||||||
local mapping = detect_mapping()
|
|
||||||
if mapping == lorom_name then map_adjust = 0x8000 end
|
|
||||||
|
|
||||||
-- Rom Registration Addresses (15 bytes)
|
-- Rom Registration Addresses (15 bytes)
|
||||||
local addr_maker_code = 0xFFB0 - map_adjust -- 2 bytes
|
local addr_maker_code = 0xFFB0 - map_adjust -- 2 bytes
|
||||||
local addr_game_code = 0xFFB2 - map_adjust -- 4 bytes
|
local addr_game_code = 0xFFB2 - map_adjust -- 4 bytes
|
||||||
|
|
@ -379,9 +357,40 @@ function get_header()
|
||||||
return internal_header
|
return internal_header
|
||||||
end
|
end
|
||||||
|
|
||||||
|
function mappingfrommapmode(map_mode_byte)
|
||||||
|
local is_hirom = (map_mode_byte & 1) > 0
|
||||||
|
if is_hirom then return hirom_name
|
||||||
|
else return lorom_name
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
function isvalidheader(internal_header)
|
||||||
|
-- Spot check a few fields.
|
||||||
|
-- TODO: Check more/all fields, look for printable name?
|
||||||
|
local valid_rom_type = hardware_type[internal_header["rom_type"]]
|
||||||
|
local valid_rom_size = rom_ubound[internal_header["rom_size"]]
|
||||||
|
local valid_sram_size = ram_size_tbl[internal_header["sram_size"]]
|
||||||
|
local valid_destination_code = destination_code[internal_header["destination_code"]]
|
||||||
|
return valid_rom_type and valid_rom_size and valid_sram_size and valid_destination_code
|
||||||
|
end
|
||||||
|
|
||||||
function test()
|
function test()
|
||||||
local internal_header = get_header()
|
local hirom_header = get_header(0x0000)
|
||||||
print_header(internal_header)
|
local lorom_header = get_header(0x8000)
|
||||||
|
local internal_header = nil
|
||||||
|
if isvalidheader(hirom_header) then
|
||||||
|
print("Valid header found at HiROM address.")
|
||||||
|
internal_header = hirom_header
|
||||||
|
elseif isvalidheader(lorom_header) then
|
||||||
|
print("Valid header found at LoROM address.")
|
||||||
|
internal_header = lorom_header
|
||||||
|
end
|
||||||
|
if internal_header then
|
||||||
|
internal_header["mapping"] = mappingfrommapmode(internal_header["map_mode"])
|
||||||
|
else
|
||||||
|
print("Could not parse internal ROM header.")
|
||||||
|
end
|
||||||
|
return internal_header
|
||||||
end
|
end
|
||||||
|
|
||||||
-- local functions
|
-- local functions
|
||||||
|
|
@ -795,13 +804,20 @@ local function process(process_opts, console_opts)
|
||||||
dict.io("IO_RESET")
|
dict.io("IO_RESET")
|
||||||
dict.io("SNES_INIT")
|
dict.io("SNES_INIT")
|
||||||
|
|
||||||
local internal_header = get_header()
|
local internal_header = nil
|
||||||
|
|
||||||
-- Use specified mapper if provided, otherwise autodetect.
|
-- Use specified mapper if provided, otherwise autodetect.
|
||||||
local snes_mapping = console_opts["mapper"]
|
local snes_mapping = console_opts["mapper"]
|
||||||
if snes_mapping == "" then
|
if (snes_mapping == lorom_name) then
|
||||||
snes_mapping = lorom_name
|
-- LOROM typically sees the upper half (A15=1) of the first address 0b0000:1000_0000
|
||||||
if (internal_header["map_mode"] & 1) == 1 then snes_mapping = hirom_name end
|
rombank = 0x00
|
||||||
print("Mapping not provided, " .. snes_mapping .. " detected.")
|
rambank = 0x70 --LOROM maps from 0x70 to 0x7D
|
||||||
|
--some for lower half of bank only, some for both halfs...
|
||||||
|
elseif (snes_mapping == hirom_name) then
|
||||||
|
-- HIROM typically sees the last 4MByte as the first addresses = 0b1100:0000_0000
|
||||||
|
rombank = 0xC0
|
||||||
|
--rombank = 0x40 --second HiROM bank (slow)
|
||||||
|
rambank = 0x30
|
||||||
end
|
end
|
||||||
|
|
||||||
local dumpram = process_opts["dumpram"]
|
local dumpram = process_opts["dumpram"]
|
||||||
|
|
@ -809,18 +825,12 @@ local function process(process_opts, console_opts)
|
||||||
|
|
||||||
-- Use specified ram size if provided, otherwise autodetect.
|
-- Use specified ram size if provided, otherwise autodetect.
|
||||||
local ram_size = console_opts["wram_size_kb"]
|
local ram_size = console_opts["wram_size_kb"]
|
||||||
if ram_size == 0 then
|
|
||||||
ram_size = ram_size_kb_tbl[internal_header["sram_size"]]
|
|
||||||
print("RAM Size not provided, " .. ram_size_tbl[internal_header["sram_size"]] .. " detected.")
|
|
||||||
end
|
|
||||||
|
|
||||||
-- Use specified rom size if provided, otherwise autodetect.
|
-- Use specified rom size if provided, otherwise autodetect.
|
||||||
local rom_size = console_opts["rom_size_kbyte"]
|
local rom_size = console_opts["rom_size_kbyte"]
|
||||||
|
|
||||||
if rom_size == 0 then
|
|
||||||
rom_size = rom_size_kb_tbl[internal_header["rom_size"]]
|
|
||||||
print("ROM Size not provided, " .. rom_ubound[internal_header["rom_size"]] .. " detected.")
|
|
||||||
end
|
|
||||||
|
|
||||||
-- TODO: Put this in a function.
|
-- TODO: Put this in a function.
|
||||||
-- SNES memory map banking
|
-- SNES memory map banking
|
||||||
|
|
@ -834,27 +844,39 @@ local function process(process_opts, console_opts)
|
||||||
local rombank --first bank of rom byte that contains A23-16
|
local rombank --first bank of rom byte that contains A23-16
|
||||||
local rambank --first bank of ram
|
local rambank --first bank of ram
|
||||||
|
|
||||||
if (snes_mapping == lorom_name) then
|
|
||||||
-- LOROM typically sees the upper half (A15=1) of the first address 0b0000:1000_0000
|
|
||||||
rombank = 0x00
|
|
||||||
rambank = 0x70 --LOROM maps from 0x70 to 0x7D
|
|
||||||
--some for lower half of bank only, some for both halfs...
|
|
||||||
elseif (snes_mapping == hirom_name) then
|
|
||||||
-- HIROM typically sees the last 4MByte as the first addresses = 0b1100:0000_0000
|
|
||||||
rombank = 0xC0
|
|
||||||
--rombank = 0x40 --second HiROM bank (slow)
|
|
||||||
rambank = 0x30
|
|
||||||
end
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
--test cart by reading manf/prod ID
|
--test cart by reading manf/prod ID
|
||||||
if test then
|
if test then
|
||||||
|
|
||||||
print("Testing SNES board");
|
print("Testing SNES board");
|
||||||
test()
|
internal_header = test()
|
||||||
|
print_header(internal_header)
|
||||||
|
|
||||||
|
-- Autodetect any missing parameters.
|
||||||
|
if isempty(snes_mapping) then
|
||||||
|
snes_mapping = internal_header["mapping"]
|
||||||
|
print("Mapping not provided, " .. snes_mapping .. " detected.")
|
||||||
|
if (snes_mapping == lorom_name) then
|
||||||
|
-- LOROM typically sees the upper half (A15=1) of the first address 0b0000:1000_0000
|
||||||
|
rombank = 0x00
|
||||||
|
rambank = 0x70 --LOROM maps from 0x70 to 0x7D
|
||||||
|
--some for lower half of bank only, some for both halfs...
|
||||||
|
elseif (snes_mapping == hirom_name) then
|
||||||
|
-- HIROM typically sees the last 4MByte as the first addresses = 0b1100:0000_0000
|
||||||
|
rombank = 0xC0
|
||||||
|
--rombank = 0x40 --second HiROM bank (slow)
|
||||||
|
rambank = 0x30
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
if ram_size == 0 then
|
||||||
|
ram_size = ram_size_kb_tbl[internal_header["sram_size"]]
|
||||||
|
print("RAM Size not provided, " .. ram_size_tbl[internal_header["sram_size"]] .. " detected.")
|
||||||
|
end
|
||||||
|
|
||||||
|
if rom_size == 0 then
|
||||||
|
rom_size = rom_size_kb_tbl[internal_header["rom_size"]]
|
||||||
|
print("ROM Size not provided, " .. rom_ubound[internal_header["rom_size"]] .. " detected.")
|
||||||
|
end
|
||||||
|
|
||||||
--[[SNES detect if able to read flash ID's
|
--[[SNES detect if able to read flash ID's
|
||||||
if not rom_manf_id(true) then
|
if not rom_manf_id(true) then
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue