In principle it works, the routine and table do everything they're supposed to. However, at some point (it differs, I have not yet found on what it depends) during the routine, the SNES gets an IRQ and some instructions later goes into a BRK-loop and the screen only shows corruption.
Here is what my added routine looks like:
Code:
arch snes.cpu; lorom\t// Load settings for SNES/WDC65816 in LoROM mode
incsrc dte_table.asm
org $00b4a2\t\t// Jump from old routine to dte subroutine
\tjsl check_codes_cont
\tnop\t\t\t// the JSL instruction is 3 bytes shorter than the old code, so we're padding here
\tnop
\tnop
org $01ecb0
check_codes_cont:\t// Continuation of the old code
\tcmp #$c3
\tbne +
\t\tjml $00b501
+;\tjsr dte_routine::init\t// Go go go!
\trtl
\t
namespace dte_routine
init:
\tcmp #$40\t\t// DTE charcodes start here
\tbcc end
\tclc
\tcmp #$80\t\t// DTE charcodes end here
\tbcs end
runcheck:
\tstx $1ffd\t\t// Backup X
\tsep #$30\t\t// Make ACL + registers 8bit
\tsec
\tsbc #$40\t\t// Start charcodes from 0, not 40
\tclc
\tldx $1fff\t\t// Load DTE flagbyte from RAM
\tcpx #$9d\t\t// If this is set, we're at the 2nd char
\tbeq secondchar
firstchar:
\tldx #$9d\t\t// set flag to true
\tdec $0772\t// decrement load_idx
\tasl \t\t\t// dte_num = charcode*2
\tjmp base
secondchar:
\tasl \t\t\t// dte_num = charcode*2
\tclc
\tadc #$01\t\t// select 2nd char of pair
\tldx #$00\t\t// set flag to false
base:
\tstx $1fff\t\t// store flag in RAM
\ttax
\tlda global::dte_table,x\t// load character from DTE table
\trep #$10\t\t// Make registers 16bit
\tldx $1ffd\t\t// Restore X
end:
\trts
incsrc dte_table.asm
org $00b4a2\t\t// Jump from old routine to dte subroutine
\tjsl check_codes_cont
\tnop\t\t\t// the JSL instruction is 3 bytes shorter than the old code, so we're padding here
\tnop
\tnop
org $01ecb0
check_codes_cont:\t// Continuation of the old code
\tcmp #$c3
\tbne +
\t\tjml $00b501
+;\tjsr dte_routine::init\t// Go go go!
\trtl
\t
namespace dte_routine
init:
\tcmp #$40\t\t// DTE charcodes start here
\tbcc end
\tclc
\tcmp #$80\t\t// DTE charcodes end here
\tbcs end
runcheck:
\tstx $1ffd\t\t// Backup X
\tsep #$30\t\t// Make ACL + registers 8bit
\tsec
\tsbc #$40\t\t// Start charcodes from 0, not 40
\tclc
\tldx $1fff\t\t// Load DTE flagbyte from RAM
\tcpx #$9d\t\t// If this is set, we're at the 2nd char
\tbeq secondchar
firstchar:
\tldx #$9d\t\t// set flag to true
\tdec $0772\t// decrement load_idx
\tasl \t\t\t// dte_num = charcode*2
\tjmp base
secondchar:
\tasl \t\t\t// dte_num = charcode*2
\tclc
\tadc #$01\t\t// select 2nd char of pair
\tldx #$00\t\t// set flag to false
base:
\tstx $1fff\t\t// store flag in RAM
\ttax
\tlda global::dte_table,x\t// load character from DTE table
\trep #$10\t\t// Make registers 16bit
\tldx $1ffd\t\t// Restore X
end:
\trts
Here is what an example of a crash looks like in the trace:
Code:
$00/B4A2 22 B0 EC 01 JSL $01ECB0[$01:ECB0] A:0043 X:0BAE Y:0032 P:envMxdizC
$01/ECB0 C9 C3 CMP #$C3 A:0043 X:0BAE Y:0032 P:envMxdizC
$01/ECB2 D0 04 BNE $04 [$ECB8] A:0043 X:0BAE Y:0032 P:eNvMxdizc
$01/ECB8 20 BC EC JSR $ECBC [$01:ECBC] A:0043 X:0BAE Y:0032 P:eNvMxdizc
$01/ECBC C9 40 CMP #$40 A:0043 X:0BAE Y:0032 P:eNvMxdizc
$01/ECBE 90 31 BCC $31 [$ECF1] A:0043 X:0BAE Y:0032 P:envMxdizC
$01/ECC0 18 CLC A:0043 X:0BAE Y:0032 P:envMxdizC
$01/ECC1 C9 80 CMP #$80 A:0043 X:0BAE Y:0032 P:envMxdizc
$01/ECC3 B0 2C BCS $2C [$ECF1] A:0043 X:0BAE Y:0032 P:eNvMxdizc
$01/ECC5 8E FD 1F STX $1FFD [$00:1FFD] A:0043 X:0BAE Y:0032 P:eNvMxdizc
$01/ECC8 E2 30 SEP #$30 A:0043 X:0BAE Y:0032 P:eNvMxdizc
$01/ECCA 38 SEC A:0043 X:00AE Y:0032 P:eNvMXdizc
$01/ECCB E9 40 SBC #$40 A:0043 X:00AE Y:0032 P:eNvMXdizC
$01/ECCD 18 CLC A:0003 X:00AE Y:0032 P:envMXdizC
$01/ECCE AE FF 1F LDX $1FFF [$00:1FFF] A:0003 X:00AE Y:0032 P:envMXdizc
*** IRQ
$00/0204 5C 80 94 00 JMP $009480[$00:9480] A:0003 X:0000 Y:0032 P:envMXdIZc
$00/9480 08 PHP A:0003 X:0000 Y:0032 P:envMXdIZc
$00/9481 C2 20 REP #$20 A:0003 X:0000 Y:0032 P:envMXdIZc
$00/9483 48 PHA A:0003 X:0000 Y:0032 P:envmXdIZc
$00/9484 DA PHX A:0003 X:0000 Y:0032 P:envmXdIZc
$00/9485 5A PHY A:0003 X:0000 Y:0032 P:envmXdIZc
$00/9486 8B PHB A:0003 X:0000 Y:0032 P:envmXdIZc
$00/9487 0B PHD A:0003 X:0000 Y:0032 P:envmXdIZc
$00/9488 A9 00 00 LDA #$0000 A:0003 X:0000 Y:0032 P:envmXdIZc
$00/948B E2 20 SEP #$20 A:0000 X:0000 Y:0032 P:envmXdIZc
$00/948D A2 00 LDX #$00 A:0000 X:0000 Y:0032 P:envMXdIZc
$00/948F 06 DA ASL $DA [$00:06DA] A:0000 X:0000 Y:0032 P:envMXdIZc
$00/9491 2B PLD A:0000 X:0000 Y:0032 P:envMXdIZc
$00/9492 A9 00 LDA #$00 A:0000 X:0000 Y:0032 P:envMXdIzc
$00/9494 48 PHA A:0000 X:0000 Y:0032 P:envMXdIZc
$00/9495 AB PLB A:0000 X:0000 Y:0032 P:envMXdIZc
$00/9496 AD 11 42 LDA $4211 [$00:4211] A:0000 X:0000 Y:0032 P:envMXdIZc
$00/9499 A5 D9 LDA $D9 [$00:06D9] A:00C2 X:0000 Y:0032 P:eNvMXdIzc
$00/949B F0 06 BEQ $06 [$94A3] A:0000 X:0000 Y:0032 P:envMXdIZc
$00/94A3 A5 DF LDA $DF [$00:06DF] A:0000 X:0000 Y:0032 P:envMXdIZc
$00/94A5 F0 06 BEQ $06 [$94AD] A:0008 X:0000 Y:0032 P:envMXdIzc
$00/94A7 20 16 B7 JSR $B716 [$00:B716] A:0008 X:0000 Y:0032 P:envMXdIzc
$00/B716 A5 7F LDA $7F [$00:067F] A:0008 X:0000 Y:0032 P:envMXdIzc
$00/B718 D0 25 BNE $25 [$B73F] A:0001 X:0000 Y:0032 P:envMXdIzc
$00/B73F A2 08 LDX #$08 A:0001 X:0000 Y:0032 P:envMXdIzc
$00/B741 00 CA BRK #$CA A:0001 X:0008 Y:0032 P:envMXdIzc
*** BRK
$00/FFFF FF 00 C1 05 SBC $05C100,x[$05:C108] A:0001 X:0008 Y:0032 P:envMXdIzc
$00/0003 00 09 BRK #$09 A:00FF X:0008 Y:0032 P:eNvMXdIzc
*** BRK
$00/FFFF FF 00 C1 05 SBC $05C100,x[$05:C108] A:00FF X:0008 Y:0032 P:eNvMXdIzc
$00/0003 00 09 BRK #$09 A:00FD X:0008 Y:0032 P:eNvMXdIzC
*** BRK
The SBC/BRK then goes on forever.$01/ECB0 C9 C3 CMP #$C3 A:0043 X:0BAE Y:0032 P:envMxdizC
$01/ECB2 D0 04 BNE $04 [$ECB8] A:0043 X:0BAE Y:0032 P:eNvMxdizc
$01/ECB8 20 BC EC JSR $ECBC [$01:ECBC] A:0043 X:0BAE Y:0032 P:eNvMxdizc
$01/ECBC C9 40 CMP #$40 A:0043 X:0BAE Y:0032 P:eNvMxdizc
$01/ECBE 90 31 BCC $31 [$ECF1] A:0043 X:0BAE Y:0032 P:envMxdizC
$01/ECC0 18 CLC A:0043 X:0BAE Y:0032 P:envMxdizC
$01/ECC1 C9 80 CMP #$80 A:0043 X:0BAE Y:0032 P:envMxdizc
$01/ECC3 B0 2C BCS $2C [$ECF1] A:0043 X:0BAE Y:0032 P:eNvMxdizc
$01/ECC5 8E FD 1F STX $1FFD [$00:1FFD] A:0043 X:0BAE Y:0032 P:eNvMxdizc
$01/ECC8 E2 30 SEP #$30 A:0043 X:0BAE Y:0032 P:eNvMxdizc
$01/ECCA 38 SEC A:0043 X:00AE Y:0032 P:eNvMXdizc
$01/ECCB E9 40 SBC #$40 A:0043 X:00AE Y:0032 P:eNvMXdizC
$01/ECCD 18 CLC A:0003 X:00AE Y:0032 P:envMXdizC
$01/ECCE AE FF 1F LDX $1FFF [$00:1FFF] A:0003 X:00AE Y:0032 P:envMXdizc
*** IRQ
$00/0204 5C 80 94 00 JMP $009480[$00:9480] A:0003 X:0000 Y:0032 P:envMXdIZc
$00/9480 08 PHP A:0003 X:0000 Y:0032 P:envMXdIZc
$00/9481 C2 20 REP #$20 A:0003 X:0000 Y:0032 P:envMXdIZc
$00/9483 48 PHA A:0003 X:0000 Y:0032 P:envmXdIZc
$00/9484 DA PHX A:0003 X:0000 Y:0032 P:envmXdIZc
$00/9485 5A PHY A:0003 X:0000 Y:0032 P:envmXdIZc
$00/9486 8B PHB A:0003 X:0000 Y:0032 P:envmXdIZc
$00/9487 0B PHD A:0003 X:0000 Y:0032 P:envmXdIZc
$00/9488 A9 00 00 LDA #$0000 A:0003 X:0000 Y:0032 P:envmXdIZc
$00/948B E2 20 SEP #$20 A:0000 X:0000 Y:0032 P:envmXdIZc
$00/948D A2 00 LDX #$00 A:0000 X:0000 Y:0032 P:envMXdIZc
$00/948F 06 DA ASL $DA [$00:06DA] A:0000 X:0000 Y:0032 P:envMXdIZc
$00/9491 2B PLD A:0000 X:0000 Y:0032 P:envMXdIZc
$00/9492 A9 00 LDA #$00 A:0000 X:0000 Y:0032 P:envMXdIzc
$00/9494 48 PHA A:0000 X:0000 Y:0032 P:envMXdIZc
$00/9495 AB PLB A:0000 X:0000 Y:0032 P:envMXdIZc
$00/9496 AD 11 42 LDA $4211 [$00:4211] A:0000 X:0000 Y:0032 P:envMXdIZc
$00/9499 A5 D9 LDA $D9 [$00:06D9] A:00C2 X:0000 Y:0032 P:eNvMXdIzc
$00/949B F0 06 BEQ $06 [$94A3] A:0000 X:0000 Y:0032 P:envMXdIZc
$00/94A3 A5 DF LDA $DF [$00:06DF] A:0000 X:0000 Y:0032 P:envMXdIZc
$00/94A5 F0 06 BEQ $06 [$94AD] A:0008 X:0000 Y:0032 P:envMXdIzc
$00/94A7 20 16 B7 JSR $B716 [$00:B716] A:0008 X:0000 Y:0032 P:envMXdIzc
$00/B716 A5 7F LDA $7F [$00:067F] A:0008 X:0000 Y:0032 P:envMXdIzc
$00/B718 D0 25 BNE $25 [$B73F] A:0001 X:0000 Y:0032 P:envMXdIzc
$00/B73F A2 08 LDX #$08 A:0001 X:0000 Y:0032 P:envMXdIzc
$00/B741 00 CA BRK #$CA A:0001 X:0008 Y:0032 P:envMXdIzc
*** BRK
$00/FFFF FF 00 C1 05 SBC $05C100,x[$05:C108] A:0001 X:0008 Y:0032 P:envMXdIzc
$00/0003 00 09 BRK #$09 A:00FF X:0008 Y:0032 P:eNvMXdIzc
*** BRK
$00/FFFF FF 00 C1 05 SBC $05C100,x[$05:C108] A:00FF X:0008 Y:0032 P:eNvMXdIzc
$00/0003 00 09 BRK #$09 A:00FD X:0008 Y:0032 P:eNvMXdIzC
*** BRK
My guess is that this has something to do with bad timing caused by my new routine.
I'm only taking my first steps in SNES ASM hacking, so I have virtually no knowledge about such issues, but I'm hoping I'll find some guidance here!
Thanks in advance!
P.S. Would it be better to attach the trace or is it okay to put it into the post itself?