From 223007187b91c7c79ae46f81acdfd3dcb69292ec Mon Sep 17 00:00:00 2001 From: Paul Black ASUS win7 Date: Sat, 17 Mar 2018 21:56:24 -0500 Subject: [PATCH] Have BNROM, and action53 working in PLCC and TSSOP. Also added swim reading of stack bottom for CICOp signature. Starting to add scripts for different mappers. Need to clean things up quite a bit as everything was a bit of a hack just so I could start building lizards and A53. Need to add back NROM, and add UNROM as well. Need to have program find bank table for itself both in the program and in a cartridge. Having problems with SWIM on new discrete NES boards for some reason. Some boards are flakey and I march right in and start writting to config bytes which will brick the device if communications are failing (and there's no reset pin...) as is with the stm8s001 --- firmware/source/dump.c | 16 ++- firmware/source/flash.c | 138 ++++++++++++++++++-- host/scripts/app/swim.lua | 31 +++++ host/scripts/inlretro.lua | 40 ++++-- host/scripts/nes/action53.lua | 189 ++++++++++++++++++++++++++++ host/scripts/nes/action53_tsop.lua | 195 +++++++++++++++++++++++++++++ host/scripts/nes/bnrom.lua | 6 +- 7 files changed, 592 insertions(+), 23 deletions(-) create mode 100644 host/scripts/nes/action53.lua create mode 100644 host/scripts/nes/action53_tsop.lua diff --git a/firmware/source/dump.c b/firmware/source/dump.c index eed0f37..42e1792 100644 --- a/firmware/source/dump.c +++ b/firmware/source/dump.c @@ -20,12 +20,24 @@ uint8_t dump_buff( buffer *buff ) { case PRGROM: addrH |= 0x80; //$8000 if (buff->mapper == BxROM) { - bank = (buff->page_num)>>7; //write bank value to bank table - //page_num shift by 6 bits A15 >> A8(0) + //page_num shift by 7 bits A15 >> A8(0) + bank = (buff->page_num)>>7; //Lizard bank table @ FF94 nes_cpu_wr( (0xFF94+bank), bank ); } + if (buff->mapper == A53) { + //write bank value to bank table + //page_num shift by 7 bits A15 >> A8(0) + bank = (buff->page_num)>>7; + //Setup as CNROM, then scroll through outer banks. + //cpu_wr(0x5000, 0x80); //reg select mode + // xxSSPPMM SS-size: 0-32KB, PP-prg mode: 0,1 32KB, MM-mirror + //cpu_wr(0x8000, 0b00000000); //reg value 256KB inner, 32KB banks + nes_cpu_wr(0x5000, 0x81); //outer reg select mode + nes_cpu_wr(0x8000, bank); //outer bank + nes_cpu_wr(0x5000, 0x00); //chr reg select act like CNROM + } buff->cur_byte = nes_cpu_page_rd_poll( buff->data, addrH, buff->id, //id contains MSb of page when <256B buffer buff->last_idx, ~FALSE ); diff --git a/firmware/source/flash.c b/firmware/source/flash.c index 35f267f..bb89bd0 100644 --- a/firmware/source/flash.c +++ b/firmware/source/flash.c @@ -7,6 +7,7 @@ uint8_t write_page( uint8_t bank, uint8_t addrH, buffer *buff, write_funcptr wr_ uint8_t n = buff->cur_byte; uint8_t read; // extern operation_info *oper_info; +// while ( cur <= buff->last_idx ) { //write unlock sequence @@ -26,11 +27,14 @@ uint8_t write_page( uint8_t bank, uint8_t addrH, buffer *buff, write_funcptr wr_ // 4KB banking A11-0 NES ctl, A12+ mapper ctl "bank" ezNSF //addrH_dmask = 0b0000 1111 //page2bankshft = A11->A8 = 4 shifts - wr_func( 0x5555, 0xAA ); + //wr_func( 0x5555, 0xAA ); + wr_func( 0xD555, 0xAA ); // wr_func( oper_info->unlock1_AH, oper_info->unlock1_AL, oper_info->unlock1_data ); - wr_func( 0x2AAA, 0x55 ); + //wr_func( 0x2AAA, 0x55 ); + wr_func( 0xAAAA, 0x55 ); // wr_func( oper_info->unlock2_AH, oper_info->unlock2_AL, oper_info->unlock2_data ); - wr_func( 0x5555, 0xA0 ); + //wr_func( 0x5555, 0xA0 ); + wr_func( 0xD555, 0xA0 ); // wr_func( oper_info->command_AH, oper_info->command_AL, oper_info->command1_data ); wr_func( ((addrH<<8)| n), buff->data[n] ); @@ -42,15 +46,18 @@ uint8_t write_page( uint8_t bank, uint8_t addrH, buffer *buff, write_funcptr wr_ //retry if write failed //this helped but still seeing similar fails to dumps - if (read == buff->data[n]) { - n++; - cur++; - LED_IP_PU(); - LED_LO(); - } else { - LED_OP(); - LED_HI(); - } + // if (read == buff->data[n]) { + n++; + cur++; + // LED_IP_PU(); + // LED_LO(); + // } else { + // nes_cpu_wr(0x5000, 0x81); //outer reg select mode + // nes_cpu_wr(0x8000, bank); //outer bank + // nes_cpu_wr(0x5000, 0x00); //chr reg select act like CNROM + // LED_OP(); + // LED_HI(); + // } } @@ -60,6 +67,90 @@ uint8_t write_page( uint8_t bank, uint8_t addrH, buffer *buff, write_funcptr wr_ } +uint8_t write_page_a53( uint8_t bank, uint8_t addrH, buffer *buff, write_funcptr wr_func, read_funcptr rd_func ) +{ + uint16_t cur = buff->cur_byte; + uint8_t n = buff->cur_byte; + uint8_t read; +// extern operation_info *oper_info; +// + + //enter unlock bypass mode + wr_func( 0x8AAA, 0xAA ); + wr_func( 0x8555, 0x55 ); + wr_func( 0x8AAA, 0x20 ); + + while ( cur <= buff->last_idx ) { + //write unlock sequence + //need to make address and unlock data variable + //best for host to communcate these values + //actual value is part mapper dependent and part flash dependent + //mapper controlled address bits dictate where split is + //32KB banking A14-0 NES ctl, A15+ mapper ctl "bank" NROM, BNROM, ANROM + //addrH_dmask = 0b0111 1111 directly addressable addrH bits + //page2bankshft = A14->A8 = 7 shifts (equal to number of set bits in addrH_mask + //16KB banking A13-0 NES ctl, A14+ mapper ctl "bank" UxROM, MMC1 + //addrH_dmask = 0b0011 1111 + //page2bankshft = A13->A8 = 6 shifts + // 8KB banking A12-0 NES ctl, A13+ mapper ctl "bank" MMC3, FME7 + //addrH_dmask = 0b0001 1111 + //page2bankshft = A12->A8 = 5 shifts + // 4KB banking A11-0 NES ctl, A12+ mapper ctl "bank" ezNSF + //addrH_dmask = 0b0000 1111 + //page2bankshft = A11->A8 = 4 shifts + //wr_func( 0x5555, 0xAA ); +// wr_func( 0x8AAA, 0xAA ); +//// wr_func( oper_info->unlock1_AH, oper_info->unlock1_AL, oper_info->unlock1_data ); +// //wr_func( 0x2AAA, 0x55 ); +// wr_func( 0x8555, 0x55 ); +//// wr_func( oper_info->unlock2_AH, oper_info->unlock2_AL, oper_info->unlock2_data ); +// //wr_func( 0x5555, 0xA0 ); +// wr_func( 0x8AAA, 0xA0 ); +//// wr_func( oper_info->command_AH, oper_info->command_AL, oper_info->command1_data ); +// wr_func( ((addrH<<8)| n), buff->data[n] ); + + + // curaddresswrite( 0xA0 ); //gained ~3KBps (59.13KBps) inl6 with v3.0 proto + wr_func( ((addrH<<8)| n), 0xA0 ); + + wr_func( ((addrH<<8)| n), buff->data[n] ); + + do { + usbPoll(); + read = rd_func((addrH<<8)|n); + + } while( read != rd_func((addrH<<8)|n) ); + + //retry if write failed + //this helped but still seeing similar fails to dumps +// if (read == buff->data[n]) { + n++; + cur++; +// LED_IP_PU(); +// LED_LO(); +// } else { +// nes_cpu_wr(0x5000, 0x81); //outer reg select mode +// nes_cpu_wr(0x8000, bank); //outer bank +// nes_cpu_wr(0x5000, 0x00); //chr reg select act like CNROM +// LED_OP(); +// LED_HI(); +// } + + } + + buff->cur_byte = n; + + //exit unlock bypass mode + wr_func( 0x8000, 0x90 ); + wr_func( 0x8000, 0x00 ); + //reset the flash chip, supposed to exit too + wr_func( 0x8000, 0xF0 ); + + + return SUCCESS; + +} + uint8_t write_page_chr( uint8_t bank, uint8_t addrH, buffer *buff, write_funcptr wr_func, read_funcptr rd_func ) { uint16_t cur = buff->cur_byte; @@ -364,7 +455,28 @@ uint8_t flash_buff( buffer *buff ) { //Lizard banktable location nes_cpu_wr( (0xFF94+bank), bank ); } - write_page( 0, (0x80 | addrH), buff, discrete_exp0_prgrom_wr, nes_cpu_rd ); + if (buff->mapper == A53) { + //write bank value to bank table + //page_num shift by 7 bits A15 >> A8(0) + bank = (buff->page_num)>>7; + //Setup as CNROM, then scroll through outer banks. + //cpu_wr(0x5000, 0x80); //reg select mode + // xxSSPPMM SS-size: 0-32KB, PP-prg mode: 0,1 32KB, MM-mirror + //cpu_wr(0x8000, 0b00000000); //reg value 256KB inner, 32KB banks + nes_cpu_wr(0x5000, 0x81); //outer reg select mode + nes_cpu_wr(0x8000, bank); //outer bank + nes_cpu_wr(0x5000, 0x54); //chr reg select act like CNROM & enable flash writes + + //need to use standard CPU writes + //write_page( 0, (0x80 | addrH), buff, nes_cpu_wr, nes_cpu_rd ); + //break; + } + //discrete: + //write_page( 0, (0x80 | addrH), buff, discrete_exp0_prgrom_wr, nes_cpu_rd ); + //WORKS PLCC Action53: + //write_page( bank, (0x80 | addrH), buff, nes_cpu_wr, nes_cpu_rd ); + //TSSOP-28 action53: + write_page_a53( bank, (0x80 | addrH), buff, nes_cpu_wr, nes_cpu_rd ); break; case CHRROM: //$0000 write_page_chr( 0, addrH, buff, nes_ppu_wr, nes_ppu_rd ); diff --git a/host/scripts/app/swim.lua b/host/scripts/app/swim.lua index 7f2b427..cdee43d 100644 --- a/host/scripts/app/swim.lua +++ b/host/scripts/app/swim.lua @@ -312,6 +312,36 @@ local function swim_test() end +local function read_stack() + + --STM8 stack starts at $0200 which is where the CIC version + --and other special data is placed starting with v2.0 + local stack_start = 0x0200 + local last_char = 73 + local ack + local data = {} + + --read + for i = 0, last_char do + ack, data[i+1] = rotf(stack_start+i, true, false) + end + + print("\n") + + local j = 1 + while data[j] do + io.write(string.char(data[j])) + j = j+1 + end + print("\n") + +-- print("rotf :", string.format("%X %X", dict.swim("ROTF_HS", 0x0000))) + + +end + + + local function start( debug ) --dict.io("IO_RESET") @@ -570,6 +600,7 @@ swim.printCSR = printCSR swim.wotf = wotf swim.rotf = rotf swim.swim_test = swim_test +swim.read_stack = read_stack swim.snes_v3_prgm = snes_v3_prgm swim.snes_v3_play = snes_v3_play swim.stop_and_reset = stop_and_reset diff --git a/host/scripts/inlretro.lua b/host/scripts/inlretro.lua index 82ceec1..2332052 100644 --- a/host/scripts/inlretro.lua +++ b/host/scripts/inlretro.lua @@ -23,6 +23,8 @@ function main () --cart/mapper specific scripts --local curcart = require "scripts.nes.nrom" local curcart = require "scripts.nes.bnrom" + --local curcart = require "scripts.nes.action53" + --local curcart = require "scripts.nes.action53_tsop" local rv -- rv = dict.pinport( "DATA_SET", 0xAA ) @@ -55,7 +57,7 @@ function main () dict.io("IO_RESET") dict.io("NES_INIT") - ---[[ + --[[ --NES detect mirroring to gain mapper info nes.detect_mapper_mirroring(true) --NES detect memories to gain more mapper/board info @@ -88,11 +90,12 @@ function main () print("start swim") dict.io("SWIM_INIT", "SWIM_ON_A0") + ----[[ if swim.start(true) then --SWIM is now established and running at HIGH SPEED snes_swimcart = false --don't want to use SWIM pin to control flash /OE, use SNES RESET (EXP0) instead - -- swim.swim_test() + swim.swim_test() --swim.write_optn_bytes( true, true ) -- enable ROP, debug @@ -101,10 +104,11 @@ function main () swim.disable_ROP_erase(true) --open CIC file - --local cic_file = assert(io.open("stm8_8KB_zero.bin", "rb")) + local cic_file = assert(io.open("stm8_8KB_zero.bin", "rb")) --local cic_file = assert(io.open("stm8_8KB_0xff.bin", "rb")) --local cic_file = assert(io.open("stm8_8KB_testpattern.bin", "rb")) - local cic_file = assert(io.open("NESCIC.bin", "rb")) + --local cic_file = assert(io.open("NESCIC.bin", "rb")) + --local cic_file = assert(io.open("LIZv1.bin", "rb")) --write CIC file swim.write_flash( cic_file ) @@ -113,7 +117,7 @@ function main () assert(cic_file:close()) --set ROP & AFR0 - swim.write_optn_bytes( false, true ) -- ROP not set, debug set + swim.write_optn_bytes( true, true ) -- ROP not set, debug set -- reset STM8 CIC and end SWIM comms to it can execute what we just flashed swim.stop_and_reset() @@ -124,6 +128,23 @@ function main () print("done flashing STM8 on A0") dict.io("IO_RESET") + + --]] + + ---[[ + --test reading back CIC version + dict.io("SWIM_INIT", "SWIM_ON_A0") + if swim.start(true) then + + swim.read_stack() + + else + print("ERROR trying to read back CIC signature stack data") + end + + print("done flashing STM8 on A0") + + dict.io("IO_RESET") --]] @@ -132,8 +153,13 @@ function main () --perform desired operation --CART and programmer should be in a RESET condition upon calling the specific script --curcart.process( true, true, true, true, "ignore/dump.bin", "ignore/ddug2.bin", "ignore/verifyout.bin") - curcart.process( false, true, true, true, "ignore/dump.bin", "ignore/lizard_v1.bin", "ignore/verifyout.bin") - --curcart.process( true, false, false, false, "ignore/dump.bin", "ignore/lizard_v1.bin", "ignore/verifyout.bin") + --curcart.process( false, true, true, false, "ignore/dump.bin", "ignore/lizard_v1.bin", "ignore/verifyout.bin") + --curcart.process( false, true, true, false, "ignore/dump.bin", "ignore/liz/liz.bin", "ignore/verifyout.bin") + curcart.process( false, false, true, true, false, "ignore/dump.bin", "ignore/lizard_v1.bin", "ignore/verifyout.bin") + --curcart.process( true, true, true, true, true, "ignore/dump.bin", "ignore/da53v2.prg", "ignore/verifyout.bin") + --curcart.process( true, true, true, true, true, "ignore/dump.bin", "ignore/da53v2_x2.prg", "ignore/verifyout.bin") + --curcart.process( true, true, true, true, true, "ignore/dump.bin", "ignore/a53part2.prg", "ignore/verifyout.bin") + --curcart.process( true, true, true, true, true, "ignore/dump.bin", "ignore/a53vol3.prg", "ignore/verifyout.bin") --[[ diff --git a/host/scripts/nes/action53.lua b/host/scripts/nes/action53.lua new file mode 100644 index 0000000..28f6cf6 --- /dev/null +++ b/host/scripts/nes/action53.lua @@ -0,0 +1,189 @@ + +-- create the module's table +local action53 = {} + +-- import required modules +local dict = require "scripts.app.dict" +local dump = require "scripts.app.dump" +local flash = require "scripts.app.flash" + +-- file constants + +-- local functions + +--local function wr_flash_byte(addr, value, debug) + +--base is the actual NES CPU address, not the rom offset (ie $FFF0, not $7FF0) +--local function wr_bank_table(base, entries) +--Action53 not susceptible to bus conflicts, no banktable needed + + + +--initialize mapper for dump/flash routines +local function init_mapper( debug ) + + --//Setup as CNROM, then scroll through outer banks. + --cpu_wr(0x5000, 0x80); //reg select mode + dict.nes("NES_CPU_WR", 0x5000, 0x80) + + --// xxSSPPMM SS-size: 0-32KB, PP-prg mode: 0,1 32KB, MM-mirror + --cpu_wr(0x8000, 0b00000000); //reg value 256KB inner, 32KB banks + dict.nes("NES_CPU_WR", 0x8000, 0x00) + --cpu_wr(0x5000, 0x81); //outer reg select mode + dict.nes("NES_CPU_WR", 0x5000, 0x81) + --cpu_wr(0x8000, 0x00); //first 32KB bank + dict.nes("NES_CPU_WR", 0x8000, 0x00) + -- + --cpu_wr(0x5000, 0x01); //inner prg reg select + dict.nes("NES_CPU_WR", 0x5000, 0x01) + --cpu_wr(0x8000, 0x00); //controls nothing in this size + dict.nes("NES_CPU_WR", 0x8000, 0x00) + --cpu_wr(0x5000, 0x00); //chr reg select + dict.nes("NES_CPU_WR", 0x5000, 0x00) + --cpu_wr(0x8000, 0x00); //first chr bank + dict.nes("NES_CPU_WR", 0x8000, 0x00) + --selecting CNROM means that mapper writes to $8000-FFFF will only change the CHR-RAM bank which + --doesn't affect anything we're concerned about + +end + + +--read PRG-ROM flash ID +local function prgrom_manf_id( debug ) + + init_mapper() + + if debug then print("reading PRG-ROM manf ID") end + --A0-A14 are all directly addressable in CNROM mode + --and mapper writes don't affect PRG banking + dict.nes("NES_CPU_WR", 0xD555, 0xAA) + dict.nes("NES_CPU_WR", 0xAAAA, 0x55) + dict.nes("NES_CPU_WR", 0xD555, 0x90) + rv = dict.nes("NES_CPU_RD", 0x8000) + if debug then print("attempted read PRG-ROM manf ID:", string.format("%X", rv)) end + rv = dict.nes("NES_CPU_RD", 0x8001) + if debug then print("attempted read PRG-ROM prod ID:", string.format("%X", rv)) end + + --exit software + dict.nes("NES_CPU_WR", 0x8000, 0xF0) + +end + + +--Cart should be in reset state upon calling this function +--this function processes all user requests for this specific board/mapper +local function process( test, read, erase, program, verify, dumpfile, flashfile, verifyfile) + + local rv = nil + local file + + +--initialize device i/o for NES + dict.io("IO_RESET") + dict.io("NES_INIT") + + +--test cart by reading manf/prod ID + if test then + prgrom_manf_id(true) + end + + +--dump the cart to dumpfile + if read then + --initialize the mapper for dumping + init_mapper(debug) + + file = assert(io.open(dumpfile, "wb")) + + --TODO find bank table to avoid bus conflicts! + --dump cart into file + dump.dumptofile( file, 512, "A53", "PRGROM", true ) + + --close file + assert(file:close()) + end + +--erase the cart + if erase then + + --initialize the mapper for erasing + init_mapper(debug) + + print("\nerasing action53"); + + print("erasing PRG-ROM"); + --A0-A14 are all directly addressable in CNROM mode + --and mapper writes don't affect PRG banking + dict.nes("NES_CPU_WR", 0xD555, 0xAA) + dict.nes("NES_CPU_WR", 0xAAAA, 0x55) + dict.nes("NES_CPU_WR", 0xD555, 0x80) + dict.nes("NES_CPU_WR", 0xD555, 0xAA) + dict.nes("NES_CPU_WR", 0xAAAA, 0x55) + dict.nes("NES_CPU_WR", 0xD555, 0x10) + rv = dict.nes("NES_CPU_RD", 0x8000) + + local i = 0 + + --TODO create some function to pass the read value + --that's smart enough to figure out if the board is actually erasing or not + while ( rv ~= 0xFF ) do + rv = dict.nes("NES_CPU_RD", 0x8000) + i = i + 1 + end + print(i, "naks, done erasing prg."); + + end + + +--program flashfile to the cart + if program then + + --initialize the mapper for dumping + init_mapper(debug) + + --open file + file = assert(io.open(flashfile, "rb")) + --determine if auto-doubling, deinterleaving, etc, + --needs done to make board compatible with rom + + --not susceptible to bus conflicts + + --flash cart + flash.write_file( file, 512, "A53", "PRGROM", true ) + --close file + assert(file:close()) + + end + +--verify flashfile is on the cart + if verify then + --for now let's just dump the file and verify manually + + --initialize the mapper for dumping + init_mapper(debug) + + file = assert(io.open(verifyfile, "wb")) + + --dump cart into file + dump.dumptofile( file, 512, "A53", "PRGROM", true ) + + --close file + assert(file:close()) + end + + dict.io("IO_RESET") +end + + +-- global variables so other modules can use them + + +-- call functions desired to run when script is called/imported + + +-- functions other modules are able to call +action53.process = process + +-- return the module's table +return action53 diff --git a/host/scripts/nes/action53_tsop.lua b/host/scripts/nes/action53_tsop.lua new file mode 100644 index 0000000..ded1e76 --- /dev/null +++ b/host/scripts/nes/action53_tsop.lua @@ -0,0 +1,195 @@ + +-- create the module's table +local action53_tsop = {} + +-- import required modules +local dict = require "scripts.app.dict" +local dump = require "scripts.app.dump" +local flash = require "scripts.app.flash" + +-- file constants + +-- local functions + +--local function wr_flash_byte(addr, value, debug) + +--base is the actual NES CPU address, not the rom offset (ie $FFF0, not $7FF0) +--local function wr_bank_table(base, entries) +--Action53 not susceptible to bus conflicts, no banktable needed + + + +--initialize mapper for dump/flash routines +local function init_mapper( debug ) + + --//Setup as CNROM, then scroll through outer banks. + --cpu_wr(0x5000, 0x80); //reg select mode + dict.nes("NES_CPU_WR", 0x5000, 0x80) + + --// xxSSPPMM SS-size: 0-32KB, PP-prg mode: 0,1 32KB, MM-mirror + --cpu_wr(0x8000, 0b00000000); //reg value 256KB inner, 32KB banks + dict.nes("NES_CPU_WR", 0x8000, 0x00) + --cpu_wr(0x5000, 0x81); //outer reg select mode + dict.nes("NES_CPU_WR", 0x5000, 0x81) + --cpu_wr(0x8000, 0x00); //first 32KB bank + dict.nes("NES_CPU_WR", 0x8000, 0x00) + -- + --cpu_wr(0x5000, 0x01); //inner prg reg select + dict.nes("NES_CPU_WR", 0x5000, 0x01) + --cpu_wr(0x8000, 0x00); //controls nothing in this size + dict.nes("NES_CPU_WR", 0x8000, 0x00) + --cpu_wr(0x5000, 0x00); //chr reg select + dict.nes("NES_CPU_WR", 0x5000, 0x00) + --cpu_wr(0x8000, 0x00); //first chr bank + dict.nes("NES_CPU_WR", 0x8000, 0x00) + --selecting CNROM means that mapper writes to $8000-FFFF will only change the CHR-RAM bank which + --doesn't affect anything we're concerned about + + --enable flash writes $5000 set to 0b0 101 010 0 + dict.nes("NES_CPU_WR", 0x5000, 0x54) + +end + + +--read PRG-ROM flash ID +local function prgrom_manf_id( debug ) + + init_mapper() + + if debug then print("reading PRG-ROM manf ID") end + --A0-A14 are all directly addressable in CNROM mode + --and mapper writes don't affect PRG banking + dict.nes("NES_CPU_WR", 0x8AAA, 0xAA) + dict.nes("NES_CPU_WR", 0x8555, 0x55) + dict.nes("NES_CPU_WR", 0x8AAA, 0x90) + rv = dict.nes("NES_CPU_RD", 0x8000) + if debug then print("attempted read PRG-ROM manf ID:", string.format("%X", rv)) end --0x01 + rv = dict.nes("NES_CPU_RD", 0x8002) + if debug then print("attempted read PRG-ROM prod ID:", string.format("%X", rv)) end --0xDA(top), 0x5B(bot) +-- rv = dict.nes("NES_CPU_RD", 0x801C) +-- if debug then print("attempted read PRG-ROM density ID:", string.format("%X", rv)) end +-- rv = dict.nes("NES_CPU_RD", 0x801E) +-- if debug then print("attempted read PRG-ROM bootsect ID:", string.format("%X", rv)) end + + --exit software + dict.nes("NES_CPU_WR", 0x8000, 0xF0) + +end + + +--Cart should be in reset state upon calling this function +--this function processes all user requests for this specific board/mapper +local function process( test, read, erase, program, verify, dumpfile, flashfile, verifyfile) + + local rv = nil + local file + + +--initialize device i/o for NES + dict.io("IO_RESET") + dict.io("NES_INIT") + +--test cart by reading manf/prod ID + if test then + prgrom_manf_id(true) + end + +--dump the cart to dumpfile + if read then + --initialize the mapper for dumping + init_mapper(debug) + + file = assert(io.open(dumpfile, "wb")) + + --TODO find bank table to avoid bus conflicts! + --dump cart into file + dump.dumptofile( file, 1024, "A53", "PRGROM", true ) + + --close file + assert(file:close()) + end + +--erase the cart + if erase then + + --initialize the mapper for erasing + init_mapper(debug) + + print("\nerasing action53 tsop takes ~30sec"); + + print("erasing PRG-ROM"); + --A0-A14 are all directly addressable in CNROM mode + --only A0-A11 are required to be valid for tsop-48 + --and mapper writes don't affect PRG banking + dict.nes("NES_CPU_WR", 0x8AAA, 0xAA) + dict.nes("NES_CPU_WR", 0x8555, 0x55) + dict.nes("NES_CPU_WR", 0x8AAA, 0x80) + dict.nes("NES_CPU_WR", 0x8AAA, 0xAA) + dict.nes("NES_CPU_WR", 0x8555, 0x55) + dict.nes("NES_CPU_WR", 0x8AAA, 0x10) + rv = dict.nes("NES_CPU_RD", 0x8000) + + local i = 0 + + --TODO create some function to pass the read value + --that's smart enough to figure out if the board is actually erasing or not + while ( rv ~= 0xFF ) do + rv = dict.nes("NES_CPU_RD", 0x8000) + i = i + 1 + end + print(i, "naks, done erasing prg."); + + end + + +--program flashfile to the cart + if program then + + --initialize the mapper for dumping + init_mapper(debug) + + --open file + file = assert(io.open(flashfile, "rb")) + --determine if auto-doubling, deinterleaving, etc, + --needs done to make board compatible with rom + + --not susceptible to bus conflicts + + --flash cart + flash.write_file( file, 1024, "A53", "PRGROM", true ) + --close file + assert(file:close()) + + end + +--verify flashfile is on the cart + if verify then + --for now let's just dump the file and verify manually + + --initialize the mapper for dumping + init_mapper(debug) + + file = assert(io.open(verifyfile, "wb")) + + --dump cart into file + dump.dumptofile( file, 1024, "A53", "PRGROM", true ) + + --close file + assert(file:close()) + end + + dict.io("IO_RESET") +end + + +-- global variables so other modules can use them + + +-- call functions desired to run when script is called/imported + + +-- functions other modules are able to call +action53_tsop.process = process + +-- return the module's table +return action53_tsop diff --git a/host/scripts/nes/bnrom.lua b/host/scripts/nes/bnrom.lua index 192227c..018cb9d 100644 --- a/host/scripts/nes/bnrom.lua +++ b/host/scripts/nes/bnrom.lua @@ -66,7 +66,7 @@ end --Cart should be in reset state upon calling this function --this function processes all user requests for this specific board/mapper -local function process( read, erase, program, verify, dumpfile, flashfile, verifyfile) +local function process( test, read, erase, program, verify, dumpfile, flashfile, verifyfile) local rv = nil local file @@ -75,6 +75,10 @@ local function process( read, erase, program, verify, dumpfile, flashfile, verif dict.io("IO_RESET") dict.io("NES_INIT") +--test cart by reading manf/prod ID + if test then +-- prgrom_manf_id(true) + end --dump the cart to dumpfile if read then