diff --git a/c64tests/0start b/c64tests/0start new file mode 100644 index 000000000..fb1cd21bc Binary files /dev/null and b/c64tests/0start differ diff --git a/c64tests/_Test Suite 2.15.txt b/c64tests/_Test Suite 2.15.txt new file mode 100644 index 000000000..b9ecc398a --- /dev/null +++ b/c64tests/_Test Suite 2.15.txt @@ -0,0 +1,376 @@ +C64 Emulator Test Suite - Public Domain, no Copyright + +https://github.com/mattgodbolt/jsbeeb/blob/master/tests/suite/cbm-hackers-post.md + + +The purpose of the C64 Emulator Test Suite is +- to help C64 emulator authors improve the compatibility +- ensure that updated emulators have no new bugs in old code parts + +The suite are a few hundred C64 programs which check the details of the C64 they are running on. The suite runs automated and stops only if it has detected an error. That the suite doesn't stop on my C64-I/PAL proves that the suite has no bugs. That the same suite doesn't stop on an emulator proves that this particular emulator is compatible to my C64 regarding every tested detail. Of course, the emulator may still have bugs in parts which are not tested by the suite. There may also be a difference between your C64 and my C64. + +While the Test Suite is running, the Datasette should be disconnected. Needs about 80 min to complete. + +The source code has been developed with MACRO(SS)ASS+ by Wolfram Roemhild. The file TEMPLATE.ASM provides a starting point for adding new tests to the suite. + + +/////////////////////////////////////////////////////////////////////////////// +Program _START - some 6510 basic commands, just as an insurance + + +/////////////////////////////////////////////////////////////////////////////// +Programs LDAb to SBCb(EB) - 6510 command function + +addressing modes +----------------------------------- +n none (implied and accu) +b byte (immediate) +w word (absolute for JMP and JSR) +z zero page +zx zero page,x +zy zero page,y +a absolute +ax absolute,x +ay absolute,y +i indirect (JMP) +ix (indirect,x) +iy (indirect),y +r relative + +Display: +before data accu xreg yreg flags sp +after data accu xreg yreg flags sp +right data accu xreg yreg flags sp + +Either press STOP or any other key to continue. + +All 256 opcodes are tested except HLTn (02 12 22 32 42 52 62 72 92 B2 D2 F2). + +Indexed addressing modes count the index registers from 00 to FF. + +JMPi (xxFF) is tested. + +Single operand commands: 256 data combinations from 00 to FF multiplied by 256 flag combinations. + +Two operand commands: 256 data combinations 00/00, 00/11, ... FF/EE, FF/FF multiplied by 256 flag combinations. + +ANEb, LASay, SHAay, SHAiy, SHXay, SHYax and SHSay are executed only in the y border. These commands cause unpredictable results when a DMA comes between the command byte and the operand. + +SHAay, SHAiy, SHXay, SHYax and SHSay are tested on a data address xxFF only. When the hibyte of the indexed address needs adjustment, these commands will write to different locations, depending on the data written. + + +/////////////////////////////////////////////////////////////////////////////// +Programs TRAP* - 6510 IO traps, page boundaries and wrap arounds + + # code data zd zptr aspect tested +----------------------------------------------------------------------------- + 1 2800 29C0 F7 F7/F8 basic functionality + 2 2FFE 29C0 F7 F7/F8 4k boundary within 3 byte commands + 3 2FFF 29C0 F7 F7/F8 4k boundary within 2 and 3 byte commands + 4 D000 29C0 F7 F7/F8 IO traps for code fetch + 5 CFFE 29C0 F7 F7/F8 RAM/IO boundary within 3 byte commands + 6 CFFF 29C0 F7 F7/F8 RAM/IO boundary within 2 and 3 byte commands + 7 2800 D0C0 F7 F7/F8 IO traps for 16 bit data access + 8 2800 D000 F7 F7/F8 IO trap adjustment in ax, ay and iy addressing + 9 2800 29C0 02 F7/F8 wrap around in zx and zy addressing +10 2800 29C0 00 F7/F8 IO traps for 8 bit data access +11 2800 29C0 F7 02/03 wrap around in ix addressing +12 2800 29C0 F7 FF/00 wrap around and IO trap for pointer accesses +13 2800 0002 F7 F7/F8 64k wrap around in ax, ay and iy addressing +14 2800 0000 F7 F7/F8 64k wrap around plus IO trap +15 CFFF D0C6 00 FF/00 1-14 all together as a stress test +16 FFFE ---- -- --/-- 64k boundary within 3 byte commands +17 FFFF ---- -- --/-- 64k boundary within 2 and 3 byte commands + +In the programs TRAP16 and TRAP17, the locations of data, zerodata and zeroptr depend on the addressing mode. The CPU port at 00/01 is not able to hold all 256 bit combinations. + +The datasette may not be connected while TRAP16 and TRAP17 are running! + +Display: +after data accu xreg yreg flags +right data accu xreg yreg flags + +If all displayed values match, some other aspect is wrong, e.g. the stack pointer or data on stack. + +All 256 commands are tested except HLTn. Registers before: +data 1B (00 01 10 11) +accu C6 (11 00 01 10) +xreg B1 (10 11 00 01) +yreg 6C (01 10 11 00) +flags 00 +sptr not initialized, typically F8 + +The code length is 6 bytes maximum (SHSay). + +When the lowbyte of the data address is less than C0, SHAay, SHAiy, SHXay, SHYax and SHSay aren't tested. Those commands don't handle the address adjustment correctly. + +Relative jumps are tested in 4 combinations: offset 01 no jump, offset 01 jump, offset 80 no jump, offset 80 jump. For the offset 80, a RTS is written to the location at code - 7E. + + +/////////////////////////////////////////////////////////////////////////////// +Program BRANCHWRAP - Forward branches from FFxx to 00xx + +Backward branches from 00xx to FFxx were already tested in TRAP16 and TRAP17. + + +/////////////////////////////////////////////////////////////////////////////// +Program MMUFETCH - 6510 code fetching while memory configuration changes + +An example is the code sequence LDA #$37 : STA 1 : BRK in RAM at Axxx. Because STA 1 maps the Basic ROM, the BRK will never get executed. + +addr sequence +--------------------- +A4DF RAM-Basic-RAM +B828 RAM-Basic-RAM +EA77 RAM-Kernal-RAM +FD25 RAM-Kernal-RAM +D400 RAM-Charset-RAM +D000 RAM-IO-RAM + +The sequence IO-Charset-IO is not tested because I didn't find some appropriate code bytes in the Charset ROM at D000-D3FF. The SID registers at D4xx are write-only. + + +/////////////////////////////////////////////////////////////////////////////// +Program MMU - 6510 port at 00/01 bits 0-2 + +Display: +0/1=0-7 repeated 6 times: values stored in 0 and 1 +after 0 1 A000 E000 D000 IO +right 0 1 A000 E000 D000 IO + +address value meaning +---------------------------------------- +A000 94 read Basic, write RAM +A000 01 read/write RAM +E000 86 read Kernal, write RAM +E000 01 read/write RAM +D000/IO 3D/02 read Charset, write RAM +D000/IO 01/02 read/write RAM +D000/IO 00/03 read/write IO + + +/////////////////////////////////////////////////////////////////////////////// +Program CPUPORT - 6510 port at 00/01 bits 0-7 + +Display: +0/1=00/FF repeated 6 times: values stored in 0 and 1 +after 00 01 +right 00 01 + +The datasette may not be connected while CPUPORT is running! + +If both values match, the port behaves instable. On my C64, this will only happen when a datasette is connected. + + +/////////////////////////////////////////////////////////////////////////////// +Program CPUTIMING - 6510 timing whole commands + +Display: +xx command byte +clocks #measured +right #2 + +#1 #2 command or addressing mode +-------------------------------------- +2 2 n +2 2 b +3 3 Rz/Wz +5 5 Mz +4 8 Rzx/Rzy/Wzx/Wzy +6 10 Mzx/Mzy +4 4 Ra/Wa +6 6 Ma +4 8 Rax/Ray (same page) +5 9 Rax/Ray (different page) +5 9 Wax/Way +7 11 Max/May +6 8 Rix/Wix +8 10 Mix/Miy +5 7 Riy (same page) +6 8 Riy (different page) +6 8 Wiy +8 10 Miy +2 18 r+00 same page not taken +3 19 r+00 same page taken +3 19 r+7F same page taken +4 20 r+01 different page taken +4 20 r+7F different page taken +3 19 r-03 same page taken +3 19 r-80 same page taken +4 20 r-03 different page taken +4 20 r-80 different page taken +7 7 BRKn +3 3 PHAn/PHPn +4 4 PLAn/PLPn +3 3 JMPw +5 5 JMPi +6 6 JSRw +6 6 RTSn +6 6 RTIn + +#1 = command execution time without overhead +#2 = displayed value including overhead for measurement +R/W/M = Read/Write/Modify + + +/////////////////////////////////////////////////////////////////////////////// +Programs IRQ and NMI - CPU interrupts within commands + +Tested are all commands except HLTn. For a command of n cycles, a loop with the interrupt occurring before cycle 1..n is performed. Rax/Ray/Riy addressing is tested with both the same page and a different page. Branches are tested not taken, taken to the same page, and taken to a different page. + +Display: +stack
+right
+ +When an interrupt occurs 2 or more cycles before the current command ends, it is executed immediately after the command. Otherwise, the CPU executes the next command first before it calls the interrupt handler. + +The only exception to this rule are taken branches to the same page which last 3 cycles. Here, the interrupt must have occurred before clock 1 of the branch command; the normal rule says before clock 2. Branches to a different page or branches not taken are behaving normal. + +The 6510 will set the IFlag on NMI, too. 6502 untested. + +When an IRQ occurs while SEIn is executing, the IFlag on the stack will be set. + +When an NMI occurs before clock 4 of a BRKn command, the BRK is finished as a NMI. In this case, BFlag on the stack will not be cleared. + + +/////////////////////////////////////////////////////////////////////////////// +Programs CIA1TB123 and CIA2TB123 - CIA timer B 1-3 cycles after writing CRB + +The cycles 1-3 after STA DD0F cannot be measured with LDA DD06 because it takes 3 cycles to decode the LDAa. Executing the STA DD0F at DD03 lets the CPU read DD06 within one cycle. + +#1 #2 DD06 sequence 1/2/3 (4) +--------------------------------- +00 01 keep keep count count +00 10 keep load keep keep +00 11 keep load keep count +01 11 count load keep count +01 10 count load keep keep +01 00 count count keep keep + +#1, #2 = values written to DD0F + + +/////////////////////////////////////////////////////////////////////////////// +Programs CIA1PB6 to CIA2PB7 - CIA timer output to PB6 and PB7 + +Checks 128 combinations of CRA/B in One Shot mode: + old CRx bit 0 Start + CRx bit 1 PBxOut + CRx bit 2 PBxToggle + new CRx bit 0 Start + CRx bit 1 PBxOut + CRx bit 2 PBxToggle + CRx bit 4 Force Load + +The resulting PB6/7 bit is: + 0 if new PBxToggle is 0 + 1 if new PBxToggle is 1 + - (undetermined) if PBxOut is 0 + +Old values do not influence the result. Start and Force Load don't either. + +Next, the programs test if PBx is toggled to 0 on the first underflow and that neither writing CRx except bit 0 nor Timer Hi/Lo will set it back to 1. The only source which is able to reset the toggle line is a rising edge on the Start bit 0 of CRx. + +Another test verifies that the toggle line is independent from PBxOut and PBxToggle. Changing these two bits will have no effect on switching the toggle flip flop when the timer underflows. + +The last test checks for the correct timing in Pulse and Toggle Mode. + + +/////////////////////////////////////////////////////////////////////////////// +Program CIA1TAB - TA, TB, PB67 and ICR in cascaded mode + +Both latches are set to 2. TA counts system clocks, TB counts TA underflows (cascaded). PB6 is high for one cycle when TA underflows, PB7 is toggled when TB underflows. IMR is $02. + +TA 01 02 02 01 02 02 01 02 02 01 02 02 +TB 02 02 02 01 01 01 00 00 02 02 02 02 +PB 80 C0 80 80 C0 80 80 C0 00 00 40 00 +ICR 00 01 01 01 01 01 01 01 03 83 83 83 + +If one of the registers doesn't match this table, the program displays the wrong values with red color. + + +/////////////////////////////////////////////////////////////////////////////// +Program LOADTH - Load timer high byte + +Writing to the high byte of the latch may load the counter only when it is not running. + +writing counter load +------------------------ +high byte stopped yes +high byte running no +low byte stopped no +low byte running no + + +/////////////////////////////////////////////////////////////////////////////// +Program CNTO2 - Switches between CNT and o2 input + +When the timer input is switched from o2 to CNT or from CNT back to o2, there must be a two clock delay until the switch is recognized. + + +/////////////////////////////////////////////////////////////////////////////// +Program ICR01 - Reads ICR around an underflow + +Reads ICR when an underflow occurs and checks if the NMI is executed. + +time ICR NMI +-------------- +t-1 00 yes +t 01 no +t+1 81 yes + + +/////////////////////////////////////////////////////////////////////////////// +Program IMR - Interrupt mask register + +When a condition in the ICR is true, setting the corresponding bit in the IMR must also set the interrupt. Clearing the bit in the IMR may not clear the interrupt. Only reading the ICR may clear the interrupt. + + +/////////////////////////////////////////////////////////////////////////////// +Program FLIPOS - Flip one shot + +Sets and clears the one shot bit when an underflow occurs at t. Set must take effect at t-1, clear at t-2. + +time set clear +------------------ +t-2 stop count +t-1 stop stop +t count stop + + +/////////////////////////////////////////////////////////////////////////////// +Program ONESHOT - Checks for start bit cleared + +Reads CRA in one shot mode with an underflow at t. + +time CRA +--------- +t-1 $09 +t $08 + + +/////////////////////////////////////////////////////////////////////////////// +Program CNTDEF - CNT default + +CNT must be high by default. This is tested with timer B cascaded mode CRB = $61. + + + + + + +******************************************* +** U N D E R C O N S T R U C T I O N ** +******************************************* + + + +/////////////////////////////////////////////////////////////////////////////// +Programs CIA1TA to CIA2TB - CIA timers in sysclock mode + +PC64Win 2.15 bug: + before 05/02/01/00 + after xx + cr 11/19 + after xx +timer low doesn't match diff --git a/c64tests/adca b/c64tests/adca new file mode 100644 index 000000000..87bfdf6cb Binary files /dev/null and b/c64tests/adca differ diff --git a/c64tests/adcax b/c64tests/adcax new file mode 100644 index 000000000..f28d92178 Binary files /dev/null and b/c64tests/adcax differ diff --git a/c64tests/adcay b/c64tests/adcay new file mode 100644 index 000000000..46a69cb23 Binary files /dev/null and b/c64tests/adcay differ diff --git a/c64tests/adcb b/c64tests/adcb new file mode 100644 index 000000000..55169ef8d Binary files /dev/null and b/c64tests/adcb differ diff --git a/c64tests/adcix b/c64tests/adcix new file mode 100644 index 000000000..252ea07b0 Binary files /dev/null and b/c64tests/adcix differ diff --git a/c64tests/adciy b/c64tests/adciy new file mode 100644 index 000000000..faafc6969 Binary files /dev/null and b/c64tests/adciy differ diff --git a/c64tests/adcz b/c64tests/adcz new file mode 100644 index 000000000..356737d1c Binary files /dev/null and b/c64tests/adcz differ diff --git a/c64tests/adczx b/c64tests/adczx new file mode 100644 index 000000000..036d83e15 Binary files /dev/null and b/c64tests/adczx differ diff --git a/c64tests/alrb b/c64tests/alrb new file mode 100644 index 000000000..75da7c89f Binary files /dev/null and b/c64tests/alrb differ diff --git a/c64tests/ancb b/c64tests/ancb new file mode 100644 index 000000000..c0e18903c Binary files /dev/null and b/c64tests/ancb differ diff --git a/c64tests/anda b/c64tests/anda new file mode 100644 index 000000000..5ebc4cde6 Binary files /dev/null and b/c64tests/anda differ diff --git a/c64tests/andax b/c64tests/andax new file mode 100644 index 000000000..ef004b71d Binary files /dev/null and b/c64tests/andax differ diff --git a/c64tests/anday b/c64tests/anday new file mode 100644 index 000000000..448381aa0 Binary files /dev/null and b/c64tests/anday differ diff --git a/c64tests/andb b/c64tests/andb new file mode 100644 index 000000000..1f4db4258 Binary files /dev/null and b/c64tests/andb differ diff --git a/c64tests/andix b/c64tests/andix new file mode 100644 index 000000000..50e632f47 Binary files /dev/null and b/c64tests/andix differ diff --git a/c64tests/andiy b/c64tests/andiy new file mode 100644 index 000000000..770f86f64 Binary files /dev/null and b/c64tests/andiy differ diff --git a/c64tests/andz b/c64tests/andz new file mode 100644 index 000000000..4e4db7bb4 Binary files /dev/null and b/c64tests/andz differ diff --git a/c64tests/andzx b/c64tests/andzx new file mode 100644 index 000000000..5a6de9e30 Binary files /dev/null and b/c64tests/andzx differ diff --git a/c64tests/aneb b/c64tests/aneb new file mode 100644 index 000000000..c5e7e063d Binary files /dev/null and b/c64tests/aneb differ diff --git a/c64tests/arrb b/c64tests/arrb new file mode 100644 index 000000000..af871cab6 Binary files /dev/null and b/c64tests/arrb differ diff --git a/c64tests/asla b/c64tests/asla new file mode 100644 index 000000000..932a6d47a Binary files /dev/null and b/c64tests/asla differ diff --git a/c64tests/aslax b/c64tests/aslax new file mode 100644 index 000000000..38bb78a16 Binary files /dev/null and b/c64tests/aslax differ diff --git a/c64tests/asln b/c64tests/asln new file mode 100644 index 000000000..451a65ae8 Binary files /dev/null and b/c64tests/asln differ diff --git a/c64tests/aslz b/c64tests/aslz new file mode 100644 index 000000000..17eff5cd5 Binary files /dev/null and b/c64tests/aslz differ diff --git a/c64tests/aslzx b/c64tests/aslzx new file mode 100644 index 000000000..594fb681e Binary files /dev/null and b/c64tests/aslzx differ diff --git a/c64tests/asoa b/c64tests/asoa new file mode 100644 index 000000000..299da9d8e Binary files /dev/null and b/c64tests/asoa differ diff --git a/c64tests/asoax b/c64tests/asoax new file mode 100644 index 000000000..205e6c1ae Binary files /dev/null and b/c64tests/asoax differ diff --git a/c64tests/asoay b/c64tests/asoay new file mode 100644 index 000000000..b6657bbd0 Binary files /dev/null and b/c64tests/asoay differ diff --git a/c64tests/asoix b/c64tests/asoix new file mode 100644 index 000000000..9ff13a131 Binary files /dev/null and b/c64tests/asoix differ diff --git a/c64tests/asoiy b/c64tests/asoiy new file mode 100644 index 000000000..389b578e2 Binary files /dev/null and b/c64tests/asoiy differ diff --git a/c64tests/asoz b/c64tests/asoz new file mode 100644 index 000000000..3e06cc8ac Binary files /dev/null and b/c64tests/asoz differ diff --git a/c64tests/asozx b/c64tests/asozx new file mode 100644 index 000000000..8be8b08a1 Binary files /dev/null and b/c64tests/asozx differ diff --git a/c64tests/axsa b/c64tests/axsa new file mode 100644 index 000000000..f53c23f67 Binary files /dev/null and b/c64tests/axsa differ diff --git a/c64tests/axsix b/c64tests/axsix new file mode 100644 index 000000000..f285bc954 Binary files /dev/null and b/c64tests/axsix differ diff --git a/c64tests/axsz b/c64tests/axsz new file mode 100644 index 000000000..c1304fce1 Binary files /dev/null and b/c64tests/axsz differ diff --git a/c64tests/axszy b/c64tests/axszy new file mode 100644 index 000000000..f886f0d24 Binary files /dev/null and b/c64tests/axszy differ diff --git a/c64tests/bccr b/c64tests/bccr new file mode 100644 index 000000000..776e88766 Binary files /dev/null and b/c64tests/bccr differ diff --git a/c64tests/bcsr b/c64tests/bcsr new file mode 100644 index 000000000..074baf222 Binary files /dev/null and b/c64tests/bcsr differ diff --git a/c64tests/beqr b/c64tests/beqr new file mode 100644 index 000000000..b77ef957e Binary files /dev/null and b/c64tests/beqr differ diff --git a/c64tests/bita b/c64tests/bita new file mode 100644 index 000000000..2800315e2 Binary files /dev/null and b/c64tests/bita differ diff --git a/c64tests/bitz b/c64tests/bitz new file mode 100644 index 000000000..439ca8216 Binary files /dev/null and b/c64tests/bitz differ diff --git a/c64tests/bmir b/c64tests/bmir new file mode 100644 index 000000000..5ed96e48c Binary files /dev/null and b/c64tests/bmir differ diff --git a/c64tests/bner b/c64tests/bner new file mode 100644 index 000000000..d14bfdeb6 Binary files /dev/null and b/c64tests/bner differ diff --git a/c64tests/bplr b/c64tests/bplr new file mode 100644 index 000000000..26f074d3c Binary files /dev/null and b/c64tests/bplr differ diff --git a/c64tests/branchwrap b/c64tests/branchwrap new file mode 100644 index 000000000..d7740b958 Binary files /dev/null and b/c64tests/branchwrap differ diff --git a/c64tests/brkn b/c64tests/brkn new file mode 100644 index 000000000..fc4611110 Binary files /dev/null and b/c64tests/brkn differ diff --git a/c64tests/bvcr b/c64tests/bvcr new file mode 100644 index 000000000..af935d66b Binary files /dev/null and b/c64tests/bvcr differ diff --git a/c64tests/bvsr b/c64tests/bvsr new file mode 100644 index 000000000..45337d0e3 Binary files /dev/null and b/c64tests/bvsr differ diff --git a/c64tests/cia1pb6 b/c64tests/cia1pb6 new file mode 100644 index 000000000..e8b683eca Binary files /dev/null and b/c64tests/cia1pb6 differ diff --git a/c64tests/cia1pb7 b/c64tests/cia1pb7 new file mode 100644 index 000000000..10920f788 Binary files /dev/null and b/c64tests/cia1pb7 differ diff --git a/c64tests/cia1ta b/c64tests/cia1ta new file mode 100644 index 000000000..9f5ccfaf1 Binary files /dev/null and b/c64tests/cia1ta differ diff --git a/c64tests/cia1tab b/c64tests/cia1tab new file mode 100644 index 000000000..5d1aea7f3 Binary files /dev/null and b/c64tests/cia1tab differ diff --git a/c64tests/cia1tb b/c64tests/cia1tb new file mode 100644 index 000000000..3802a1bf5 Binary files /dev/null and b/c64tests/cia1tb differ diff --git a/c64tests/cia1tb123 b/c64tests/cia1tb123 new file mode 100644 index 000000000..f7a90a299 Binary files /dev/null and b/c64tests/cia1tb123 differ diff --git a/c64tests/cia2pb6 b/c64tests/cia2pb6 new file mode 100644 index 000000000..fa0dc4308 Binary files /dev/null and b/c64tests/cia2pb6 differ diff --git a/c64tests/cia2pb7 b/c64tests/cia2pb7 new file mode 100644 index 000000000..118c51f0f Binary files /dev/null and b/c64tests/cia2pb7 differ diff --git a/c64tests/cia2ta b/c64tests/cia2ta new file mode 100644 index 000000000..59254a2c4 Binary files /dev/null and b/c64tests/cia2ta differ diff --git a/c64tests/cia2tb b/c64tests/cia2tb new file mode 100644 index 000000000..886daac15 Binary files /dev/null and b/c64tests/cia2tb differ diff --git a/c64tests/cia2tb123 b/c64tests/cia2tb123 new file mode 100644 index 000000000..f8b13c7a2 Binary files /dev/null and b/c64tests/cia2tb123 differ diff --git a/c64tests/clcn b/c64tests/clcn new file mode 100644 index 000000000..a89106ab2 Binary files /dev/null and b/c64tests/clcn differ diff --git a/c64tests/cldn b/c64tests/cldn new file mode 100644 index 000000000..950696e5a Binary files /dev/null and b/c64tests/cldn differ diff --git a/c64tests/clin b/c64tests/clin new file mode 100644 index 000000000..f5dd27042 Binary files /dev/null and b/c64tests/clin differ diff --git a/c64tests/clvn b/c64tests/clvn new file mode 100644 index 000000000..ec9bfb4b1 Binary files /dev/null and b/c64tests/clvn differ diff --git a/c64tests/cmpa b/c64tests/cmpa new file mode 100644 index 000000000..b515e0861 Binary files /dev/null and b/c64tests/cmpa differ diff --git a/c64tests/cmpax b/c64tests/cmpax new file mode 100644 index 000000000..baa55f161 Binary files /dev/null and b/c64tests/cmpax differ diff --git a/c64tests/cmpay b/c64tests/cmpay new file mode 100644 index 000000000..f8351fc17 Binary files /dev/null and b/c64tests/cmpay differ diff --git a/c64tests/cmpb b/c64tests/cmpb new file mode 100644 index 000000000..fbe1b911c Binary files /dev/null and b/c64tests/cmpb differ diff --git a/c64tests/cmpix b/c64tests/cmpix new file mode 100644 index 000000000..5e07d9d42 Binary files /dev/null and b/c64tests/cmpix differ diff --git a/c64tests/cmpiy b/c64tests/cmpiy new file mode 100644 index 000000000..692666465 Binary files /dev/null and b/c64tests/cmpiy differ diff --git a/c64tests/cmpz b/c64tests/cmpz new file mode 100644 index 000000000..27f2ca3bb Binary files /dev/null and b/c64tests/cmpz differ diff --git a/c64tests/cmpzx b/c64tests/cmpzx new file mode 100644 index 000000000..d332c16bb Binary files /dev/null and b/c64tests/cmpzx differ diff --git a/c64tests/cntdef b/c64tests/cntdef new file mode 100644 index 000000000..b12f46c51 Binary files /dev/null and b/c64tests/cntdef differ diff --git a/c64tests/cnto2 b/c64tests/cnto2 new file mode 100644 index 000000000..a7b0405b3 Binary files /dev/null and b/c64tests/cnto2 differ diff --git a/c64tests/cpuport b/c64tests/cpuport new file mode 100644 index 000000000..c3ac852dc Binary files /dev/null and b/c64tests/cpuport differ diff --git a/c64tests/cputiming b/c64tests/cputiming new file mode 100644 index 000000000..fc3114e63 Binary files /dev/null and b/c64tests/cputiming differ diff --git a/c64tests/cpxa b/c64tests/cpxa new file mode 100644 index 000000000..bc36f1874 Binary files /dev/null and b/c64tests/cpxa differ diff --git a/c64tests/cpxb b/c64tests/cpxb new file mode 100644 index 000000000..97f8988d1 Binary files /dev/null and b/c64tests/cpxb differ diff --git a/c64tests/cpxz b/c64tests/cpxz new file mode 100644 index 000000000..01ebf3191 Binary files /dev/null and b/c64tests/cpxz differ diff --git a/c64tests/cpya b/c64tests/cpya new file mode 100644 index 000000000..ab9448419 Binary files /dev/null and b/c64tests/cpya differ diff --git a/c64tests/cpyb b/c64tests/cpyb new file mode 100644 index 000000000..8247ec99d Binary files /dev/null and b/c64tests/cpyb differ diff --git a/c64tests/cpyz b/c64tests/cpyz new file mode 100644 index 000000000..81451bc17 Binary files /dev/null and b/c64tests/cpyz differ diff --git a/c64tests/dcma b/c64tests/dcma new file mode 100644 index 000000000..9ed51d4aa Binary files /dev/null and b/c64tests/dcma differ diff --git a/c64tests/dcmax b/c64tests/dcmax new file mode 100644 index 000000000..18ccbe866 Binary files /dev/null and b/c64tests/dcmax differ diff --git a/c64tests/dcmay b/c64tests/dcmay new file mode 100644 index 000000000..01b27fb75 Binary files /dev/null and b/c64tests/dcmay differ diff --git a/c64tests/dcmix b/c64tests/dcmix new file mode 100644 index 000000000..2f6de7487 Binary files /dev/null and b/c64tests/dcmix differ diff --git a/c64tests/dcmiy b/c64tests/dcmiy new file mode 100644 index 000000000..4df404452 Binary files /dev/null and b/c64tests/dcmiy differ diff --git a/c64tests/dcmz b/c64tests/dcmz new file mode 100644 index 000000000..fa04f43bc Binary files /dev/null and b/c64tests/dcmz differ diff --git a/c64tests/dcmzx b/c64tests/dcmzx new file mode 100644 index 000000000..c9e72b7a2 Binary files /dev/null and b/c64tests/dcmzx differ diff --git a/c64tests/deca b/c64tests/deca new file mode 100644 index 000000000..167ef5463 Binary files /dev/null and b/c64tests/deca differ diff --git a/c64tests/decax b/c64tests/decax new file mode 100644 index 000000000..69c31f94c Binary files /dev/null and b/c64tests/decax differ diff --git a/c64tests/decz b/c64tests/decz new file mode 100644 index 000000000..f7f39461d Binary files /dev/null and b/c64tests/decz differ diff --git a/c64tests/deczx b/c64tests/deczx new file mode 100644 index 000000000..d8c0e7694 Binary files /dev/null and b/c64tests/deczx differ diff --git a/c64tests/dexn b/c64tests/dexn new file mode 100644 index 000000000..c02027a02 Binary files /dev/null and b/c64tests/dexn differ diff --git a/c64tests/deyn b/c64tests/deyn new file mode 100644 index 000000000..8c9e06871 Binary files /dev/null and b/c64tests/deyn differ diff --git a/c64tests/eora b/c64tests/eora new file mode 100644 index 000000000..7473a9b7b Binary files /dev/null and b/c64tests/eora differ diff --git a/c64tests/eorax b/c64tests/eorax new file mode 100644 index 000000000..584be503a Binary files /dev/null and b/c64tests/eorax differ diff --git a/c64tests/eoray b/c64tests/eoray new file mode 100644 index 000000000..340b6a514 Binary files /dev/null and b/c64tests/eoray differ diff --git a/c64tests/eorb b/c64tests/eorb new file mode 100644 index 000000000..3b1716849 Binary files /dev/null and b/c64tests/eorb differ diff --git a/c64tests/eorix b/c64tests/eorix new file mode 100644 index 000000000..06de6ff57 Binary files /dev/null and b/c64tests/eorix differ diff --git a/c64tests/eoriy b/c64tests/eoriy new file mode 100644 index 000000000..194802bfc Binary files /dev/null and b/c64tests/eoriy differ diff --git a/c64tests/eorz b/c64tests/eorz new file mode 100644 index 000000000..fa3e882ca Binary files /dev/null and b/c64tests/eorz differ diff --git a/c64tests/eorzx b/c64tests/eorzx new file mode 100644 index 000000000..c39e0ebb1 Binary files /dev/null and b/c64tests/eorzx differ diff --git a/c64tests/finish b/c64tests/finish new file mode 100644 index 000000000..52f6f4521 Binary files /dev/null and b/c64tests/finish differ diff --git a/c64tests/flipos b/c64tests/flipos new file mode 100644 index 000000000..431e4907a Binary files /dev/null and b/c64tests/flipos differ diff --git a/c64tests/icr01 b/c64tests/icr01 new file mode 100644 index 000000000..de8bd989f Binary files /dev/null and b/c64tests/icr01 differ diff --git a/c64tests/imr b/c64tests/imr new file mode 100644 index 000000000..3fe057bd5 Binary files /dev/null and b/c64tests/imr differ diff --git a/c64tests/inca b/c64tests/inca new file mode 100644 index 000000000..bb031cb3c Binary files /dev/null and b/c64tests/inca differ diff --git a/c64tests/incax b/c64tests/incax new file mode 100644 index 000000000..065ae3183 Binary files /dev/null and b/c64tests/incax differ diff --git a/c64tests/incz b/c64tests/incz new file mode 100644 index 000000000..b3b9bac4d Binary files /dev/null and b/c64tests/incz differ diff --git a/c64tests/inczx b/c64tests/inczx new file mode 100644 index 000000000..019a4698f Binary files /dev/null and b/c64tests/inczx differ diff --git a/c64tests/insa b/c64tests/insa new file mode 100644 index 000000000..b117525b0 Binary files /dev/null and b/c64tests/insa differ diff --git a/c64tests/insax b/c64tests/insax new file mode 100644 index 000000000..e6b1cc3ec Binary files /dev/null and b/c64tests/insax differ diff --git a/c64tests/insay b/c64tests/insay new file mode 100644 index 000000000..06a4b7346 Binary files /dev/null and b/c64tests/insay differ diff --git a/c64tests/insix b/c64tests/insix new file mode 100644 index 000000000..85572f234 Binary files /dev/null and b/c64tests/insix differ diff --git a/c64tests/insiy b/c64tests/insiy new file mode 100644 index 000000000..8f0af40a2 Binary files /dev/null and b/c64tests/insiy differ diff --git a/c64tests/insz b/c64tests/insz new file mode 100644 index 000000000..717dd27b8 Binary files /dev/null and b/c64tests/insz differ diff --git a/c64tests/inszx b/c64tests/inszx new file mode 100644 index 000000000..fbc205708 Binary files /dev/null and b/c64tests/inszx differ diff --git a/c64tests/inxn b/c64tests/inxn new file mode 100644 index 000000000..b18ba9457 Binary files /dev/null and b/c64tests/inxn differ diff --git a/c64tests/inyn b/c64tests/inyn new file mode 100644 index 000000000..5ceba8dfd Binary files /dev/null and b/c64tests/inyn differ diff --git a/c64tests/irq b/c64tests/irq new file mode 100644 index 000000000..54be04f9b Binary files /dev/null and b/c64tests/irq differ diff --git a/c64tests/jmpi b/c64tests/jmpi new file mode 100644 index 000000000..5c4f88257 Binary files /dev/null and b/c64tests/jmpi differ diff --git a/c64tests/jmpw b/c64tests/jmpw new file mode 100644 index 000000000..738249c18 Binary files /dev/null and b/c64tests/jmpw differ diff --git a/c64tests/jsrw b/c64tests/jsrw new file mode 100644 index 000000000..a08772f92 Binary files /dev/null and b/c64tests/jsrw differ diff --git a/c64tests/lasay b/c64tests/lasay new file mode 100644 index 000000000..6b85ce3fb Binary files /dev/null and b/c64tests/lasay differ diff --git a/c64tests/laxa b/c64tests/laxa new file mode 100644 index 000000000..7693a0cf3 Binary files /dev/null and b/c64tests/laxa differ diff --git a/c64tests/laxay b/c64tests/laxay new file mode 100644 index 000000000..1292c0dc2 Binary files /dev/null and b/c64tests/laxay differ diff --git a/c64tests/laxix b/c64tests/laxix new file mode 100644 index 000000000..67d038867 Binary files /dev/null and b/c64tests/laxix differ diff --git a/c64tests/laxiy b/c64tests/laxiy new file mode 100644 index 000000000..1daac98e3 Binary files /dev/null and b/c64tests/laxiy differ diff --git a/c64tests/laxz b/c64tests/laxz new file mode 100644 index 000000000..9b24d20a0 Binary files /dev/null and b/c64tests/laxz differ diff --git a/c64tests/laxzy b/c64tests/laxzy new file mode 100644 index 000000000..a9de62c27 Binary files /dev/null and b/c64tests/laxzy differ diff --git a/c64tests/ldaa b/c64tests/ldaa new file mode 100644 index 000000000..55be82f2c Binary files /dev/null and b/c64tests/ldaa differ diff --git a/c64tests/ldaax b/c64tests/ldaax new file mode 100644 index 000000000..130c5c4e4 Binary files /dev/null and b/c64tests/ldaax differ diff --git a/c64tests/ldaay b/c64tests/ldaay new file mode 100644 index 000000000..1cb9f6c38 Binary files /dev/null and b/c64tests/ldaay differ diff --git a/c64tests/ldab b/c64tests/ldab new file mode 100644 index 000000000..103e9f6cf Binary files /dev/null and b/c64tests/ldab differ diff --git a/c64tests/ldaix b/c64tests/ldaix new file mode 100644 index 000000000..31c5945b0 Binary files /dev/null and b/c64tests/ldaix differ diff --git a/c64tests/ldaiy b/c64tests/ldaiy new file mode 100644 index 000000000..6f7bd1165 Binary files /dev/null and b/c64tests/ldaiy differ diff --git a/c64tests/ldaz b/c64tests/ldaz new file mode 100644 index 000000000..63ffdc77b Binary files /dev/null and b/c64tests/ldaz differ diff --git a/c64tests/ldazx b/c64tests/ldazx new file mode 100644 index 000000000..4739e4b4c Binary files /dev/null and b/c64tests/ldazx differ diff --git a/c64tests/ldxa b/c64tests/ldxa new file mode 100644 index 000000000..d2c8558b0 Binary files /dev/null and b/c64tests/ldxa differ diff --git a/c64tests/ldxay b/c64tests/ldxay new file mode 100644 index 000000000..6d6267cde Binary files /dev/null and b/c64tests/ldxay differ diff --git a/c64tests/ldxb b/c64tests/ldxb new file mode 100644 index 000000000..ccab216c8 Binary files /dev/null and b/c64tests/ldxb differ diff --git a/c64tests/ldxz b/c64tests/ldxz new file mode 100644 index 000000000..792838e61 Binary files /dev/null and b/c64tests/ldxz differ diff --git a/c64tests/ldxzy b/c64tests/ldxzy new file mode 100644 index 000000000..727a70a10 Binary files /dev/null and b/c64tests/ldxzy differ diff --git a/c64tests/ldya b/c64tests/ldya new file mode 100644 index 000000000..fef0d4b52 Binary files /dev/null and b/c64tests/ldya differ diff --git a/c64tests/ldyax b/c64tests/ldyax new file mode 100644 index 000000000..57defb991 Binary files /dev/null and b/c64tests/ldyax differ diff --git a/c64tests/ldyb b/c64tests/ldyb new file mode 100644 index 000000000..1e011d2f5 Binary files /dev/null and b/c64tests/ldyb differ diff --git a/c64tests/ldyz b/c64tests/ldyz new file mode 100644 index 000000000..042fd2461 Binary files /dev/null and b/c64tests/ldyz differ diff --git a/c64tests/ldyzx b/c64tests/ldyzx new file mode 100644 index 000000000..4205dc74b Binary files /dev/null and b/c64tests/ldyzx differ diff --git a/c64tests/loadth b/c64tests/loadth new file mode 100644 index 000000000..9125b8e08 Binary files /dev/null and b/c64tests/loadth differ diff --git a/c64tests/lsea b/c64tests/lsea new file mode 100644 index 000000000..8b33a4b20 Binary files /dev/null and b/c64tests/lsea differ diff --git a/c64tests/lseax b/c64tests/lseax new file mode 100644 index 000000000..2468fd743 Binary files /dev/null and b/c64tests/lseax differ diff --git a/c64tests/lseay b/c64tests/lseay new file mode 100644 index 000000000..f7dfac287 Binary files /dev/null and b/c64tests/lseay differ diff --git a/c64tests/lseix b/c64tests/lseix new file mode 100644 index 000000000..3d40ff65f Binary files /dev/null and b/c64tests/lseix differ diff --git a/c64tests/lseiy b/c64tests/lseiy new file mode 100644 index 000000000..96764e263 Binary files /dev/null and b/c64tests/lseiy differ diff --git a/c64tests/lsez b/c64tests/lsez new file mode 100644 index 000000000..d6f75b745 Binary files /dev/null and b/c64tests/lsez differ diff --git a/c64tests/lsezx b/c64tests/lsezx new file mode 100644 index 000000000..d5063d031 Binary files /dev/null and b/c64tests/lsezx differ diff --git a/c64tests/lsra b/c64tests/lsra new file mode 100644 index 000000000..27151dd15 Binary files /dev/null and b/c64tests/lsra differ diff --git a/c64tests/lsrax b/c64tests/lsrax new file mode 100644 index 000000000..d87966c29 Binary files /dev/null and b/c64tests/lsrax differ diff --git a/c64tests/lsrn b/c64tests/lsrn new file mode 100644 index 000000000..48fbb5019 Binary files /dev/null and b/c64tests/lsrn differ diff --git a/c64tests/lsrz b/c64tests/lsrz new file mode 100644 index 000000000..4e3cbef95 Binary files /dev/null and b/c64tests/lsrz differ diff --git a/c64tests/lsrzx b/c64tests/lsrzx new file mode 100644 index 000000000..8e5c3992a Binary files /dev/null and b/c64tests/lsrzx differ diff --git a/c64tests/lxab b/c64tests/lxab new file mode 100644 index 000000000..24e950db2 Binary files /dev/null and b/c64tests/lxab differ diff --git a/c64tests/mmu b/c64tests/mmu new file mode 100644 index 000000000..f1140ad9f Binary files /dev/null and b/c64tests/mmu differ diff --git a/c64tests/mmufetch b/c64tests/mmufetch new file mode 100644 index 000000000..148940e19 Binary files /dev/null and b/c64tests/mmufetch differ diff --git a/c64tests/nmi b/c64tests/nmi new file mode 100644 index 000000000..445bf2674 Binary files /dev/null and b/c64tests/nmi differ diff --git a/c64tests/nopa b/c64tests/nopa new file mode 100644 index 000000000..40784d9d4 Binary files /dev/null and b/c64tests/nopa differ diff --git a/c64tests/nopax b/c64tests/nopax new file mode 100644 index 000000000..8f70d1506 Binary files /dev/null and b/c64tests/nopax differ diff --git a/c64tests/nopb b/c64tests/nopb new file mode 100644 index 000000000..0b6516e84 Binary files /dev/null and b/c64tests/nopb differ diff --git a/c64tests/nopn b/c64tests/nopn new file mode 100644 index 000000000..7d9264ab1 Binary files /dev/null and b/c64tests/nopn differ diff --git a/c64tests/nopz b/c64tests/nopz new file mode 100644 index 000000000..30ab92682 Binary files /dev/null and b/c64tests/nopz differ diff --git a/c64tests/nopzx b/c64tests/nopzx new file mode 100644 index 000000000..ec8770e78 Binary files /dev/null and b/c64tests/nopzx differ diff --git a/c64tests/oneshot b/c64tests/oneshot new file mode 100644 index 000000000..eda87c0ae Binary files /dev/null and b/c64tests/oneshot differ diff --git a/c64tests/oraa b/c64tests/oraa new file mode 100644 index 000000000..fe07787e3 Binary files /dev/null and b/c64tests/oraa differ diff --git a/c64tests/oraax b/c64tests/oraax new file mode 100644 index 000000000..642f0a4f7 Binary files /dev/null and b/c64tests/oraax differ diff --git a/c64tests/oraay b/c64tests/oraay new file mode 100644 index 000000000..3a67e19be Binary files /dev/null and b/c64tests/oraay differ diff --git a/c64tests/orab b/c64tests/orab new file mode 100644 index 000000000..39be6e8d6 Binary files /dev/null and b/c64tests/orab differ diff --git a/c64tests/oraix b/c64tests/oraix new file mode 100644 index 000000000..68d2fdf85 Binary files /dev/null and b/c64tests/oraix differ diff --git a/c64tests/oraiy b/c64tests/oraiy new file mode 100644 index 000000000..5c3fce3d7 Binary files /dev/null and b/c64tests/oraiy differ diff --git a/c64tests/oraz b/c64tests/oraz new file mode 100644 index 000000000..23addc4d6 Binary files /dev/null and b/c64tests/oraz differ diff --git a/c64tests/orazx b/c64tests/orazx new file mode 100644 index 000000000..bca23a94e Binary files /dev/null and b/c64tests/orazx differ diff --git a/c64tests/phan b/c64tests/phan new file mode 100644 index 000000000..c0a02475b Binary files /dev/null and b/c64tests/phan differ diff --git a/c64tests/phpn b/c64tests/phpn new file mode 100644 index 000000000..be4b9870a Binary files /dev/null and b/c64tests/phpn differ diff --git a/c64tests/plan b/c64tests/plan new file mode 100644 index 000000000..785291bb7 Binary files /dev/null and b/c64tests/plan differ diff --git a/c64tests/plpn b/c64tests/plpn new file mode 100644 index 000000000..9e179c662 Binary files /dev/null and b/c64tests/plpn differ diff --git a/c64tests/rlaa b/c64tests/rlaa new file mode 100644 index 000000000..6fe1d283d Binary files /dev/null and b/c64tests/rlaa differ diff --git a/c64tests/rlaax b/c64tests/rlaax new file mode 100644 index 000000000..712eaeb7c Binary files /dev/null and b/c64tests/rlaax differ diff --git a/c64tests/rlaay b/c64tests/rlaay new file mode 100644 index 000000000..ce337cdc5 Binary files /dev/null and b/c64tests/rlaay differ diff --git a/c64tests/rlaix b/c64tests/rlaix new file mode 100644 index 000000000..f60672eaf Binary files /dev/null and b/c64tests/rlaix differ diff --git a/c64tests/rlaiy b/c64tests/rlaiy new file mode 100644 index 000000000..2391a9530 Binary files /dev/null and b/c64tests/rlaiy differ diff --git a/c64tests/rlaz b/c64tests/rlaz new file mode 100644 index 000000000..bdacdb12b Binary files /dev/null and b/c64tests/rlaz differ diff --git a/c64tests/rlazx b/c64tests/rlazx new file mode 100644 index 000000000..24e26844f Binary files /dev/null and b/c64tests/rlazx differ diff --git a/c64tests/rola b/c64tests/rola new file mode 100644 index 000000000..f79f6b809 Binary files /dev/null and b/c64tests/rola differ diff --git a/c64tests/rolax b/c64tests/rolax new file mode 100644 index 000000000..05a11e612 Binary files /dev/null and b/c64tests/rolax differ diff --git a/c64tests/roln b/c64tests/roln new file mode 100644 index 000000000..b3c468407 Binary files /dev/null and b/c64tests/roln differ diff --git a/c64tests/rolz b/c64tests/rolz new file mode 100644 index 000000000..d694c1387 Binary files /dev/null and b/c64tests/rolz differ diff --git a/c64tests/rolzx b/c64tests/rolzx new file mode 100644 index 000000000..928beafa4 Binary files /dev/null and b/c64tests/rolzx differ diff --git a/c64tests/rora b/c64tests/rora new file mode 100644 index 000000000..32d8fa473 Binary files /dev/null and b/c64tests/rora differ diff --git a/c64tests/rorax b/c64tests/rorax new file mode 100644 index 000000000..e2438f618 Binary files /dev/null and b/c64tests/rorax differ diff --git a/c64tests/rorn b/c64tests/rorn new file mode 100644 index 000000000..46a5435c4 Binary files /dev/null and b/c64tests/rorn differ diff --git a/c64tests/rorz b/c64tests/rorz new file mode 100644 index 000000000..31e907e81 Binary files /dev/null and b/c64tests/rorz differ diff --git a/c64tests/rorzx b/c64tests/rorzx new file mode 100644 index 000000000..8e1294bfe Binary files /dev/null and b/c64tests/rorzx differ diff --git a/c64tests/rraa b/c64tests/rraa new file mode 100644 index 000000000..fdbc3c793 Binary files /dev/null and b/c64tests/rraa differ diff --git a/c64tests/rraax b/c64tests/rraax new file mode 100644 index 000000000..a3e801148 Binary files /dev/null and b/c64tests/rraax differ diff --git a/c64tests/rraay b/c64tests/rraay new file mode 100644 index 000000000..d55640f1c Binary files /dev/null and b/c64tests/rraay differ diff --git a/c64tests/rraix b/c64tests/rraix new file mode 100644 index 000000000..cbdc97f83 Binary files /dev/null and b/c64tests/rraix differ diff --git a/c64tests/rraiy b/c64tests/rraiy new file mode 100644 index 000000000..82d7e4d2c Binary files /dev/null and b/c64tests/rraiy differ diff --git a/c64tests/rraz b/c64tests/rraz new file mode 100644 index 000000000..dd79bc2e9 Binary files /dev/null and b/c64tests/rraz differ diff --git a/c64tests/rrazx b/c64tests/rrazx new file mode 100644 index 000000000..532835824 Binary files /dev/null and b/c64tests/rrazx differ diff --git a/c64tests/rtin b/c64tests/rtin new file mode 100644 index 000000000..d3b632275 Binary files /dev/null and b/c64tests/rtin differ diff --git a/c64tests/rtsn b/c64tests/rtsn new file mode 100644 index 000000000..1dadcf21c Binary files /dev/null and b/c64tests/rtsn differ diff --git a/c64tests/sbca b/c64tests/sbca new file mode 100644 index 000000000..5bb1e960e Binary files /dev/null and b/c64tests/sbca differ diff --git a/c64tests/sbcax b/c64tests/sbcax new file mode 100644 index 000000000..b811793b0 Binary files /dev/null and b/c64tests/sbcax differ diff --git a/c64tests/sbcay b/c64tests/sbcay new file mode 100644 index 000000000..dda6c459e Binary files /dev/null and b/c64tests/sbcay differ diff --git a/c64tests/sbcb b/c64tests/sbcb new file mode 100644 index 000000000..806ecd83b Binary files /dev/null and b/c64tests/sbcb differ diff --git a/c64tests/sbcb(eb) b/c64tests/sbcb(eb) new file mode 100644 index 000000000..5b684dcce Binary files /dev/null and b/c64tests/sbcb(eb) differ diff --git a/c64tests/sbcix b/c64tests/sbcix new file mode 100644 index 000000000..88f082819 Binary files /dev/null and b/c64tests/sbcix differ diff --git a/c64tests/sbciy b/c64tests/sbciy new file mode 100644 index 000000000..b34ec55ad Binary files /dev/null and b/c64tests/sbciy differ diff --git a/c64tests/sbcz b/c64tests/sbcz new file mode 100644 index 000000000..4d446e48e Binary files /dev/null and b/c64tests/sbcz differ diff --git a/c64tests/sbczx b/c64tests/sbczx new file mode 100644 index 000000000..fde9acc3a Binary files /dev/null and b/c64tests/sbczx differ diff --git a/c64tests/sbxb b/c64tests/sbxb new file mode 100644 index 000000000..7c6a9b5b1 Binary files /dev/null and b/c64tests/sbxb differ diff --git a/c64tests/secn b/c64tests/secn new file mode 100644 index 000000000..391795d26 Binary files /dev/null and b/c64tests/secn differ diff --git a/c64tests/sedn b/c64tests/sedn new file mode 100644 index 000000000..a9f1e1f6d Binary files /dev/null and b/c64tests/sedn differ diff --git a/c64tests/sein b/c64tests/sein new file mode 100644 index 000000000..e69ce7c3a Binary files /dev/null and b/c64tests/sein differ diff --git a/c64tests/shaay b/c64tests/shaay new file mode 100644 index 000000000..df7b51c44 Binary files /dev/null and b/c64tests/shaay differ diff --git a/c64tests/shaiy b/c64tests/shaiy new file mode 100644 index 000000000..5640d04d8 Binary files /dev/null and b/c64tests/shaiy differ diff --git a/c64tests/shsay b/c64tests/shsay new file mode 100644 index 000000000..88ac4ce34 Binary files /dev/null and b/c64tests/shsay differ diff --git a/c64tests/shxay b/c64tests/shxay new file mode 100644 index 000000000..0918d21d6 Binary files /dev/null and b/c64tests/shxay differ diff --git a/c64tests/shyax b/c64tests/shyax new file mode 100644 index 000000000..74b4f840b Binary files /dev/null and b/c64tests/shyax differ diff --git a/c64tests/staa b/c64tests/staa new file mode 100644 index 000000000..f7350eff7 Binary files /dev/null and b/c64tests/staa differ diff --git a/c64tests/staax b/c64tests/staax new file mode 100644 index 000000000..96d3f80f6 Binary files /dev/null and b/c64tests/staax differ diff --git a/c64tests/staay b/c64tests/staay new file mode 100644 index 000000000..6783682a4 Binary files /dev/null and b/c64tests/staay differ diff --git a/c64tests/staix b/c64tests/staix new file mode 100644 index 000000000..9752dc68e Binary files /dev/null and b/c64tests/staix differ diff --git a/c64tests/staiy b/c64tests/staiy new file mode 100644 index 000000000..a70dfcf1a Binary files /dev/null and b/c64tests/staiy differ diff --git a/c64tests/staz b/c64tests/staz new file mode 100644 index 000000000..f271defc7 Binary files /dev/null and b/c64tests/staz differ diff --git a/c64tests/stazx b/c64tests/stazx new file mode 100644 index 000000000..9bd9a7746 Binary files /dev/null and b/c64tests/stazx differ diff --git a/c64tests/stxa b/c64tests/stxa new file mode 100644 index 000000000..e11db6d5a Binary files /dev/null and b/c64tests/stxa differ diff --git a/c64tests/stxz b/c64tests/stxz new file mode 100644 index 000000000..9bf1c9214 Binary files /dev/null and b/c64tests/stxz differ diff --git a/c64tests/stxzy b/c64tests/stxzy new file mode 100644 index 000000000..ff194a263 Binary files /dev/null and b/c64tests/stxzy differ diff --git a/c64tests/stya b/c64tests/stya new file mode 100644 index 000000000..e520a626e Binary files /dev/null and b/c64tests/stya differ diff --git a/c64tests/styz b/c64tests/styz new file mode 100644 index 000000000..12816e4a2 Binary files /dev/null and b/c64tests/styz differ diff --git a/c64tests/styzx b/c64tests/styzx new file mode 100644 index 000000000..18e0b24cd Binary files /dev/null and b/c64tests/styzx differ diff --git a/c64tests/taxn b/c64tests/taxn new file mode 100644 index 000000000..ab0eaa067 Binary files /dev/null and b/c64tests/taxn differ diff --git a/c64tests/tayn b/c64tests/tayn new file mode 100644 index 000000000..b1bff05d5 Binary files /dev/null and b/c64tests/tayn differ diff --git a/c64tests/trap1 b/c64tests/trap1 new file mode 100644 index 000000000..69e1311bf Binary files /dev/null and b/c64tests/trap1 differ diff --git a/c64tests/trap10 b/c64tests/trap10 new file mode 100644 index 000000000..039c61e00 Binary files /dev/null and b/c64tests/trap10 differ diff --git a/c64tests/trap11 b/c64tests/trap11 new file mode 100644 index 000000000..2bab32054 Binary files /dev/null and b/c64tests/trap11 differ diff --git a/c64tests/trap12 b/c64tests/trap12 new file mode 100644 index 000000000..7407832ef Binary files /dev/null and b/c64tests/trap12 differ diff --git a/c64tests/trap13 b/c64tests/trap13 new file mode 100644 index 000000000..b7545c9b5 Binary files /dev/null and b/c64tests/trap13 differ diff --git a/c64tests/trap14 b/c64tests/trap14 new file mode 100644 index 000000000..1bb487673 Binary files /dev/null and b/c64tests/trap14 differ diff --git a/c64tests/trap15 b/c64tests/trap15 new file mode 100644 index 000000000..f610d1078 Binary files /dev/null and b/c64tests/trap15 differ diff --git a/c64tests/trap16 b/c64tests/trap16 new file mode 100644 index 000000000..64165d06b Binary files /dev/null and b/c64tests/trap16 differ diff --git a/c64tests/trap17 b/c64tests/trap17 new file mode 100644 index 000000000..f0fd40c57 Binary files /dev/null and b/c64tests/trap17 differ diff --git a/c64tests/trap2 b/c64tests/trap2 new file mode 100644 index 000000000..d0ed81742 Binary files /dev/null and b/c64tests/trap2 differ diff --git a/c64tests/trap3 b/c64tests/trap3 new file mode 100644 index 000000000..8b16ad9de Binary files /dev/null and b/c64tests/trap3 differ diff --git a/c64tests/trap4 b/c64tests/trap4 new file mode 100644 index 000000000..124ac747c Binary files /dev/null and b/c64tests/trap4 differ diff --git a/c64tests/trap5 b/c64tests/trap5 new file mode 100644 index 000000000..f8ab1f60a Binary files /dev/null and b/c64tests/trap5 differ diff --git a/c64tests/trap6 b/c64tests/trap6 new file mode 100644 index 000000000..0221dcd69 Binary files /dev/null and b/c64tests/trap6 differ diff --git a/c64tests/trap7 b/c64tests/trap7 new file mode 100644 index 000000000..f573c6f1d Binary files /dev/null and b/c64tests/trap7 differ diff --git a/c64tests/trap8 b/c64tests/trap8 new file mode 100644 index 000000000..b47e19b48 Binary files /dev/null and b/c64tests/trap8 differ diff --git a/c64tests/trap9 b/c64tests/trap9 new file mode 100644 index 000000000..68e8a7fcf Binary files /dev/null and b/c64tests/trap9 differ diff --git a/c64tests/tsxn b/c64tests/tsxn new file mode 100644 index 000000000..d94b43872 Binary files /dev/null and b/c64tests/tsxn differ diff --git a/c64tests/txan b/c64tests/txan new file mode 100644 index 000000000..e9e137e62 Binary files /dev/null and b/c64tests/txan differ diff --git a/c64tests/txsn b/c64tests/txsn new file mode 100644 index 000000000..dde0444af Binary files /dev/null and b/c64tests/txsn differ diff --git a/c64tests/tyan b/c64tests/tyan new file mode 100644 index 000000000..44d844a70 Binary files /dev/null and b/c64tests/tyan differ diff --git a/sim65/bcd_vice_sim.c b/sim65/bcd_vice_sim.c new file mode 100644 index 000000000..4d8cfab96 --- /dev/null +++ b/sim65/bcd_vice_sim.c @@ -0,0 +1,160 @@ +#include + +static int flag_Z; +static int flag_C; +static int flag_N; +static int flag_V; + +unsigned int ADC(unsigned int A, unsigned int value, unsigned int bcd_mode) +{ + unsigned int tmp_value; + unsigned int tmp; + + tmp_value = (value); + + if (bcd_mode) { + tmp = (A & 0xf) + (tmp_value & 0xf) + flag_C; + if (tmp > 0x9) { + tmp += 0x6; + } + if (tmp <= 0x0f) { + tmp = (tmp & 0xf) + (A & 0xf0) + (tmp_value & 0xf0); + } else { + tmp = (tmp & 0xf) + (A & 0xf0) + (tmp_value & 0xf0) + 0x10; + } + flag_Z = !((A + tmp_value + flag_C) & 0xff); + flag_N = tmp & 0x80; + flag_V = ((A ^ tmp) & 0x80) && !((A ^ tmp_value) & 0x80); + if ((tmp & 0x1f0) > 0x90) { + tmp += 0x60; + } + flag_C = (tmp & 0xff0) > 0xf0; + } else { + tmp = tmp_value + A + flag_C; + flag_Z = (tmp&0xff)==0; + flag_N = (tmp&0x80)!=0; + flag_V = !((A ^ tmp_value) & 0x80) && ((A ^ tmp) & 0x80); + flag_C = tmp > 0xff; + } + return tmp & 0xff; +} + +unsigned int SBC(unsigned int A, unsigned int value, unsigned int bcd_mode) +{ + unsigned int src, tmp; + src = (unsigned int)(value); + tmp = A - src - (flag_C ? 0 : 1); + + if (bcd_mode) { + unsigned int tmp_a; + tmp_a = (A & 0xf) - (src & 0xf) - (flag_C ? 0 : 1); + if (tmp_a & 0x10) { + tmp_a = ((tmp_a - 6) & 0xf) | ((A & 0xf0) - (src & 0xf0) - 0x10); + } else { + tmp_a = (tmp_a & 0xf) | ((A & 0xf0) - (src & 0xf0)); + } + if (tmp_a & 0x100) { + tmp_a -= 0x60; + } + flag_C = tmp < 0x100; + flag_Z = (tmp&0xff)==0; + flag_N = (tmp&0x80)!=0; + flag_V = ((A ^ tmp) & 0x80) && ((A ^ src) & 0x80); + return tmp_a && 255; + } else { + flag_Z = (tmp&0xff)==0; + flag_N = (tmp&0x80)!=0; + flag_C = tmp < 0x100; + flag_V = ((A ^ tmp) & 0x80) && ((A ^ src) & 0x80); + return tmp && 255; + } +} + + +void print_result(int result) { + printf(" %02x", result); + printf(" N=%d", flag_N? 1:0); + printf(" V=%d", flag_V? 1:0); + printf(" Z=%d", flag_Z? 1:0); + printf(" C=%d", flag_C? 1:0); + printf("\n"); +} + +int main(char* argv) { + flag_C = flag_N = flag_V = flag_Z = 0; + + for(unsigned int A=0; A<256; ++A) { + for(unsigned int v=0; v<256; ++v) { + flag_C = 0; + printf("adc,normal,carry0: %02x + %02x = ", A, v); + unsigned int result = ADC(A, v, 0); + print_result(result); + } + } + printf("\n"); + for(unsigned int A=0; A<256; ++A) { + for(unsigned int v=0; v<256; ++v) { + flag_C = 1; + printf("adc,normal,carry1: %02x + %02x = ", A, v); + unsigned int result = ADC(A, v, 0); + print_result(result); + } + } + printf("\n"); + for(unsigned int A=0; A<256; ++A) { + for(unsigned int v=0; v<256; ++v) { + flag_C = 0; + printf("adc,bcd,carry0: %02x + %02x = ", A, v); + unsigned int result = ADC(A, v, 1); + print_result(result); + } + } + printf("\n"); + for(unsigned int A=0; A<256; ++A) { + for(unsigned int v=0; v<256; ++v) { + flag_C = 1; + printf("adc,bcd,carry1: %02x + %02x = ", A, v); + unsigned int result = ADC(A, v, 1); + print_result(result); + } + } + + + + for(unsigned int A=0; A<256; ++A) { + for(unsigned int v=0; v<256; ++v) { + flag_C = 0; + printf("sbc,normal,carry0: %02x - %02x = ", A, v); + unsigned int result = SBC(A, v, 0); + print_result(result); + } + } + printf("\n"); + for(unsigned int A=0; A<256; ++A) { + for(unsigned int v=0; v<256; ++v) { + flag_C = 1; + printf("sbc,normal,carry1: %02x - %02x = ", A, v); + unsigned int result = SBC(A, v, 0); + print_result(result); + } + } + printf("\n"); + for(unsigned int A=0; A<256; ++A) { + for(unsigned int v=0; v<256; ++v) { + flag_C = 0; + printf("sbc,bcd,carry0: %02x - %02x = ", A, v); + unsigned int result = SBC(A, v, 1); + print_result(result); + } + } + printf("\n"); + for(unsigned int A=0; A<256; ++A) { + for(unsigned int v=0; v<256; ++v) { + flag_C = 1; + printf("sbc,bcd,carry1: %02x - %02x = ", A, v); + unsigned int result = SBC(A, v, 1); + print_result(result); + } + } +} + diff --git a/sim65/src/C64KernalStubs.kt b/sim65/src/C64KernalStubs.kt index c79567579..caf6e9a33 100644 --- a/sim65/src/C64KernalStubs.kt +++ b/sim65/src/C64KernalStubs.kt @@ -4,6 +4,7 @@ import sim65.components.Address import sim65.components.Cpu6502 import sim65.components.ICpu import sim65.components.Ram +import kotlin.system.exitProcess object C64KernalStubs { @@ -14,10 +15,11 @@ object C64KernalStubs { when(pc) { 0xffd2 -> { // CHROUT - val char = C64Screencodes.decodeScreencode(listOf(cpu.A.toShort()), true) - if(char=="m") + ram[0x030c] = 0 + val char = Petscii.decodePetscii(listOf(cpu.A.toShort()), true).first() + if(char==13.toChar()) println() - else + else if(char in ' '..'~') print(char) cpu.currentOpcode = 0x60 // rts to end the stub } @@ -26,18 +28,18 @@ object C64KernalStubs { print("[Input required:] ") val s = readLine() if(s.isNullOrEmpty()) - cpu.A = 0 + cpu.A = 3 else - cpu.A = C64Screencodes.encodeScreencode(s, true).first().toInt() + cpu.A = Petscii.encodePetscii(s, true).first().toInt() cpu.currentOpcode = 0x60 // rts to end the stub } 0xe16f -> { // LOAD/VERIFY - val loc = ram.read(0xbb).toInt() or (ram.read(0xbc).toInt() shl 8) - val len = ram.read(0xb7).toInt() - val filename = C64Screencodes.decodeScreencode((loc until loc+len).map { ram.read(it) }.toList(), true).toLowerCase() - println("\n[loading $filename ...]") + val loc = ram[0xbb].toInt() or (this.ram[0xbc].toInt() shl 8) + val len = ram[0xb7].toInt() + val filename = Petscii.decodePetscii((loc until loc+len).map { ram[it] }.toList(), true).toLowerCase() ram.loadPrg("c64tests/$filename") + cpu.popStackAddr() cpu.PC = 0x0816 // continue in next module } } diff --git a/sim65/src/C64Screencodes.kt b/sim65/src/C64Screencodes.kt deleted file mode 100644 index 5497de1bf..000000000 --- a/sim65/src/C64Screencodes.kt +++ /dev/null @@ -1,550 +0,0 @@ -package sim65 - -import java.io.CharConversionException - -object C64Screencodes { - - // decoding: from Screencodes (0-255) to unicode - // character tables used from https://github.com/dj51d/cbmcodecs - - private val decodingScreencodeLowercase = arrayOf( - '@' , // @ 0x00 -> COMMERCIAL AT - 'a' , // a 0x01 -> LATIN SMALL LETTER A - 'b' , // b 0x02 -> LATIN SMALL LETTER B - 'c' , // c 0x03 -> LATIN SMALL LETTER C - 'd' , // d 0x04 -> LATIN SMALL LETTER D - 'e' , // e 0x05 -> LATIN SMALL LETTER E - 'f' , // f 0x06 -> LATIN SMALL LETTER F - 'g' , // g 0x07 -> LATIN SMALL LETTER G - 'h' , // h 0x08 -> LATIN SMALL LETTER H - 'i' , // i 0x09 -> LATIN SMALL LETTER I - 'j' , // j 0x0A -> LATIN SMALL LETTER J - 'k' , // k 0x0B -> LATIN SMALL LETTER K - 'l' , // l 0x0C -> LATIN SMALL LETTER L - 'm' , // m 0x0D -> LATIN SMALL LETTER M - 'n' , // n 0x0E -> LATIN SMALL LETTER N - 'o' , // o 0x0F -> LATIN SMALL LETTER O - 'p' , // p 0x10 -> LATIN SMALL LETTER P - 'q' , // q 0x11 -> LATIN SMALL LETTER Q - 'r' , // r 0x12 -> LATIN SMALL LETTER R - 's' , // s 0x13 -> LATIN SMALL LETTER S - 't' , // t 0x14 -> LATIN SMALL LETTER T - 'u' , // u 0x15 -> LATIN SMALL LETTER U - 'v' , // v 0x16 -> LATIN SMALL LETTER V - 'w' , // w 0x17 -> LATIN SMALL LETTER W - 'x' , // x 0x18 -> LATIN SMALL LETTER X - 'y' , // y 0x19 -> LATIN SMALL LETTER Y - 'z' , // z 0x1A -> LATIN SMALL LETTER Z - '[' , // [ 0x1B -> LEFT SQUARE BRACKET - '\u00a3', // £ 0x1C -> POUND SIGN - ']' , // ] 0x1D -> RIGHT SQUARE BRACKET - '\u2191', // ↑ 0x1E -> UPWARDS ARROW - '\u2190', // ← 0x1F -> LEFTWARDS ARROW - ' ' , // 0x20 -> SPACE - '!' , // ! 0x21 -> EXCLAMATION MARK - '"' , // " 0x22 -> QUOTATION MARK - '#' , // # 0x23 -> NUMBER SIGN - '$' , // $ 0x24 -> DOLLAR SIGN - '%' , // % 0x25 -> PERCENT SIGN - '&' , // & 0x26 -> AMPERSAND - '\'' , // ' 0x27 -> APOSTROPHE - '(' , // ( 0x28 -> LEFT PARENTHESIS - ')' , // ) 0x29 -> RIGHT PARENTHESIS - '*' , // * 0x2A -> ASTERISK - '+' , // + 0x2B -> PLUS SIGN - ',' , // , 0x2C -> COMMA - '-' , // - 0x2D -> HYPHEN-MINUS - '.' , // . 0x2E -> FULL STOP - '/' , // / 0x2F -> SOLIDUS - '0' , // 0 0x30 -> DIGIT ZERO - '1' , // 1 0x31 -> DIGIT ONE - '2' , // 2 0x32 -> DIGIT TWO - '3' , // 3 0x33 -> DIGIT THREE - '4' , // 4 0x34 -> DIGIT FOUR - '5' , // 5 0x35 -> DIGIT FIVE - '6' , // 6 0x36 -> DIGIT SIX - '7' , // 7 0x37 -> DIGIT SEVEN - '8' , // 8 0x38 -> DIGIT EIGHT - '9' , // 9 0x39 -> DIGIT NINE - ':' , // : 0x3A -> COLON - ';' , // ; 0x3B -> SEMICOLON - '<' , // < 0x3C -> LESS-THAN SIGN - '=' , // = 0x3D -> EQUALS SIGN - '>' , // > 0x3E -> GREATER-THAN SIGN - '?' , // ? 0x3F -> QUESTION MARK - '\u2500', // ─ 0x40 -> BOX DRAWINGS LIGHT HORIZONTAL - 'A' , // A 0x41 -> LATIN CAPITAL LETTER A - 'B' , // B 0x42 -> LATIN CAPITAL LETTER B - 'C' , // C 0x43 -> LATIN CAPITAL LETTER C - 'D' , // D 0x44 -> LATIN CAPITAL LETTER D - 'E' , // E 0x45 -> LATIN CAPITAL LETTER E - 'F' , // F 0x46 -> LATIN CAPITAL LETTER F - 'G' , // G 0x47 -> LATIN CAPITAL LETTER G - 'H' , // H 0x48 -> LATIN CAPITAL LETTER H - 'I' , // I 0x49 -> LATIN CAPITAL LETTER I - 'J' , // J 0x4A -> LATIN CAPITAL LETTER J - 'K' , // K 0x4B -> LATIN CAPITAL LETTER K - 'L' , // L 0x4C -> LATIN CAPITAL LETTER L - 'M' , // M 0x4D -> LATIN CAPITAL LETTER M - 'N' , // N 0x4E -> LATIN CAPITAL LETTER N - 'O' , // O 0x4F -> LATIN CAPITAL LETTER O - 'P' , // P 0x50 -> LATIN CAPITAL LETTER P - 'Q' , // Q 0x51 -> LATIN CAPITAL LETTER Q - 'R' , // R 0x52 -> LATIN CAPITAL LETTER R - 'S' , // S 0x53 -> LATIN CAPITAL LETTER S - 'T' , // T 0x54 -> LATIN CAPITAL LETTER T - 'U' , // U 0x55 -> LATIN CAPITAL LETTER U - 'V' , // V 0x56 -> LATIN CAPITAL LETTER V - 'W' , // W 0x57 -> LATIN CAPITAL LETTER W - 'X' , // X 0x58 -> LATIN CAPITAL LETTER X - 'Y' , // Y 0x59 -> LATIN CAPITAL LETTER Y - 'Z' , // Z 0x5A -> LATIN CAPITAL LETTER Z - '\u253c', // ┼ 0x5B -> BOX DRAWINGS LIGHT VERTICAL AND HORIZONTAL - '\uf12e', //  0x5C -> LEFT HALF BLOCK MEDIUM SHADE (CUS) - '\u2502', // │ 0x5D -> BOX DRAWINGS LIGHT VERTICAL - '\u2592', // ▒ 0x5E -> MEDIUM SHADE - '\uf139', //  0x5F -> MEDIUM SHADE SLASHED LEFT (CUS) - '\u00a0', // 0x60 -> NO-BREAK SPACE - '\u258c', // ▌ 0x61 -> LEFT HALF BLOCK - '\u2584', // ▄ 0x62 -> LOWER HALF BLOCK - '\u2594', // ▔ 0x63 -> UPPER ONE EIGHTH BLOCK - '\u2581', // ▁ 0x64 -> LOWER ONE EIGHTH BLOCK - '\u258f', // ▏ 0x65 -> LEFT ONE EIGHTH BLOCK - '\u2592', // ▒ 0x66 -> MEDIUM SHADE - '\u2595', // ▕ 0x67 -> RIGHT ONE EIGHTH BLOCK - '\uf12f', //  0x68 -> LOWER HALF BLOCK MEDIUM SHADE (CUS) - '\uf13a', //  0x69 -> MEDIUM SHADE SLASHED RIGHT (CUS) - '\uf130', //  0x6A -> RIGHT ONE QUARTER BLOCK (CUS) - '\u251c', // ├ 0x6B -> BOX DRAWINGS LIGHT VERTICAL AND RIGHT - '\u2597', // ▗ 0x6C -> QUADRANT LOWER RIGHT - '\u2514', // └ 0x6D -> BOX DRAWINGS LIGHT UP AND RIGHT - '\u2510', // ┐ 0x6E -> BOX DRAWINGS LIGHT DOWN AND LEFT - '\u2582', // ▂ 0x6F -> LOWER ONE QUARTER BLOCK - '\u250c', // ┌ 0x70 -> BOX DRAWINGS LIGHT DOWN AND RIGHT - '\u2534', // ┴ 0x71 -> BOX DRAWINGS LIGHT UP AND HORIZONTAL - '\u252c', // ┬ 0x72 -> BOX DRAWINGS LIGHT DOWN AND HORIZONTAL - '\u2524', // ┤ 0x73 -> BOX DRAWINGS LIGHT VERTICAL AND LEFT - '\u258e', // ▎ 0x74 -> LEFT ONE QUARTER BLOCK - '\u258d', // ▍ 0x75 -> LEFT THREE EIGTHS BLOCK - '\uf131', //  0x76 -> RIGHT THREE EIGHTHS BLOCK (CUS) - '\uf132', //  0x77 -> UPPER ONE QUARTER BLOCK (CUS) - '\uf133', //  0x78 -> UPPER THREE EIGHTS BLOCK (CUS) - '\u2583', // ▃ 0x79 -> LOWER THREE EIGHTHS BLOCK - '\u2713', // ✓ 0x7A -> CHECK MARK - '\u2596', // ▖ 0x7B -> QUADRANT LOWER LEFT - '\u259d', // ▝ 0x7C -> QUADRANT UPPER RIGHT - '\u2518', // ┘ 0x7D -> BOX DRAWINGS LIGHT UP AND LEFT - '\u2598', // ▘ 0x7E -> QUADRANT UPPER LEFT - '\u259a', // ▚ 0x7F -> QUADRANT UPPER LEFT AND LOWER RIGHT - '\ufffe', // 0x80 -> UNDEFINED - '\ufffe', // 0x81 -> UNDEFINED - '\ufffe', // 0x82 -> UNDEFINED - '\ufffe', // 0x83 -> UNDEFINED - '\ufffe', // 0x84 -> UNDEFINED - '\ufffe', // 0x85 -> UNDEFINED - '\ufffe', // 0x86 -> UNDEFINED - '\ufffe', // 0x87 -> UNDEFINED - '\ufffe', // 0x88 -> UNDEFINED - '\ufffe', // 0x89 -> UNDEFINED - '\ufffe', // 0x8A -> UNDEFINED - '\ufffe', // 0x8B -> UNDEFINED - '\ufffe', // 0x8C -> UNDEFINED - '\ufffe', // 0x8D -> UNDEFINED - '\ufffe', // 0x8E -> UNDEFINED - '\ufffe', // 0x8F -> UNDEFINED - '\ufffe', // 0x90 -> UNDEFINED - '\ufffe', // 0x91 -> UNDEFINED - '\ufffe', // 0x92 -> UNDEFINED - '\ufffe', // 0x93 -> UNDEFINED - '\ufffe', // 0x94 -> UNDEFINED - '\ufffe', // 0x95 -> UNDEFINED - '\ufffe', // 0x96 -> UNDEFINED - '\ufffe', // 0x97 -> UNDEFINED - '\ufffe', // 0x98 -> UNDEFINED - '\ufffe', // 0x99 -> UNDEFINED - '\ufffe', // 0x9A -> UNDEFINED - '\ufffe', // 0x9B -> UNDEFINED - '\ufffe', // 0x9C -> UNDEFINED - '\ufffe', // 0x9D -> UNDEFINED - '\ufffe', // 0x9E -> UNDEFINED - '\ufffe', // 0x9F -> UNDEFINED - '\ufffe', // 0xA0 -> UNDEFINED - '\ufffe', // 0xA1 -> UNDEFINED - '\ufffe', // 0xA2 -> UNDEFINED - '\ufffe', // 0xA3 -> UNDEFINED - '\ufffe', // 0xA4 -> UNDEFINED - '\ufffe', // 0xA5 -> UNDEFINED - '\ufffe', // 0xA6 -> UNDEFINED - '\ufffe', // 0xA7 -> UNDEFINED - '\ufffe', // 0xA8 -> UNDEFINED - '\ufffe', // 0xA9 -> UNDEFINED - '\ufffe', // 0xAA -> UNDEFINED - '\ufffe', // 0xAB -> UNDEFINED - '\ufffe', // 0xAC -> UNDEFINED - '\ufffe', // 0xAD -> UNDEFINED - '\ufffe', // 0xAE -> UNDEFINED - '\ufffe', // 0xAF -> UNDEFINED - '\ufffe', // 0xB0 -> UNDEFINED - '\ufffe', // 0xB1 -> UNDEFINED - '\ufffe', // 0xB2 -> UNDEFINED - '\ufffe', // 0xB3 -> UNDEFINED - '\ufffe', // 0xB4 -> UNDEFINED - '\ufffe', // 0xB5 -> UNDEFINED - '\ufffe', // 0xB6 -> UNDEFINED - '\ufffe', // 0xB7 -> UNDEFINED - '\ufffe', // 0xB8 -> UNDEFINED - '\ufffe', // 0xB9 -> UNDEFINED - '\ufffe', // 0xBA -> UNDEFINED - '\ufffe', // 0xBB -> UNDEFINED - '\ufffe', // 0xBC -> UNDEFINED - '\ufffe', // 0xBD -> UNDEFINED - '\ufffe', // 0xBE -> UNDEFINED - '\ufffe', // 0xBF -> UNDEFINED - '\ufffe', // 0xC0 -> UNDEFINED - '\ufffe', // 0xC1 -> UNDEFINED - '\ufffe', // 0xC2 -> UNDEFINED - '\ufffe', // 0xC3 -> UNDEFINED - '\ufffe', // 0xC4 -> UNDEFINED - '\ufffe', // 0xC5 -> UNDEFINED - '\ufffe', // 0xC6 -> UNDEFINED - '\ufffe', // 0xC7 -> UNDEFINED - '\ufffe', // 0xC8 -> UNDEFINED - '\ufffe', // 0xC9 -> UNDEFINED - '\ufffe', // 0xCA -> UNDEFINED - '\ufffe', // 0xCB -> UNDEFINED - '\ufffe', // 0xCC -> UNDEFINED - '\ufffe', // 0xCD -> UNDEFINED - '\ufffe', // 0xCE -> UNDEFINED - '\ufffe', // 0xCF -> UNDEFINED - '\ufffe', // 0xD0 -> UNDEFINED - '\ufffe', // 0xD1 -> UNDEFINED - '\ufffe', // 0xD2 -> UNDEFINED - '\ufffe', // 0xD3 -> UNDEFINED - '\ufffe', // 0xD4 -> UNDEFINED - '\ufffe', // 0xD5 -> UNDEFINED - '\ufffe', // 0xD6 -> UNDEFINED - '\ufffe', // 0xD7 -> UNDEFINED - '\ufffe', // 0xD8 -> UNDEFINED - '\ufffe', // 0xD9 -> UNDEFINED - '\ufffe', // 0xDA -> UNDEFINED - '\ufffe', // 0xDB -> UNDEFINED - '\ufffe', // 0xDC -> UNDEFINED - '\ufffe', // 0xDD -> UNDEFINED - '\ufffe', // 0xDE -> UNDEFINED - '\ufffe', // 0xDF -> UNDEFINED - '\ufffe', // 0xE0 -> UNDEFINED - '\ufffe', // 0xE1 -> UNDEFINED - '\ufffe', // 0xE2 -> UNDEFINED - '\ufffe', // 0xE3 -> UNDEFINED - '\ufffe', // 0xE4 -> UNDEFINED - '\ufffe', // 0xE5 -> UNDEFINED - '\ufffe', // 0xE6 -> UNDEFINED - '\ufffe', // 0xE7 -> UNDEFINED - '\ufffe', // 0xE8 -> UNDEFINED - '\ufffe', // 0xE9 -> UNDEFINED - '\ufffe', // 0xEA -> UNDEFINED - '\ufffe', // 0xEB -> UNDEFINED - '\ufffe', // 0xEC -> UNDEFINED - '\ufffe', // 0xED -> UNDEFINED - '\ufffe', // 0xEE -> UNDEFINED - '\ufffe', // 0xEF -> UNDEFINED - '\ufffe', // 0xF0 -> UNDEFINED - '\ufffe', // 0xF1 -> UNDEFINED - '\ufffe', // 0xF2 -> UNDEFINED - '\ufffe', // 0xF3 -> UNDEFINED - '\ufffe', // 0xF4 -> UNDEFINED - '\ufffe', // 0xF5 -> UNDEFINED - '\ufffe', // 0xF6 -> UNDEFINED - '\ufffe', // 0xF7 -> UNDEFINED - '\ufffe', // 0xF8 -> UNDEFINED - '\ufffe', // 0xF9 -> UNDEFINED - '\ufffe', // 0xFA -> UNDEFINED - '\ufffe', // 0xFB -> UNDEFINED - '\ufffe', // 0xFC -> UNDEFINED - '\ufffe', // 0xFD -> UNDEFINED - '\ufffe', // 0xFE -> UNDEFINED - '\ufffe' // 0xFF -> UNDEFINED - ) - - private val decodingScreencodeUppercase = arrayOf( - '@' , // @ 0x00 -> COMMERCIAL AT - 'A' , // A 0x01 -> LATIN CAPITAL LETTER A - 'B' , // B 0x02 -> LATIN CAPITAL LETTER B - 'C' , // C 0x03 -> LATIN CAPITAL LETTER C - 'D' , // D 0x04 -> LATIN CAPITAL LETTER D - 'E' , // E 0x05 -> LATIN CAPITAL LETTER E - 'F' , // F 0x06 -> LATIN CAPITAL LETTER F - 'G' , // G 0x07 -> LATIN CAPITAL LETTER G - 'H' , // H 0x08 -> LATIN CAPITAL LETTER H - 'I' , // I 0x09 -> LATIN CAPITAL LETTER I - 'J' , // J 0x0A -> LATIN CAPITAL LETTER J - 'K' , // K 0x0B -> LATIN CAPITAL LETTER K - 'L' , // L 0x0C -> LATIN CAPITAL LETTER L - 'M' , // M 0x0D -> LATIN CAPITAL LETTER M - 'N' , // N 0x0E -> LATIN CAPITAL LETTER N - 'O' , // O 0x0F -> LATIN CAPITAL LETTER O - 'P' , // P 0x10 -> LATIN CAPITAL LETTER P - 'Q' , // Q 0x11 -> LATIN CAPITAL LETTER Q - 'R' , // R 0x12 -> LATIN CAPITAL LETTER R - 'S' , // S 0x13 -> LATIN CAPITAL LETTER S - 'T' , // T 0x14 -> LATIN CAPITAL LETTER T - 'U' , // U 0x15 -> LATIN CAPITAL LETTER U - 'V' , // V 0x16 -> LATIN CAPITAL LETTER V - 'W' , // W 0x17 -> LATIN CAPITAL LETTER W - 'X' , // X 0x18 -> LATIN CAPITAL LETTER X - 'Y' , // Y 0x19 -> LATIN CAPITAL LETTER Y - 'Z' , // Z 0x1A -> LATIN CAPITAL LETTER Z - '[' , // [ 0x1B -> LEFT SQUARE BRACKET - '\u00a3', // £ 0x1C -> POUND SIGN - ']' , // ] 0x1D -> RIGHT SQUARE BRACKET - '\u2191', // ↑ 0x1E -> UPWARDS ARROW - '\u2190', // ← 0x1F -> LEFTWARDS ARROW - ' ' , // 0x20 -> SPACE - '!' , // ! 0x21 -> EXCLAMATION MARK - '"' , // " 0x22 -> QUOTATION MARK - '#' , // # 0x23 -> NUMBER SIGN - '$' , // $ 0x24 -> DOLLAR SIGN - '%' , // % 0x25 -> PERCENT SIGN - '&' , // & 0x26 -> AMPERSAND - '\'' , // ' 0x27 -> APOSTROPHE - '(' , // ( 0x28 -> LEFT PARENTHESIS - ')' , // ) 0x29 -> RIGHT PARENTHESIS - '*' , // * 0x2A -> ASTERISK - '+' , // + 0x2B -> PLUS SIGN - ',' , // , 0x2C -> COMMA - '-' , // - 0x2D -> HYPHEN-MINUS - '.' , // . 0x2E -> FULL STOP - '/' , // / 0x2F -> SOLIDUS - '0' , // 0 0x30 -> DIGIT ZERO - '1' , // 1 0x31 -> DIGIT ONE - '2' , // 2 0x32 -> DIGIT TWO - '3' , // 3 0x33 -> DIGIT THREE - '4' , // 4 0x34 -> DIGIT FOUR - '5' , // 5 0x35 -> DIGIT FIVE - '6' , // 6 0x36 -> DIGIT SIX - '7' , // 7 0x37 -> DIGIT SEVEN - '8' , // 8 0x38 -> DIGIT EIGHT - '9' , // 9 0x39 -> DIGIT NINE - ':' , // : 0x3A -> COLON - ';' , // ; 0x3B -> SEMICOLON - '<' , // < 0x3C -> LESS-THAN SIGN - '=' , // = 0x3D -> EQUALS SIGN - '>' , // > 0x3E -> GREATER-THAN SIGN - '?' , // ? 0x3F -> QUESTION MARK - '\u2500', // ─ 0x40 -> BOX DRAWINGS LIGHT HORIZONTAL - '\u2660', // ♠ 0x41 -> BLACK SPADE SUIT - '\u2502', // │ 0x42 -> BOX DRAWINGS LIGHT VERTICAL - '\u2500', // ─ 0x43 -> BOX DRAWINGS LIGHT HORIZONTAL - '\uf122', //  0x44 -> BOX DRAWINGS LIGHT HORIZONTAL ONE QUARTER UP (CUS) - '\uf123', //  0x45 -> BOX DRAWINGS LIGHT HORIZONTAL TWO QUARTERS UP (CUS) - '\uf124', //  0x46 -> BOX DRAWINGS LIGHT HORIZONTAL ONE QUARTER DOWN (CUS) - '\uf126', //  0x47 -> BOX DRAWINGS LIGHT VERTICAL ONE QUARTER LEFT (CUS) - '\uf128', //  0x48 -> BOX DRAWINGS LIGHT VERTICAL ONE QUARTER RIGHT (CUS) - '\u256e', // ╮ 0x49 -> BOX DRAWINGS LIGHT ARC DOWN AND LEFT - '\u2570', // ╰ 0x4A -> BOX DRAWINGS LIGHT ARC UP AND RIGHT - '\u256f', // ╯ 0x4B -> BOX DRAWINGS LIGHT ARC UP AND LEFT - '\uf12a', //  0x4C -> ONE EIGHTH BLOCK UP AND RIGHT (CUS) - '\u2572', // ╲ 0x4D -> BOX DRAWINGS LIGHT DIAGONAL UPPER LEFT TO LOWER RIGHT - '\u2571', // ╱ 0x4E -> BOX DRAWINGS LIGHT DIAGONAL UPPER RIGHT TO LOWER LEFT - '\uf12b', //  0x4F -> ONE EIGHTH BLOCK DOWN AND RIGHT (CUS) - '\uf12c', //  0x50 -> ONE EIGHTH BLOCK DOWN AND LEFT (CUS) - '\u25cf', // ● 0x51 -> BLACK CIRCLE - '\uf125', //  0x52 -> BOX DRAWINGS LIGHT HORIZONTAL TWO QUARTERS DOWN (CUS) - '\u2665', // ♥ 0x53 -> BLACK HEART SUIT - '\uf127', //  0x54 -> BOX DRAWINGS LIGHT VERTICAL TWO QUARTERS LEFT (CUS) - '\u256d', // ╭ 0x55 -> BOX DRAWINGS LIGHT ARC DOWN AND RIGHT - '\u2573', // ╳ 0x56 -> BOX DRAWINGS LIGHT DIAGONAL CROSS - '\u25cb', // ○ 0x57 -> WHITE CIRCLE - '\u2663', // ♣ 0x58 -> BLACK CLUB SUIT - '\uf129', //  0x59 -> BOX DRAWINGS LIGHT VERTICAL TWO QUARTERS RIGHT (CUS) - '\u2666', // ♦ 0x5A -> BLACK DIAMOND SUIT - '\u253c', // ┼ 0x5B -> BOX DRAWINGS LIGHT VERTICAL AND HORIZONTAL - '\uf12e', //  0x5C -> LEFT HALF BLOCK MEDIUM SHADE (CUS) - '\u2502', // │ 0x5D -> BOX DRAWINGS LIGHT VERTICAL - '\u03c0', // π 0x5E -> GREEK SMALL LETTER PI - '\u25e5', // ◥ 0x5F -> BLACK UPPER RIGHT TRIANGLE - '\u00a0', // 0x60 -> NO-BREAK SPACE - '\u258c', // ▌ 0x61 -> LEFT HALF BLOCK - '\u2584', // ▄ 0x62 -> LOWER HALF BLOCK - '\u2594', // ▔ 0x63 -> UPPER ONE EIGHTH BLOCK - '\u2581', // ▁ 0x64 -> LOWER ONE EIGHTH BLOCK - '\u258f', // ▏ 0x65 -> LEFT ONE EIGHTH BLOCK - '\u2592', // ▒ 0x66 -> MEDIUM SHADE - '\u2595', // ▕ 0x67 -> RIGHT ONE EIGHTH BLOCK - '\uf12f', //  0x68 -> LOWER HALF BLOCK MEDIUM SHADE (CUS) - '\u25e4', // ◤ 0x69 -> BLACK UPPER LEFT TRIANGLE - '\uf130', //  0x6A -> RIGHT ONE QUARTER BLOCK (CUS) - '\u251c', // ├ 0x6B -> BOX DRAWINGS LIGHT VERTICAL AND RIGHT - '\u2597', // ▗ 0x6C -> QUADRANT LOWER RIGHT - '\u2514', // └ 0x6D -> BOX DRAWINGS LIGHT UP AND RIGHT - '\u2510', // ┐ 0x6E -> BOX DRAWINGS LIGHT DOWN AND LEFT - '\u2582', // ▂ 0x6F -> LOWER ONE QUARTER BLOCK - '\u250c', // ┌ 0x70 -> BOX DRAWINGS LIGHT DOWN AND RIGHT - '\u2534', // ┴ 0x71 -> BOX DRAWINGS LIGHT UP AND HORIZONTAL - '\u252c', // ┬ 0x72 -> BOX DRAWINGS LIGHT DOWN AND HORIZONTAL - '\u2524', // ┤ 0x73 -> BOX DRAWINGS LIGHT VERTICAL AND LEFT - '\u258e', // ▎ 0x74 -> LEFT ONE QUARTER BLOCK - '\u258d', // ▍ 0x75 -> LEFT THREE EIGTHS BLOCK - '\uf131', //  0x76 -> RIGHT THREE EIGHTHS BLOCK (CUS) - '\uf132', //  0x77 -> UPPER ONE QUARTER BLOCK (CUS) - '\uf133', //  0x78 -> UPPER THREE EIGHTS BLOCK (CUS) - '\u2583', // ▃ 0x79 -> LOWER THREE EIGHTHS BLOCK - '\uf12d', //  0x7A -> ONE EIGHTH BLOCK UP AND LEFT (CUS) - '\u2596', // ▖ 0x7B -> QUADRANT LOWER LEFT - '\u259d', // ▝ 0x7C -> QUADRANT UPPER RIGHT - '\u2518', // ┘ 0x7D -> BOX DRAWINGS LIGHT UP AND LEFT - '\u2598', // ▘ 0x7E -> QUADRANT UPPER LEFT - '\u259a', // ▚ 0x7F -> QUADRANT UPPER LEFT AND LOWER RIGHT - '\ufffe', // 0x80 -> UNDEFINED - '\ufffe', // 0x81 -> UNDEFINED - '\ufffe', // 0x82 -> UNDEFINED - '\ufffe', // 0x83 -> UNDEFINED - '\ufffe', // 0x84 -> UNDEFINED - '\ufffe', // 0x85 -> UNDEFINED - '\ufffe', // 0x86 -> UNDEFINED - '\ufffe', // 0x87 -> UNDEFINED - '\ufffe', // 0x88 -> UNDEFINED - '\ufffe', // 0x89 -> UNDEFINED - '\ufffe', // 0x8A -> UNDEFINED - '\ufffe', // 0x8B -> UNDEFINED - '\ufffe', // 0x8C -> UNDEFINED - '\ufffe', // 0x8D -> UNDEFINED - '\ufffe', // 0x8E -> UNDEFINED - '\ufffe', // 0x8F -> UNDEFINED - '\ufffe', // 0x90 -> UNDEFINED - '\ufffe', // 0x91 -> UNDEFINED - '\ufffe', // 0x92 -> UNDEFINED - '\ufffe', // 0x93 -> UNDEFINED - '\ufffe', // 0x94 -> UNDEFINED - '\ufffe', // 0x95 -> UNDEFINED - '\ufffe', // 0x96 -> UNDEFINED - '\ufffe', // 0x97 -> UNDEFINED - '\ufffe', // 0x98 -> UNDEFINED - '\ufffe', // 0x99 -> UNDEFINED - '\ufffe', // 0x9A -> UNDEFINED - '\ufffe', // 0x9B -> UNDEFINED - '\ufffe', // 0x9C -> UNDEFINED - '\ufffe', // 0x9D -> UNDEFINED - '\ufffe', // 0x9E -> UNDEFINED - '\ufffe', // 0x9F -> UNDEFINED - '\ufffe', // 0xA0 -> UNDEFINED - '\ufffe', // 0xA1 -> UNDEFINED - '\ufffe', // 0xA2 -> UNDEFINED - '\ufffe', // 0xA3 -> UNDEFINED - '\ufffe', // 0xA4 -> UNDEFINED - '\ufffe', // 0xA5 -> UNDEFINED - '\ufffe', // 0xA6 -> UNDEFINED - '\ufffe', // 0xA7 -> UNDEFINED - '\ufffe', // 0xA8 -> UNDEFINED - '\ufffe', // 0xA9 -> UNDEFINED - '\ufffe', // 0xAA -> UNDEFINED - '\ufffe', // 0xAB -> UNDEFINED - '\ufffe', // 0xAC -> UNDEFINED - '\ufffe', // 0xAD -> UNDEFINED - '\ufffe', // 0xAE -> UNDEFINED - '\ufffe', // 0xAF -> UNDEFINED - '\ufffe', // 0xB0 -> UNDEFINED - '\ufffe', // 0xB1 -> UNDEFINED - '\ufffe', // 0xB2 -> UNDEFINED - '\ufffe', // 0xB3 -> UNDEFINED - '\ufffe', // 0xB4 -> UNDEFINED - '\ufffe', // 0xB5 -> UNDEFINED - '\ufffe', // 0xB6 -> UNDEFINED - '\ufffe', // 0xB7 -> UNDEFINED - '\ufffe', // 0xB8 -> UNDEFINED - '\ufffe', // 0xB9 -> UNDEFINED - '\ufffe', // 0xBA -> UNDEFINED - '\ufffe', // 0xBB -> UNDEFINED - '\ufffe', // 0xBC -> UNDEFINED - '\ufffe', // 0xBD -> UNDEFINED - '\ufffe', // 0xBE -> UNDEFINED - '\ufffe', // 0xBF -> UNDEFINED - '\ufffe', // 0xC0 -> UNDEFINED - '\ufffe', // 0xC1 -> UNDEFINED - '\ufffe', // 0xC2 -> UNDEFINED - '\ufffe', // 0xC3 -> UNDEFINED - '\ufffe', // 0xC4 -> UNDEFINED - '\ufffe', // 0xC5 -> UNDEFINED - '\ufffe', // 0xC6 -> UNDEFINED - '\ufffe', // 0xC7 -> UNDEFINED - '\ufffe', // 0xC8 -> UNDEFINED - '\ufffe', // 0xC9 -> UNDEFINED - '\ufffe', // 0xCA -> UNDEFINED - '\ufffe', // 0xCB -> UNDEFINED - '\ufffe', // 0xCC -> UNDEFINED - '\ufffe', // 0xCD -> UNDEFINED - '\ufffe', // 0xCE -> UNDEFINED - '\ufffe', // 0xCF -> UNDEFINED - '\ufffe', // 0xD0 -> UNDEFINED - '\ufffe', // 0xD1 -> UNDEFINED - '\ufffe', // 0xD2 -> UNDEFINED - '\ufffe', // 0xD3 -> UNDEFINED - '\ufffe', // 0xD4 -> UNDEFINED - '\ufffe', // 0xD5 -> UNDEFINED - '\ufffe', // 0xD6 -> UNDEFINED - '\ufffe', // 0xD7 -> UNDEFINED - '\ufffe', // 0xD8 -> UNDEFINED - '\ufffe', // 0xD9 -> UNDEFINED - '\ufffe', // 0xDA -> UNDEFINED - '\ufffe', // 0xDB -> UNDEFINED - '\ufffe', // 0xDC -> UNDEFINED - '\ufffe', // 0xDD -> UNDEFINED - '\ufffe', // 0xDE -> UNDEFINED - '\ufffe', // 0xDF -> UNDEFINED - '\ufffe', // 0xE0 -> UNDEFINED - '\ufffe', // 0xE1 -> UNDEFINED - '\ufffe', // 0xE2 -> UNDEFINED - '\ufffe', // 0xE3 -> UNDEFINED - '\ufffe', // 0xE4 -> UNDEFINED - '\ufffe', // 0xE5 -> UNDEFINED - '\ufffe', // 0xE6 -> UNDEFINED - '\ufffe', // 0xE7 -> UNDEFINED - '\ufffe', // 0xE8 -> UNDEFINED - '\ufffe', // 0xE9 -> UNDEFINED - '\ufffe', // 0xEA -> UNDEFINED - '\ufffe', // 0xEB -> UNDEFINED - '\ufffe', // 0xEC -> UNDEFINED - '\ufffe', // 0xED -> UNDEFINED - '\ufffe', // 0xEE -> UNDEFINED - '\ufffe', // 0xEF -> UNDEFINED - '\ufffe', // 0xF0 -> UNDEFINED - '\ufffe', // 0xF1 -> UNDEFINED - '\ufffe', // 0xF2 -> UNDEFINED - '\ufffe', // 0xF3 -> UNDEFINED - '\ufffe', // 0xF4 -> UNDEFINED - '\ufffe', // 0xF5 -> UNDEFINED - '\ufffe', // 0xF6 -> UNDEFINED - '\ufffe', // 0xF7 -> UNDEFINED - '\ufffe', // 0xF8 -> UNDEFINED - '\ufffe', // 0xF9 -> UNDEFINED - '\ufffe', // 0xFA -> UNDEFINED - '\ufffe', // 0xFB -> UNDEFINED - '\ufffe', // 0xFC -> UNDEFINED - '\ufffe', // 0xFD -> UNDEFINED - '\ufffe', // 0xFE -> UNDEFINED - '\ufffe' // 0xFF -> UNDEFINED - ) - - // encoding: from unicode to Screencodes (0-255) - private val encodingScreencodeLowercase = decodingScreencodeLowercase.withIndex().associate{it.value to it.index} - private val encodingScreencodeUppercase = decodingScreencodeUppercase.withIndex().associate{it.value to it.index} - - - fun encodeScreencode(text: String, lowercase: Boolean = false): List { - val lookup = if(lowercase) encodingScreencodeLowercase else encodingScreencodeUppercase - return text.map{ - val screencode = lookup[it] - screencode?.toShort() ?: if(it=='\u0000') - 0.toShort() - else { - val case = if (lowercase) "lower" else "upper" - throw CharConversionException("no ${case}Screencode character for '$it'") - } - } - } - - fun decodeScreencode(screencode: Iterable, lowercase: Boolean = false): String { - val decodeTable = if(lowercase) decodingScreencodeLowercase else decodingScreencodeUppercase - return screencode.map { decodeTable[it.toInt()] }.joinToString("") - } -} diff --git a/sim65/src/Petscii.kt b/sim65/src/Petscii.kt new file mode 100644 index 000000000..009edcf22 --- /dev/null +++ b/sim65/src/Petscii.kt @@ -0,0 +1,1121 @@ +package sim65 + +import java.io.CharConversionException + +object Petscii { + + // decoding: from Petscii/Screencodes (0-255) to unicode + // character tables used from https://github.com/dj51d/cbmcodecs + + private val decodingPetsciiLowercase = arrayOf( + '\u0000', // 0x00 -> \u0000 + '\ufffe', // 0x01 -> UNDEFINED + '\ufffe', // 0x02 -> UNDEFINED + '\ufffe', // 0x03 -> UNDEFINED + '\ufffe', // 0x04 -> UNDEFINED + '\uf100', // 0x05 -> WHITE COLOR SWITCH (CUS) + '\ufffe', // 0x06 -> UNDEFINED + '\ufffe', // 0x07 -> UNDEFINED + '\uf118', // 0x08 -> DISABLE CHARACTER SET SWITCHING (CUS) + '\uf119', // 0x09 -> ENABLE CHARACTER SET SWITCHING (CUS) + '\ufffe', // 0x0A -> UNDEFINED + '\ufffe', // 0x0B -> UNDEFINED + '\ufffe', // 0x0C -> UNDEFINED + '\r' , // 0x0D -> CARRIAGE RETURN + '\u000e', // 0x0E -> SHIFT OUT + '\ufffe', // 0x0F -> UNDEFINED + '\ufffe', // 0x10 -> UNDEFINED + '\uf11c', // 0x11 -> CURSOR DOWN (CUS) + '\uf11a', // 0x12 -> REVERSE VIDEO ON (CUS) + '\uf120', // 0x13 -> HOME (CUS) + '\u007f', // 0x14 -> DELETE + '\ufffe', // 0x15 -> UNDEFINED + '\ufffe', // 0x16 -> UNDEFINED + '\ufffe', // 0x17 -> UNDEFINED + '\ufffe', // 0x18 -> UNDEFINED + '\ufffe', // 0x19 -> UNDEFINED + '\ufffe', // 0x1A -> UNDEFINED + '\ufffe', // 0x1B -> UNDEFINED + '\uf101', // 0x1C -> RED COLOR SWITCH (CUS) + '\uf11d', // 0x1D -> CURSOR RIGHT (CUS) + '\uf102', // 0x1E -> GREEN COLOR SWITCH (CUS) + '\uf103', // 0x1F -> BLUE COLOR SWITCH (CUS) + ' ' , // 0x20 -> SPACE + '!' , // ! 0x21 -> EXCLAMATION MARK + '"' , // " 0x22 -> QUOTATION MARK + '#' , // # 0x23 -> NUMBER SIGN + '$' , // $ 0x24 -> DOLLAR SIGN + '%' , // % 0x25 -> PERCENT SIGN + '&' , // & 0x26 -> AMPERSAND + '\'' , // ' 0x27 -> APOSTROPHE + '(' , // ( 0x28 -> LEFT PARENTHESIS + ')' , // ) 0x29 -> RIGHT PARENTHESIS + '*' , // * 0x2A -> ASTERISK + '+' , // + 0x2B -> PLUS SIGN + ',' , // , 0x2C -> COMMA + '-' , // - 0x2D -> HYPHEN-MINUS + '.' , // . 0x2E -> FULL STOP + '/' , // / 0x2F -> SOLIDUS + '0' , // 0 0x30 -> DIGIT ZERO + '1' , // 1 0x31 -> DIGIT ONE + '2' , // 2 0x32 -> DIGIT TWO + '3' , // 3 0x33 -> DIGIT THREE + '4' , // 4 0x34 -> DIGIT FOUR + '5' , // 5 0x35 -> DIGIT FIVE + '6' , // 6 0x36 -> DIGIT SIX + '7' , // 7 0x37 -> DIGIT SEVEN + '8' , // 8 0x38 -> DIGIT EIGHT + '9' , // 9 0x39 -> DIGIT NINE + ':' , // : 0x3A -> COLON + ';' , // ; 0x3B -> SEMICOLON + '<' , // < 0x3C -> LESS-THAN SIGN + '=' , // = 0x3D -> EQUALS SIGN + '>' , // > 0x3E -> GREATER-THAN SIGN + '?' , // ? 0x3F -> QUESTION MARK + '@' , // @ 0x40 -> COMMERCIAL AT + 'a' , // a 0x41 -> LATIN SMALL LETTER A + 'b' , // b 0x42 -> LATIN SMALL LETTER B + 'c' , // c 0x43 -> LATIN SMALL LETTER C + 'd' , // d 0x44 -> LATIN SMALL LETTER D + 'e' , // e 0x45 -> LATIN SMALL LETTER E + 'f' , // f 0x46 -> LATIN SMALL LETTER F + 'g' , // g 0x47 -> LATIN SMALL LETTER G + 'h' , // h 0x48 -> LATIN SMALL LETTER H + 'i' , // i 0x49 -> LATIN SMALL LETTER I + 'j' , // j 0x4A -> LATIN SMALL LETTER J + 'k' , // k 0x4B -> LATIN SMALL LETTER K + 'l' , // l 0x4C -> LATIN SMALL LETTER L + 'm' , // m 0x4D -> LATIN SMALL LETTER M + 'n' , // n 0x4E -> LATIN SMALL LETTER N + 'o' , // o 0x4F -> LATIN SMALL LETTER O + 'p' , // p 0x50 -> LATIN SMALL LETTER P + 'q' , // q 0x51 -> LATIN SMALL LETTER Q + 'r' , // r 0x52 -> LATIN SMALL LETTER R + 's' , // s 0x53 -> LATIN SMALL LETTER S + 't' , // t 0x54 -> LATIN SMALL LETTER T + 'u' , // u 0x55 -> LATIN SMALL LETTER U + 'v' , // v 0x56 -> LATIN SMALL LETTER V + 'w' , // w 0x57 -> LATIN SMALL LETTER W + 'x' , // x 0x58 -> LATIN SMALL LETTER X + 'y' , // y 0x59 -> LATIN SMALL LETTER Y + 'z' , // z 0x5A -> LATIN SMALL LETTER Z + '[' , // [ 0x5B -> LEFT SQUARE BRACKET + '\u00a3', // £ 0x5C -> POUND SIGN + ']' , // ] 0x5D -> RIGHT SQUARE BRACKET + '\u2191', // ↑ 0x5E -> UPWARDS ARROW + '\u2190', // ← 0x5F -> LEFTWARDS ARROW + '\u2500', // ─ 0x60 -> BOX DRAWINGS LIGHT HORIZONTAL + 'A' , // A 0x61 -> LATIN CAPITAL LETTER A + 'B' , // B 0x62 -> LATIN CAPITAL LETTER B + 'C' , // C 0x63 -> LATIN CAPITAL LETTER C + 'D' , // D 0x64 -> LATIN CAPITAL LETTER D + 'E' , // E 0x65 -> LATIN CAPITAL LETTER E + 'F' , // F 0x66 -> LATIN CAPITAL LETTER F + 'G' , // G 0x67 -> LATIN CAPITAL LETTER G + 'H' , // H 0x68 -> LATIN CAPITAL LETTER H + 'I' , // I 0x69 -> LATIN CAPITAL LETTER I + 'J' , // J 0x6A -> LATIN CAPITAL LETTER J + 'K' , // K 0x6B -> LATIN CAPITAL LETTER K + 'L' , // L 0x6C -> LATIN CAPITAL LETTER L + 'M' , // M 0x6D -> LATIN CAPITAL LETTER M + 'N' , // N 0x6E -> LATIN CAPITAL LETTER N + 'O' , // O 0x6F -> LATIN CAPITAL LETTER O + 'P' , // P 0x70 -> LATIN CAPITAL LETTER P + 'Q' , // Q 0x71 -> LATIN CAPITAL LETTER Q + 'R' , // R 0x72 -> LATIN CAPITAL LETTER R + 'S' , // S 0x73 -> LATIN CAPITAL LETTER S + 'T' , // T 0x74 -> LATIN CAPITAL LETTER T + 'U' , // U 0x75 -> LATIN CAPITAL LETTER U + 'V' , // V 0x76 -> LATIN CAPITAL LETTER V + 'W' , // W 0x77 -> LATIN CAPITAL LETTER W + 'X' , // X 0x78 -> LATIN CAPITAL LETTER X + 'Y' , // Y 0x79 -> LATIN CAPITAL LETTER Y + 'Z' , // Z 0x7A -> LATIN CAPITAL LETTER Z + '\u253c', // ┼ 0x7B -> BOX DRAWINGS LIGHT VERTICAL AND HORIZONTAL + '\uf12e', //  0x7C -> LEFT HALF BLOCK MEDIUM SHADE (CUS) + '\u2502', // │ 0x7D -> BOX DRAWINGS LIGHT VERTICAL + '\u2592', // ▒ 0x7E -> MEDIUM SHADE + '\uf139', //  0x7F -> MEDIUM SHADE SLASHED LEFT (CUS) + '\ufffe', // 0x80 -> UNDEFINED + '\uf104', // 0x81 -> ORANGE COLOR SWITCH (CUS) + '\ufffe', // 0x82 -> UNDEFINED + '\ufffe', // 0x83 -> UNDEFINED + '\ufffe', // 0x84 -> UNDEFINED + '\uf110', //  0x85 -> FUNCTION KEY 1 (CUS) + '\uf112', //  0x86 -> FUNCTION KEY 3 (CUS) + '\uf114', //  0x87 -> FUNCTION KEY 5 (CUS) + '\uf116', //  0x88 -> FUNCTION KEY 7 (CUS) + '\uf111', //  0x89 -> FUNCTION KEY 2 (CUS) + '\uf113', //  0x8A -> FUNCTION KEY 4 (CUS) + '\uf115', //  0x8B -> FUNCTION KEY 6 (CUS) + '\uf117', //  0x8C -> FUNCTION KEY 8 (CUS) + '\n' , // 0x8D -> LINE FEED + '\u000f', //  0x8E -> SHIFT IN + '\ufffe', // 0x8F -> UNDEFINED + '\uf105', // 0x90 -> BLACK COLOR SWITCH (CUS) + '\uf11e', //  0x91 -> CURSOR UP (CUS) + '\uf11b', //  0x92 -> REVERSE VIDEO OFF (CUS) + '\u000c', // 0x93 -> FORM FEED + '\uf121', //  0x94 -> INSERT (CUS) + '\uf106', // 0x95 -> BROWN COLOR SWITCH (CUS) + '\uf107', // 0x96 -> LIGHT RED COLOR SWITCH (CUS) + '\uf108', // 0x97 -> GRAY 1 COLOR SWITCH (CUS) + '\uf109', //  0x98 -> GRAY 2 COLOR SWITCH (CUS) + '\uf10a', //  0x99 -> LIGHT GREEN COLOR SWITCH (CUS) + '\uf10b', //  0x9A -> LIGHT BLUE COLOR SWITCH (CUS) + '\uf10c', //  0x9B -> GRAY 3 COLOR SWITCH (CUS) + '\uf10d', //  0x9C -> PURPLE COLOR SWITCH (CUS) + '\uf11d', //  0x9D -> CURSOR LEFT (CUS) + '\uf10e', //  0x9E -> YELLOW COLOR SWITCH (CUS) + '\uf10f', //  0x9F -> CYAN COLOR SWITCH (CUS) + '\u00a0', // 0xA0 -> NO-BREAK SPACE + '\u258c', // ▌ 0xA1 -> LEFT HALF BLOCK + '\u2584', // ▄ 0xA2 -> LOWER HALF BLOCK + '\u2594', // ▔ 0xA3 -> UPPER ONE EIGHTH BLOCK + '\u2581', // ▁ 0xA4 -> LOWER ONE EIGHTH BLOCK + '\u258f', // ▏ 0xA5 -> LEFT ONE EIGHTH BLOCK + '\u2592', // ▒ 0xA6 -> MEDIUM SHADE + '\u2595', // ▕ 0xA7 -> RIGHT ONE EIGHTH BLOCK + '\uf12f', //  0xA8 -> LOWER HALF BLOCK MEDIUM SHADE (CUS) + '\uf13a', //  0xA9 -> MEDIUM SHADE SLASHED RIGHT (CUS) + '\uf130', //  0xAA -> RIGHT ONE QUARTER BLOCK (CUS) + '\u251c', // ├ 0xAB -> BOX DRAWINGS LIGHT VERTICAL AND RIGHT + '\u2597', // ▗ 0xAC -> QUADRANT LOWER RIGHT + '\u2514', // └ 0xAD -> BOX DRAWINGS LIGHT UP AND RIGHT + '\u2510', // ┐ 0xAE -> BOX DRAWINGS LIGHT DOWN AND LEFT + '\u2582', // ▂ 0xAF -> LOWER ONE QUARTER BLOCK + '\u250c', // ┌ 0xB0 -> BOX DRAWINGS LIGHT DOWN AND RIGHT + '\u2534', // ┴ 0xB1 -> BOX DRAWINGS LIGHT UP AND HORIZONTAL + '\u252c', // ┬ 0xB2 -> BOX DRAWINGS LIGHT DOWN AND HORIZONTAL + '\u2524', // ┤ 0xB3 -> BOX DRAWINGS LIGHT VERTICAL AND LEFT + '\u258e', // ▎ 0xB4 -> LEFT ONE QUARTER BLOCK + '\u258d', // ▍ 0xB5 -> LEFT THREE EIGTHS BLOCK + '\uf131', //  0xB6 -> RIGHT THREE EIGHTHS BLOCK (CUS) + '\uf132', //  0xB7 -> UPPER ONE QUARTER BLOCK (CUS) + '\uf133', //  0xB8 -> UPPER THREE EIGHTS BLOCK (CUS) + '\u2583', // ▃ 0xB9 -> LOWER THREE EIGHTHS BLOCK + '\u2713', // ✓ 0xBA -> CHECK MARK + '\u2596', // ▖ 0xBB -> QUADRANT LOWER LEFT + '\u259d', // ▝ 0xBC -> QUADRANT UPPER RIGHT + '\u2518', // ┘ 0xBD -> BOX DRAWINGS LIGHT UP AND LEFT + '\u2598', // ▘ 0xBE -> QUADRANT UPPER LEFT + '\u259a', // ▚ 0xBF -> QUADRANT UPPER LEFT AND LOWER RIGHT + '\u2500', // ─ 0xC0 -> BOX DRAWINGS LIGHT HORIZONTAL + 'A' , // A 0xC1 -> LATIN CAPITAL LETTER A + 'B' , // B 0xC2 -> LATIN CAPITAL LETTER B + 'C' , // C 0xC3 -> LATIN CAPITAL LETTER C + 'D' , // D 0xC4 -> LATIN CAPITAL LETTER D + 'E' , // E 0xC5 -> LATIN CAPITAL LETTER E + 'F' , // F 0xC6 -> LATIN CAPITAL LETTER F + 'G' , // G 0xC7 -> LATIN CAPITAL LETTER G + 'H' , // H 0xC8 -> LATIN CAPITAL LETTER H + 'I' , // I 0xC9 -> LATIN CAPITAL LETTER I + 'J' , // J 0xCA -> LATIN CAPITAL LETTER J + 'K' , // K 0xCB -> LATIN CAPITAL LETTER K + 'L' , // L 0xCC -> LATIN CAPITAL LETTER L + 'M' , // M 0xCD -> LATIN CAPITAL LETTER M + 'N' , // N 0xCE -> LATIN CAPITAL LETTER N + 'O' , // O 0xCF -> LATIN CAPITAL LETTER O + 'P' , // P 0xD0 -> LATIN CAPITAL LETTER P + 'Q' , // Q 0xD1 -> LATIN CAPITAL LETTER Q + 'R' , // R 0xD2 -> LATIN CAPITAL LETTER R + 'S' , // S 0xD3 -> LATIN CAPITAL LETTER S + 'T' , // T 0xD4 -> LATIN CAPITAL LETTER T + 'U' , // U 0xD5 -> LATIN CAPITAL LETTER U + 'V' , // V 0xD6 -> LATIN CAPITAL LETTER V + 'W' , // W 0xD7 -> LATIN CAPITAL LETTER W + 'X' , // X 0xD8 -> LATIN CAPITAL LETTER X + 'Y' , // Y 0xD9 -> LATIN CAPITAL LETTER Y + 'Z' , // Z 0xDA -> LATIN CAPITAL LETTER Z + '\u253c', // ┼ 0xDB -> BOX DRAWINGS LIGHT VERTICAL AND HORIZONTAL + '\uf12e', //  0xDC -> LEFT HALF BLOCK MEDIUM SHADE (CUS) + '\u2502', // │ 0xDD -> BOX DRAWINGS LIGHT VERTICAL + '\u2592', // ▒ 0xDE -> MEDIUM SHADE + '\uf139', //  0xDF -> MEDIUM SHADE SLASHED LEFT (CUS) + '\u00a0', // 0xE0 -> NO-BREAK SPACE + '\u258c', // ▌ 0xE1 -> LEFT HALF BLOCK + '\u2584', // ▄ 0xE2 -> LOWER HALF BLOCK + '\u2594', // ▔ 0xE3 -> UPPER ONE EIGHTH BLOCK + '\u2581', // ▁ 0xE4 -> LOWER ONE EIGHTH BLOCK + '\u258f', // ▏ 0xE5 -> LEFT ONE EIGHTH BLOCK + '\u2592', // ▒ 0xE6 -> MEDIUM SHADE + '\u2595', // ▕ 0xE7 -> RIGHT ONE EIGHTH BLOCK + '\uf12f', //  0xE8 -> LOWER HALF BLOCK MEDIUM SHADE (CUS) + '\uf13a', //  0xE9 -> MEDIUM SHADE SLASHED RIGHT (CUS) + '\uf130', //  0xEA -> RIGHT ONE QUARTER BLOCK (CUS) + '\u251c', // ├ 0xEB -> BOX DRAWINGS LIGHT VERTICAL AND RIGHT + '\u2597', // ▗ 0xEC -> QUADRANT LOWER RIGHT + '\u2514', // └ 0xED -> BOX DRAWINGS LIGHT UP AND RIGHT + '\u2510', // ┐ 0xEE -> BOX DRAWINGS LIGHT DOWN AND LEFT + '\u2582', // ▂ 0xEF -> LOWER ONE QUARTER BLOCK + '\u250c', // ┌ 0xF0 -> BOX DRAWINGS LIGHT DOWN AND RIGHT + '\u2534', // ┴ 0xF1 -> BOX DRAWINGS LIGHT UP AND HORIZONTAL + '\u252c', // ┬ 0xF2 -> BOX DRAWINGS LIGHT DOWN AND HORIZONTAL + '\u2524', // ┤ 0xF3 -> BOX DRAWINGS LIGHT VERTICAL AND LEFT + '\u258e', // ▎ 0xF4 -> LEFT ONE QUARTER BLOCK + '\u258d', // ▍ 0xF5 -> LEFT THREE EIGTHS BLOCK + '\uf131', //  0xF6 -> RIGHT THREE EIGHTHS BLOCK (CUS) + '\uf132', //  0xF7 -> UPPER ONE QUARTER BLOCK (CUS) + '\uf133', //  0xF8 -> UPPER THREE EIGHTS BLOCK (CUS) + '\u2583', // ▃ 0xF9 -> LOWER THREE EIGHTHS BLOCK + '\u2713', // ✓ 0xFA -> CHECK MARK + '\u2596', // ▖ 0xFB -> QUADRANT LOWER LEFT + '\u259d', // ▝ 0xFC -> QUADRANT UPPER RIGHT + '\u2518', // ┘ 0xFD -> BOX DRAWINGS LIGHT UP AND LEFT + '\u2598', // ▘ 0xFE -> QUADRANT UPPER LEFT + '\u2592' // ▒ 0xFF -> MEDIUM SHADE + ) + + private val decodingPetsciiUppercase = arrayOf( + '\u0000', // 0x00 -> \u0000 + '\ufffe', // 0x01 -> UNDEFINED + '\ufffe', // 0x02 -> UNDEFINED + '\ufffe', // 0x03 -> UNDEFINED + '\ufffe', // 0x04 -> UNDEFINED + '\uf100', // 0x05 -> WHITE COLOR SWITCH (CUS) + '\ufffe', // 0x06 -> UNDEFINED + '\ufffe', // 0x07 -> UNDEFINED + '\uf118', // 0x08 -> DISABLE CHARACTER SET SWITCHING (CUS) + '\uf119', // 0x09 -> ENABLE CHARACTER SET SWITCHING (CUS) + '\ufffe', // 0x0A -> UNDEFINED + '\ufffe', // 0x0B -> UNDEFINED + '\ufffe', // 0x0C -> UNDEFINED + '\r' , // 0x0D -> CARRIAGE RETURN + '\u000e', // 0x0E -> SHIFT OUT + '\ufffe', // 0x0F -> UNDEFINED + '\ufffe', // 0x10 -> UNDEFINED + '\uf11c', // 0x11 -> CURSOR DOWN (CUS) + '\uf11a', // 0x12 -> REVERSE VIDEO ON (CUS) + '\uf120', // 0x13 -> HOME (CUS) + '\u007f', // 0x14 -> DELETE + '\ufffe', // 0x15 -> UNDEFINED + '\ufffe', // 0x16 -> UNDEFINED + '\ufffe', // 0x17 -> UNDEFINED + '\ufffe', // 0x18 -> UNDEFINED + '\ufffe', // 0x19 -> UNDEFINED + '\ufffe', // 0x1A -> UNDEFINED + '\ufffe', // 0x1B -> UNDEFINED + '\uf101', // 0x1C -> RED COLOR SWITCH (CUS) + '\uf11d', // 0x1D -> CURSOR RIGHT (CUS) + '\uf102', // 0x1E -> GREEN COLOR SWITCH (CUS) + '\uf103', // 0x1F -> BLUE COLOR SWITCH (CUS) + ' ' , // 0x20 -> SPACE + '!' , // ! 0x21 -> EXCLAMATION MARK + '"' , // " 0x22 -> QUOTATION MARK + '#' , // # 0x23 -> NUMBER SIGN + '$' , // $ 0x24 -> DOLLAR SIGN + '%' , // % 0x25 -> PERCENT SIGN + '&' , // & 0x26 -> AMPERSAND + '\'' , // ' 0x27 -> APOSTROPHE + '(' , // ( 0x28 -> LEFT PARENTHESIS + ')' , // ) 0x29 -> RIGHT PARENTHESIS + '*' , // * 0x2A -> ASTERISK + '+' , // + 0x2B -> PLUS SIGN + ',' , // , 0x2C -> COMMA + '-' , // - 0x2D -> HYPHEN-MINUS + '.' , // . 0x2E -> FULL STOP + '/' , // / 0x2F -> SOLIDUS + '0' , // 0 0x30 -> DIGIT ZERO + '1' , // 1 0x31 -> DIGIT ONE + '2' , // 2 0x32 -> DIGIT TWO + '3' , // 3 0x33 -> DIGIT THREE + '4' , // 4 0x34 -> DIGIT FOUR + '5' , // 5 0x35 -> DIGIT FIVE + '6' , // 6 0x36 -> DIGIT SIX + '7' , // 7 0x37 -> DIGIT SEVEN + '8' , // 8 0x38 -> DIGIT EIGHT + '9' , // 9 0x39 -> DIGIT NINE + ':' , // : 0x3A -> COLON + ';' , // ; 0x3B -> SEMICOLON + '<' , // < 0x3C -> LESS-THAN SIGN + '=' , // = 0x3D -> EQUALS SIGN + '>' , // > 0x3E -> GREATER-THAN SIGN + '?' , // ? 0x3F -> QUESTION MARK + '@' , // @ 0x40 -> COMMERCIAL AT + 'A' , // A 0x41 -> LATIN CAPITAL LETTER A + 'B' , // B 0x42 -> LATIN CAPITAL LETTER B + 'C' , // C 0x43 -> LATIN CAPITAL LETTER C + 'D' , // D 0x44 -> LATIN CAPITAL LETTER D + 'E' , // E 0x45 -> LATIN CAPITAL LETTER E + 'F' , // F 0x46 -> LATIN CAPITAL LETTER F + 'G' , // G 0x47 -> LATIN CAPITAL LETTER G + 'H' , // H 0x48 -> LATIN CAPITAL LETTER H + 'I' , // I 0x49 -> LATIN CAPITAL LETTER I + 'J' , // J 0x4A -> LATIN CAPITAL LETTER J + 'K' , // K 0x4B -> LATIN CAPITAL LETTER K + 'L' , // L 0x4C -> LATIN CAPITAL LETTER L + 'M' , // M 0x4D -> LATIN CAPITAL LETTER M + 'N' , // N 0x4E -> LATIN CAPITAL LETTER N + 'O' , // O 0x4F -> LATIN CAPITAL LETTER O + 'P' , // P 0x50 -> LATIN CAPITAL LETTER P + 'Q' , // Q 0x51 -> LATIN CAPITAL LETTER Q + 'R' , // R 0x52 -> LATIN CAPITAL LETTER R + 'S' , // S 0x53 -> LATIN CAPITAL LETTER S + 'T' , // T 0x54 -> LATIN CAPITAL LETTER T + 'U' , // U 0x55 -> LATIN CAPITAL LETTER U + 'V' , // V 0x56 -> LATIN CAPITAL LETTER V + 'W' , // W 0x57 -> LATIN CAPITAL LETTER W + 'X' , // X 0x58 -> LATIN CAPITAL LETTER X + 'Y' , // Y 0x59 -> LATIN CAPITAL LETTER Y + 'Z' , // Z 0x5A -> LATIN CAPITAL LETTER Z + '[' , // [ 0x5B -> LEFT SQUARE BRACKET + '\u00a3', // £ 0x5C -> POUND SIGN + ']' , // ] 0x5D -> RIGHT SQUARE BRACKET + '\u2191', // ↑ 0x5E -> UPWARDS ARROW + '\u2190', // ← 0x5F -> LEFTWARDS ARROW + '\u2500', // ─ 0x60 -> BOX DRAWINGS LIGHT HORIZONTAL + '\u2660', // ♠ 0x61 -> BLACK SPADE SUIT + '\u2502', // │ 0x62 -> BOX DRAWINGS LIGHT VERTICAL + '\u2500', // ─ 0x63 -> BOX DRAWINGS LIGHT HORIZONTAL + '\uf122', //  0x64 -> BOX DRAWINGS LIGHT HORIZONTAL ONE QUARTER UP (CUS) + '\uf123', //  0x65 -> BOX DRAWINGS LIGHT HORIZONTAL TWO QUARTERS UP (CUS) + '\uf124', //  0x66 -> BOX DRAWINGS LIGHT HORIZONTAL ONE QUARTER DOWN (CUS) + '\uf126', //  0x67 -> BOX DRAWINGS LIGHT VERTICAL ONE QUARTER LEFT (CUS) + '\uf128', //  0x68 -> BOX DRAWINGS LIGHT VERTICAL ONE QUARTER RIGHT (CUS) + '\u256e', // ╮ 0x69 -> BOX DRAWINGS LIGHT ARC DOWN AND LEFT + '\u2570', // ╰ 0x6A -> BOX DRAWINGS LIGHT ARC UP AND RIGHT + '\u256f', // ╯ 0x6B -> BOX DRAWINGS LIGHT ARC UP AND LEFT + '\uf12a', //  0x6C -> ONE EIGHTH BLOCK UP AND RIGHT (CUS) + '\u2572', // ╲ 0x6D -> BOX DRAWINGS LIGHT DIAGONAL UPPER LEFT TO LOWER RIGHT + '\u2571', // ╱ 0x6E -> BOX DRAWINGS LIGHT DIAGONAL UPPER RIGHT TO LOWER LEFT + '\uf12b', //  0x6F -> ONE EIGHTH BLOCK DOWN AND RIGHT (CUS) + '\uf12c', //  0x70 -> ONE EIGHTH BLOCK DOWN AND LEFT (CUS) + '\u25cf', // ● 0x71 -> BLACK CIRCLE + '\uf125', //  0x72 -> BOX DRAWINGS LIGHT HORIZONTAL TWO QUARTERS DOWN (CUS) + '\u2665', // ♥ 0x73 -> BLACK HEART SUIT + '\uf127', //  0x74 -> BOX DRAWINGS LIGHT VERTICAL TWO QUARTERS LEFT (CUS) + '\u256d', // ╭ 0x75 -> BOX DRAWINGS LIGHT ARC DOWN AND RIGHT + '\u2573', // ╳ 0x76 -> BOX DRAWINGS LIGHT DIAGONAL CROSS + '\u25cb', // ○ 0x77 -> WHITE CIRCLE + '\u2663', // ♣ 0x78 -> BLACK CLUB SUIT + '\uf129', //  0x79 -> BOX DRAWINGS LIGHT VERTICAL TWO QUARTERS RIGHT (CUS) + '\u2666', // ♦ 0x7A -> BLACK DIAMOND SUIT + '\u253c', // ┼ 0x7B -> BOX DRAWINGS LIGHT VERTICAL AND HORIZONTAL + '\uf12e', //  0x7C -> LEFT HALF BLOCK MEDIUM SHADE (CUS) + '\u2502', // │ 0x7D -> BOX DRAWINGS LIGHT VERTICAL + '\u03c0', // π 0x7E -> GREEK SMALL LETTER PI + '\u25e5', // ◥ 0x7F -> BLACK UPPER RIGHT TRIANGLE + '\ufffe', // 0x80 -> UNDEFINED + '\uf104', //  0x81 -> ORANGE COLOR SWITCH (CUS) + '\ufffe', // 0x82 -> UNDEFINED + '\ufffe', // 0x83 -> UNDEFINED + '\ufffe', // 0x84 -> UNDEFINED + '\uf110', // 0x85 -> FUNCTION KEY 1 (CUS) + '\uf112', // 0x86 -> FUNCTION KEY 3 (CUS) + '\uf114', // 0x87 -> FUNCTION KEY 5 (CUS) + '\uf116', // 0x88 -> FUNCTION KEY 7 (CUS) + '\uf111', // 0x89 -> FUNCTION KEY 2 (CUS) + '\uf113', // 0x8A -> FUNCTION KEY 4 (CUS) + '\uf115', // 0x8B -> FUNCTION KEY 6 (CUS) + '\uf117', // 0x8C -> FUNCTION KEY 8 (CUS) + '\n' , // 0x8D -> LINE FEED + '\u000f', // 0x8E -> SHIFT IN + '\ufffe', // 0x8F -> UNDEFINED + '\uf105', // 0x90 -> BLACK COLOR SWITCH (CUS) + '\uf11e', // 0x91 -> CURSOR UP (CUS) + '\uf11b', // 0x92 -> REVERSE VIDEO OFF (CUS) + '\u000c', // 0x93 -> FORM FEED + '\uf121', // 0x94 -> INSERT (CUS) + '\uf106', // 0x95 -> BROWN COLOR SWITCH (CUS) + '\uf107', // 0x96 -> LIGHT RED COLOR SWITCH (CUS) + '\uf108', // 0x97 -> GRAY 1 COLOR SWITCH (CUS) + '\uf109', // 0x98 -> GRAY 2 COLOR SWITCH (CUS) + '\uf10a', // 0x99 -> LIGHT GREEN COLOR SWITCH (CUS) + '\uf10b', // 0x9A -> LIGHT BLUE COLOR SWITCH (CUS) + '\uf10c', // 0x9B -> GRAY 3 COLOR SWITCH (CUS) + '\uf10d', // 0x9C -> PURPLE COLOR SWITCH (CUS) + '\uf11d', // 0x9D -> CURSOR LEFT (CUS) + '\uf10e', // 0x9E -> YELLOW COLOR SWITCH (CUS) + '\uf10f', // 0x9F -> CYAN COLOR SWITCH (CUS) + '\u00a0', // 0xA0 -> NO-BREAK SPACE + '\u258c', // ▌ 0xA1 -> LEFT HALF BLOCK + '\u2584', // ▄ 0xA2 -> LOWER HALF BLOCK + '\u2594', // ▔ 0xA3 -> UPPER ONE EIGHTH BLOCK + '\u2581', // ▁ 0xA4 -> LOWER ONE EIGHTH BLOCK + '\u258f', // ▏ 0xA5 -> LEFT ONE EIGHTH BLOCK + '\u2592', // ▒ 0xA6 -> MEDIUM SHADE + '\u2595', // ▕ 0xA7 -> RIGHT ONE EIGHTH BLOCK + '\uf12f', //  0xA8 -> LOWER HALF BLOCK MEDIUM SHADE (CUS) + '\u25e4', // ◤ 0xA9 -> BLACK UPPER LEFT TRIANGLE + '\uf130', //  0xAA -> RIGHT ONE QUARTER BLOCK (CUS) + '\u251c', // ├ 0xAB -> BOX DRAWINGS LIGHT VERTICAL AND RIGHT + '\u2597', // ▗ 0xAC -> QUADRANT LOWER RIGHT + '\u2514', // └ 0xAD -> BOX DRAWINGS LIGHT UP AND RIGHT + '\u2510', // ┐ 0xAE -> BOX DRAWINGS LIGHT DOWN AND LEFT + '\u2582', // ▂ 0xAF -> LOWER ONE QUARTER BLOCK + '\u250c', // ┌ 0xB0 -> BOX DRAWINGS LIGHT DOWN AND RIGHT + '\u2534', // ┴ 0xB1 -> BOX DRAWINGS LIGHT UP AND HORIZONTAL + '\u252c', // ┬ 0xB2 -> BOX DRAWINGS LIGHT DOWN AND HORIZONTAL + '\u2524', // ┤ 0xB3 -> BOX DRAWINGS LIGHT VERTICAL AND LEFT + '\u258e', // ▎ 0xB4 -> LEFT ONE QUARTER BLOCK + '\u258d', // ▍ 0xB5 -> LEFT THREE EIGTHS BLOCK + '\uf131', //  0xB6 -> RIGHT THREE EIGHTHS BLOCK (CUS) + '\uf132', //  0xB7 -> UPPER ONE QUARTER BLOCK (CUS) + '\uf133', //  0xB8 -> UPPER THREE EIGHTS BLOCK (CUS) + '\u2583', // ▃ 0xB9 -> LOWER THREE EIGHTHS BLOCK + '\uf12d', //  0xBA -> ONE EIGHTH BLOCK UP AND LEFT (CUS) + '\u2596', // ▖ 0xBB -> QUADRANT LOWER LEFT + '\u259d', // ▝ 0xBC -> QUADRANT UPPER RIGHT + '\u2518', // ┘ 0xBD -> BOX DRAWINGS LIGHT UP AND LEFT + '\u2598', // ▘ 0xBE -> QUADRANT UPPER LEFT + '\u259a', // ▚ 0xBF -> QUADRANT UPPER LEFT AND LOWER RIGHT + '\u2500', // ─ 0xC0 -> BOX DRAWINGS LIGHT HORIZONTAL + '\u2660', // ♠ 0xC1 -> BLACK SPADE SUIT + '\u2502', // │ 0xC2 -> BOX DRAWINGS LIGHT VERTICAL + '\u2500', // ─ 0xC3 -> BOX DRAWINGS LIGHT HORIZONTAL + '\uf122', //  0xC4 -> BOX DRAWINGS LIGHT HORIZONTAL ONE QUARTER UP (CUS) + '\uf123', //  0xC5 -> BOX DRAWINGS LIGHT HORIZONTAL TWO QUARTERS UP (CUS) + '\uf124', //  0xC6 -> BOX DRAWINGS LIGHT HORIZONTAL ONE QUARTER DOWN (CUS) + '\uf126', //  0xC7 -> BOX DRAWINGS LIGHT VERTICAL ONE QUARTER LEFT (CUS) + '\uf128', //  0xC8 -> BOX DRAWINGS LIGHT VERTICAL ONE QUARTER RIGHT (CUS) + '\u256e', // ╮ 0xC9 -> BOX DRAWINGS LIGHT ARC DOWN AND LEFT + '\u2570', // ╰ 0xCA -> BOX DRAWINGS LIGHT ARC UP AND RIGHT + '\u256f', // ╯ 0xCB -> BOX DRAWINGS LIGHT ARC UP AND LEFT + '\uf12a', //  0xCC -> ONE EIGHTH BLOCK UP AND RIGHT (CUS) + '\u2572', // ╲ 0xCD -> BOX DRAWINGS LIGHT DIAGONAL UPPER LEFT TO LOWER RIGHT + '\u2571', // ╱ 0xCE -> BOX DRAWINGS LIGHT DIAGONAL UPPER RIGHT TO LOWER LEFT + '\uf12b', //  0xCF -> ONE EIGHTH BLOCK DOWN AND RIGHT (CUS) + '\uf12c', //  0xD0 -> ONE EIGHTH BLOCK DOWN AND LEFT (CUS) + '\u25cf', // ● 0xD1 -> BLACK CIRCLE + '\uf125', //  0xD2 -> BOX DRAWINGS LIGHT HORIZONTAL TWO QUARTERS DOWN (CUS) + '\u2665', // ♥ 0xD3 -> BLACK HEART SUIT + '\uf127', //  0xD4 -> BOX DRAWINGS LIGHT VERTICAL TWO QUARTERS LEFT (CUS) + '\u256d', // ╭ 0xD5 -> BOX DRAWINGS LIGHT ARC DOWN AND LEFT + '\u2573', // ╳ 0xD6 -> BOX DRAWINGS LIGHT DIAGONAL CROSS + '\u25cb', // ○ 0xD7 -> WHITE CIRCLE + '\u2663', // ♣ 0xD8 -> BLACK CLUB SUIT + '\uf129', //  0xD9 -> BOX DRAWINGS LIGHT VERTICAL TWO QUARTERS RIGHT (CUS) + '\u2666', // ♦ 0xDA -> BLACK DIAMOND SUIT + '\u253c', // ┼ 0xDB -> BOX DRAWINGS LIGHT VERTICAL AND HORIZONTAL + '\uf12e', //  0xDC -> LEFT HALF BLOCK MEDIUM SHADE (CUS) + '\u2502', // │ 0xDD -> BOX DRAWINGS LIGHT VERTICAL + '\u03c0', // π 0xDE -> GREEK SMALL LETTER PI + '\u25e5', // ◥ 0xDF -> BLACK UPPER RIGHT TRIANGLE + '\u00a0', // 0xE0 -> NO-BREAK SPACE + '\u258c', // ▌ 0xE1 -> LEFT HALF BLOCK + '\u2584', // ▄ 0xE2 -> LOWER HALF BLOCK + '\u2594', // ▔ 0xE3 -> UPPER ONE EIGHTH BLOCK + '\u2581', // ▁ 0xE4 -> LOWER ONE EIGHTH BLOCK + '\u258f', // ▏ 0xE5 -> LEFT ONE EIGHTH BLOCK + '\u2592', // ▒ 0xE6 -> MEDIUM SHADE + '\u2595', // ▕ 0xE7 -> RIGHT ONE EIGHTH BLOCK + '\uf12f', //  0xE8 -> LOWER HALF BLOCK MEDIUM SHADE (CUS) + '\u25e4', // ◤ 0xE9 -> BLACK UPPER LEFT TRIANGLE + '\uf130', //  0xEA -> RIGHT ONE QUARTER BLOCK (CUS) + '\u251c', // ├ 0xEB -> BOX DRAWINGS LIGHT VERTICAL AND RIGHT + '\u2597', // ▗ 0xEC -> QUADRANT LOWER RIGHT + '\u2514', // └ 0xED -> BOX DRAWINGS LIGHT UP AND RIGHT + '\u2510', // ┐ 0xEE -> BOX DRAWINGS LIGHT DOWN AND LEFT + '\u2582', // ▂ 0xEF -> LOWER ONE QUARTER BLOCK + '\u250c', // ┌ 0xF0 -> BOX DRAWINGS LIGHT DOWN AND RIGHT + '\u2534', // ┴ 0xF1 -> BOX DRAWINGS LIGHT UP AND HORIZONTAL + '\u252c', // ┬ 0xF2 -> BOX DRAWINGS LIGHT DOWN AND HORIZONTAL + '\u2524', // ┤ 0xF3 -> BOX DRAWINGS LIGHT VERTICAL AND LEFT + '\u258e', // ▎ 0xF4 -> LEFT ONE QUARTER BLOCK + '\u258d', // ▍ 0xF5 -> LEFT THREE EIGTHS BLOCK + '\uf131', //  0xF6 -> RIGHT THREE EIGHTHS BLOCK (CUS) + '\uf132', //  0xF7 -> UPPER ONE QUARTER BLOCK (CUS) + '\uf133', //  0xF8 -> UPPER THREE EIGHTS BLOCK (CUS) + '\u2583', // ▃ 0xF9 -> LOWER THREE EIGHTHS BLOCK + '\uf12d', //  0xFA -> ONE EIGHTH BLOCK UP AND LEFT (CUS) + '\u2596', // ▖ 0xFB -> QUADRANT LOWER LEFT + '\u259d', // ▝ 0xFC -> QUADRANT UPPER RIGHT + '\u2518', // ┘ 0xFD -> BOX DRAWINGS LIGHT UP AND LEFT + '\u2598', // ▘ 0xFE -> QUADRANT UPPER LEFT + '\u03c0' // π 0xFF -> GREEK SMALL LETTER PI + ) + + private val decodingScreencodeLowercase = arrayOf( + '@' , // @ 0x00 -> COMMERCIAL AT + 'a' , // a 0x01 -> LATIN SMALL LETTER A + 'b' , // b 0x02 -> LATIN SMALL LETTER B + 'c' , // c 0x03 -> LATIN SMALL LETTER C + 'd' , // d 0x04 -> LATIN SMALL LETTER D + 'e' , // e 0x05 -> LATIN SMALL LETTER E + 'f' , // f 0x06 -> LATIN SMALL LETTER F + 'g' , // g 0x07 -> LATIN SMALL LETTER G + 'h' , // h 0x08 -> LATIN SMALL LETTER H + 'i' , // i 0x09 -> LATIN SMALL LETTER I + 'j' , // j 0x0A -> LATIN SMALL LETTER J + 'k' , // k 0x0B -> LATIN SMALL LETTER K + 'l' , // l 0x0C -> LATIN SMALL LETTER L + 'm' , // m 0x0D -> LATIN SMALL LETTER M + 'n' , // n 0x0E -> LATIN SMALL LETTER N + 'o' , // o 0x0F -> LATIN SMALL LETTER O + 'p' , // p 0x10 -> LATIN SMALL LETTER P + 'q' , // q 0x11 -> LATIN SMALL LETTER Q + 'r' , // r 0x12 -> LATIN SMALL LETTER R + 's' , // s 0x13 -> LATIN SMALL LETTER S + 't' , // t 0x14 -> LATIN SMALL LETTER T + 'u' , // u 0x15 -> LATIN SMALL LETTER U + 'v' , // v 0x16 -> LATIN SMALL LETTER V + 'w' , // w 0x17 -> LATIN SMALL LETTER W + 'x' , // x 0x18 -> LATIN SMALL LETTER X + 'y' , // y 0x19 -> LATIN SMALL LETTER Y + 'z' , // z 0x1A -> LATIN SMALL LETTER Z + '[' , // [ 0x1B -> LEFT SQUARE BRACKET + '\u00a3', // £ 0x1C -> POUND SIGN + ']' , // ] 0x1D -> RIGHT SQUARE BRACKET + '\u2191', // ↑ 0x1E -> UPWARDS ARROW + '\u2190', // ← 0x1F -> LEFTWARDS ARROW + ' ' , // 0x20 -> SPACE + '!' , // ! 0x21 -> EXCLAMATION MARK + '"' , // " 0x22 -> QUOTATION MARK + '#' , // # 0x23 -> NUMBER SIGN + '$' , // $ 0x24 -> DOLLAR SIGN + '%' , // % 0x25 -> PERCENT SIGN + '&' , // & 0x26 -> AMPERSAND + '\'' , // ' 0x27 -> APOSTROPHE + '(' , // ( 0x28 -> LEFT PARENTHESIS + ')' , // ) 0x29 -> RIGHT PARENTHESIS + '*' , // * 0x2A -> ASTERISK + '+' , // + 0x2B -> PLUS SIGN + ',' , // , 0x2C -> COMMA + '-' , // - 0x2D -> HYPHEN-MINUS + '.' , // . 0x2E -> FULL STOP + '/' , // / 0x2F -> SOLIDUS + '0' , // 0 0x30 -> DIGIT ZERO + '1' , // 1 0x31 -> DIGIT ONE + '2' , // 2 0x32 -> DIGIT TWO + '3' , // 3 0x33 -> DIGIT THREE + '4' , // 4 0x34 -> DIGIT FOUR + '5' , // 5 0x35 -> DIGIT FIVE + '6' , // 6 0x36 -> DIGIT SIX + '7' , // 7 0x37 -> DIGIT SEVEN + '8' , // 8 0x38 -> DIGIT EIGHT + '9' , // 9 0x39 -> DIGIT NINE + ':' , // : 0x3A -> COLON + ';' , // ; 0x3B -> SEMICOLON + '<' , // < 0x3C -> LESS-THAN SIGN + '=' , // = 0x3D -> EQUALS SIGN + '>' , // > 0x3E -> GREATER-THAN SIGN + '?' , // ? 0x3F -> QUESTION MARK + '\u2500', // ─ 0x40 -> BOX DRAWINGS LIGHT HORIZONTAL + 'A' , // A 0x41 -> LATIN CAPITAL LETTER A + 'B' , // B 0x42 -> LATIN CAPITAL LETTER B + 'C' , // C 0x43 -> LATIN CAPITAL LETTER C + 'D' , // D 0x44 -> LATIN CAPITAL LETTER D + 'E' , // E 0x45 -> LATIN CAPITAL LETTER E + 'F' , // F 0x46 -> LATIN CAPITAL LETTER F + 'G' , // G 0x47 -> LATIN CAPITAL LETTER G + 'H' , // H 0x48 -> LATIN CAPITAL LETTER H + 'I' , // I 0x49 -> LATIN CAPITAL LETTER I + 'J' , // J 0x4A -> LATIN CAPITAL LETTER J + 'K' , // K 0x4B -> LATIN CAPITAL LETTER K + 'L' , // L 0x4C -> LATIN CAPITAL LETTER L + 'M' , // M 0x4D -> LATIN CAPITAL LETTER M + 'N' , // N 0x4E -> LATIN CAPITAL LETTER N + 'O' , // O 0x4F -> LATIN CAPITAL LETTER O + 'P' , // P 0x50 -> LATIN CAPITAL LETTER P + 'Q' , // Q 0x51 -> LATIN CAPITAL LETTER Q + 'R' , // R 0x52 -> LATIN CAPITAL LETTER R + 'S' , // S 0x53 -> LATIN CAPITAL LETTER S + 'T' , // T 0x54 -> LATIN CAPITAL LETTER T + 'U' , // U 0x55 -> LATIN CAPITAL LETTER U + 'V' , // V 0x56 -> LATIN CAPITAL LETTER V + 'W' , // W 0x57 -> LATIN CAPITAL LETTER W + 'X' , // X 0x58 -> LATIN CAPITAL LETTER X + 'Y' , // Y 0x59 -> LATIN CAPITAL LETTER Y + 'Z' , // Z 0x5A -> LATIN CAPITAL LETTER Z + '\u253c', // ┼ 0x5B -> BOX DRAWINGS LIGHT VERTICAL AND HORIZONTAL + '\uf12e', //  0x5C -> LEFT HALF BLOCK MEDIUM SHADE (CUS) + '\u2502', // │ 0x5D -> BOX DRAWINGS LIGHT VERTICAL + '\u2592', // ▒ 0x5E -> MEDIUM SHADE + '\uf139', //  0x5F -> MEDIUM SHADE SLASHED LEFT (CUS) + '\u00a0', // 0x60 -> NO-BREAK SPACE + '\u258c', // ▌ 0x61 -> LEFT HALF BLOCK + '\u2584', // ▄ 0x62 -> LOWER HALF BLOCK + '\u2594', // ▔ 0x63 -> UPPER ONE EIGHTH BLOCK + '\u2581', // ▁ 0x64 -> LOWER ONE EIGHTH BLOCK + '\u258f', // ▏ 0x65 -> LEFT ONE EIGHTH BLOCK + '\u2592', // ▒ 0x66 -> MEDIUM SHADE + '\u2595', // ▕ 0x67 -> RIGHT ONE EIGHTH BLOCK + '\uf12f', //  0x68 -> LOWER HALF BLOCK MEDIUM SHADE (CUS) + '\uf13a', //  0x69 -> MEDIUM SHADE SLASHED RIGHT (CUS) + '\uf130', //  0x6A -> RIGHT ONE QUARTER BLOCK (CUS) + '\u251c', // ├ 0x6B -> BOX DRAWINGS LIGHT VERTICAL AND RIGHT + '\u2597', // ▗ 0x6C -> QUADRANT LOWER RIGHT + '\u2514', // └ 0x6D -> BOX DRAWINGS LIGHT UP AND RIGHT + '\u2510', // ┐ 0x6E -> BOX DRAWINGS LIGHT DOWN AND LEFT + '\u2582', // ▂ 0x6F -> LOWER ONE QUARTER BLOCK + '\u250c', // ┌ 0x70 -> BOX DRAWINGS LIGHT DOWN AND RIGHT + '\u2534', // ┴ 0x71 -> BOX DRAWINGS LIGHT UP AND HORIZONTAL + '\u252c', // ┬ 0x72 -> BOX DRAWINGS LIGHT DOWN AND HORIZONTAL + '\u2524', // ┤ 0x73 -> BOX DRAWINGS LIGHT VERTICAL AND LEFT + '\u258e', // ▎ 0x74 -> LEFT ONE QUARTER BLOCK + '\u258d', // ▍ 0x75 -> LEFT THREE EIGTHS BLOCK + '\uf131', //  0x76 -> RIGHT THREE EIGHTHS BLOCK (CUS) + '\uf132', //  0x77 -> UPPER ONE QUARTER BLOCK (CUS) + '\uf133', //  0x78 -> UPPER THREE EIGHTS BLOCK (CUS) + '\u2583', // ▃ 0x79 -> LOWER THREE EIGHTHS BLOCK + '\u2713', // ✓ 0x7A -> CHECK MARK + '\u2596', // ▖ 0x7B -> QUADRANT LOWER LEFT + '\u259d', // ▝ 0x7C -> QUADRANT UPPER RIGHT + '\u2518', // ┘ 0x7D -> BOX DRAWINGS LIGHT UP AND LEFT + '\u2598', // ▘ 0x7E -> QUADRANT UPPER LEFT + '\u259a', // ▚ 0x7F -> QUADRANT UPPER LEFT AND LOWER RIGHT + '\ufffe', // 0x80 -> UNDEFINED + '\ufffe', // 0x81 -> UNDEFINED + '\ufffe', // 0x82 -> UNDEFINED + '\ufffe', // 0x83 -> UNDEFINED + '\ufffe', // 0x84 -> UNDEFINED + '\ufffe', // 0x85 -> UNDEFINED + '\ufffe', // 0x86 -> UNDEFINED + '\ufffe', // 0x87 -> UNDEFINED + '\ufffe', // 0x88 -> UNDEFINED + '\ufffe', // 0x89 -> UNDEFINED + '\ufffe', // 0x8A -> UNDEFINED + '\ufffe', // 0x8B -> UNDEFINED + '\ufffe', // 0x8C -> UNDEFINED + '\ufffe', // 0x8D -> UNDEFINED + '\ufffe', // 0x8E -> UNDEFINED + '\ufffe', // 0x8F -> UNDEFINED + '\ufffe', // 0x90 -> UNDEFINED + '\ufffe', // 0x91 -> UNDEFINED + '\ufffe', // 0x92 -> UNDEFINED + '\ufffe', // 0x93 -> UNDEFINED + '\ufffe', // 0x94 -> UNDEFINED + '\ufffe', // 0x95 -> UNDEFINED + '\ufffe', // 0x96 -> UNDEFINED + '\ufffe', // 0x97 -> UNDEFINED + '\ufffe', // 0x98 -> UNDEFINED + '\ufffe', // 0x99 -> UNDEFINED + '\ufffe', // 0x9A -> UNDEFINED + '\ufffe', // 0x9B -> UNDEFINED + '\ufffe', // 0x9C -> UNDEFINED + '\ufffe', // 0x9D -> UNDEFINED + '\ufffe', // 0x9E -> UNDEFINED + '\ufffe', // 0x9F -> UNDEFINED + '\ufffe', // 0xA0 -> UNDEFINED + '\ufffe', // 0xA1 -> UNDEFINED + '\ufffe', // 0xA2 -> UNDEFINED + '\ufffe', // 0xA3 -> UNDEFINED + '\ufffe', // 0xA4 -> UNDEFINED + '\ufffe', // 0xA5 -> UNDEFINED + '\ufffe', // 0xA6 -> UNDEFINED + '\ufffe', // 0xA7 -> UNDEFINED + '\ufffe', // 0xA8 -> UNDEFINED + '\ufffe', // 0xA9 -> UNDEFINED + '\ufffe', // 0xAA -> UNDEFINED + '\ufffe', // 0xAB -> UNDEFINED + '\ufffe', // 0xAC -> UNDEFINED + '\ufffe', // 0xAD -> UNDEFINED + '\ufffe', // 0xAE -> UNDEFINED + '\ufffe', // 0xAF -> UNDEFINED + '\ufffe', // 0xB0 -> UNDEFINED + '\ufffe', // 0xB1 -> UNDEFINED + '\ufffe', // 0xB2 -> UNDEFINED + '\ufffe', // 0xB3 -> UNDEFINED + '\ufffe', // 0xB4 -> UNDEFINED + '\ufffe', // 0xB5 -> UNDEFINED + '\ufffe', // 0xB6 -> UNDEFINED + '\ufffe', // 0xB7 -> UNDEFINED + '\ufffe', // 0xB8 -> UNDEFINED + '\ufffe', // 0xB9 -> UNDEFINED + '\ufffe', // 0xBA -> UNDEFINED + '\ufffe', // 0xBB -> UNDEFINED + '\ufffe', // 0xBC -> UNDEFINED + '\ufffe', // 0xBD -> UNDEFINED + '\ufffe', // 0xBE -> UNDEFINED + '\ufffe', // 0xBF -> UNDEFINED + '\ufffe', // 0xC0 -> UNDEFINED + '\ufffe', // 0xC1 -> UNDEFINED + '\ufffe', // 0xC2 -> UNDEFINED + '\ufffe', // 0xC3 -> UNDEFINED + '\ufffe', // 0xC4 -> UNDEFINED + '\ufffe', // 0xC5 -> UNDEFINED + '\ufffe', // 0xC6 -> UNDEFINED + '\ufffe', // 0xC7 -> UNDEFINED + '\ufffe', // 0xC8 -> UNDEFINED + '\ufffe', // 0xC9 -> UNDEFINED + '\ufffe', // 0xCA -> UNDEFINED + '\ufffe', // 0xCB -> UNDEFINED + '\ufffe', // 0xCC -> UNDEFINED + '\ufffe', // 0xCD -> UNDEFINED + '\ufffe', // 0xCE -> UNDEFINED + '\ufffe', // 0xCF -> UNDEFINED + '\ufffe', // 0xD0 -> UNDEFINED + '\ufffe', // 0xD1 -> UNDEFINED + '\ufffe', // 0xD2 -> UNDEFINED + '\ufffe', // 0xD3 -> UNDEFINED + '\ufffe', // 0xD4 -> UNDEFINED + '\ufffe', // 0xD5 -> UNDEFINED + '\ufffe', // 0xD6 -> UNDEFINED + '\ufffe', // 0xD7 -> UNDEFINED + '\ufffe', // 0xD8 -> UNDEFINED + '\ufffe', // 0xD9 -> UNDEFINED + '\ufffe', // 0xDA -> UNDEFINED + '\ufffe', // 0xDB -> UNDEFINED + '\ufffe', // 0xDC -> UNDEFINED + '\ufffe', // 0xDD -> UNDEFINED + '\ufffe', // 0xDE -> UNDEFINED + '\ufffe', // 0xDF -> UNDEFINED + '\ufffe', // 0xE0 -> UNDEFINED + '\ufffe', // 0xE1 -> UNDEFINED + '\ufffe', // 0xE2 -> UNDEFINED + '\ufffe', // 0xE3 -> UNDEFINED + '\ufffe', // 0xE4 -> UNDEFINED + '\ufffe', // 0xE5 -> UNDEFINED + '\ufffe', // 0xE6 -> UNDEFINED + '\ufffe', // 0xE7 -> UNDEFINED + '\ufffe', // 0xE8 -> UNDEFINED + '\ufffe', // 0xE9 -> UNDEFINED + '\ufffe', // 0xEA -> UNDEFINED + '\ufffe', // 0xEB -> UNDEFINED + '\ufffe', // 0xEC -> UNDEFINED + '\ufffe', // 0xED -> UNDEFINED + '\ufffe', // 0xEE -> UNDEFINED + '\ufffe', // 0xEF -> UNDEFINED + '\ufffe', // 0xF0 -> UNDEFINED + '\ufffe', // 0xF1 -> UNDEFINED + '\ufffe', // 0xF2 -> UNDEFINED + '\ufffe', // 0xF3 -> UNDEFINED + '\ufffe', // 0xF4 -> UNDEFINED + '\ufffe', // 0xF5 -> UNDEFINED + '\ufffe', // 0xF6 -> UNDEFINED + '\ufffe', // 0xF7 -> UNDEFINED + '\ufffe', // 0xF8 -> UNDEFINED + '\ufffe', // 0xF9 -> UNDEFINED + '\ufffe', // 0xFA -> UNDEFINED + '\ufffe', // 0xFB -> UNDEFINED + '\ufffe', // 0xFC -> UNDEFINED + '\ufffe', // 0xFD -> UNDEFINED + '\ufffe', // 0xFE -> UNDEFINED + '\ufffe' // 0xFF -> UNDEFINED + ) + + private val decodingScreencodeUppercase = arrayOf( + '@' , // @ 0x00 -> COMMERCIAL AT + 'A' , // A 0x01 -> LATIN CAPITAL LETTER A + 'B' , // B 0x02 -> LATIN CAPITAL LETTER B + 'C' , // C 0x03 -> LATIN CAPITAL LETTER C + 'D' , // D 0x04 -> LATIN CAPITAL LETTER D + 'E' , // E 0x05 -> LATIN CAPITAL LETTER E + 'F' , // F 0x06 -> LATIN CAPITAL LETTER F + 'G' , // G 0x07 -> LATIN CAPITAL LETTER G + 'H' , // H 0x08 -> LATIN CAPITAL LETTER H + 'I' , // I 0x09 -> LATIN CAPITAL LETTER I + 'J' , // J 0x0A -> LATIN CAPITAL LETTER J + 'K' , // K 0x0B -> LATIN CAPITAL LETTER K + 'L' , // L 0x0C -> LATIN CAPITAL LETTER L + 'M' , // M 0x0D -> LATIN CAPITAL LETTER M + 'N' , // N 0x0E -> LATIN CAPITAL LETTER N + 'O' , // O 0x0F -> LATIN CAPITAL LETTER O + 'P' , // P 0x10 -> LATIN CAPITAL LETTER P + 'Q' , // Q 0x11 -> LATIN CAPITAL LETTER Q + 'R' , // R 0x12 -> LATIN CAPITAL LETTER R + 'S' , // S 0x13 -> LATIN CAPITAL LETTER S + 'T' , // T 0x14 -> LATIN CAPITAL LETTER T + 'U' , // U 0x15 -> LATIN CAPITAL LETTER U + 'V' , // V 0x16 -> LATIN CAPITAL LETTER V + 'W' , // W 0x17 -> LATIN CAPITAL LETTER W + 'X' , // X 0x18 -> LATIN CAPITAL LETTER X + 'Y' , // Y 0x19 -> LATIN CAPITAL LETTER Y + 'Z' , // Z 0x1A -> LATIN CAPITAL LETTER Z + '[' , // [ 0x1B -> LEFT SQUARE BRACKET + '\u00a3', // £ 0x1C -> POUND SIGN + ']' , // ] 0x1D -> RIGHT SQUARE BRACKET + '\u2191', // ↑ 0x1E -> UPWARDS ARROW + '\u2190', // ← 0x1F -> LEFTWARDS ARROW + ' ' , // 0x20 -> SPACE + '!' , // ! 0x21 -> EXCLAMATION MARK + '"' , // " 0x22 -> QUOTATION MARK + '#' , // # 0x23 -> NUMBER SIGN + '$' , // $ 0x24 -> DOLLAR SIGN + '%' , // % 0x25 -> PERCENT SIGN + '&' , // & 0x26 -> AMPERSAND + '\'' , // ' 0x27 -> APOSTROPHE + '(' , // ( 0x28 -> LEFT PARENTHESIS + ')' , // ) 0x29 -> RIGHT PARENTHESIS + '*' , // * 0x2A -> ASTERISK + '+' , // + 0x2B -> PLUS SIGN + ',' , // , 0x2C -> COMMA + '-' , // - 0x2D -> HYPHEN-MINUS + '.' , // . 0x2E -> FULL STOP + '/' , // / 0x2F -> SOLIDUS + '0' , // 0 0x30 -> DIGIT ZERO + '1' , // 1 0x31 -> DIGIT ONE + '2' , // 2 0x32 -> DIGIT TWO + '3' , // 3 0x33 -> DIGIT THREE + '4' , // 4 0x34 -> DIGIT FOUR + '5' , // 5 0x35 -> DIGIT FIVE + '6' , // 6 0x36 -> DIGIT SIX + '7' , // 7 0x37 -> DIGIT SEVEN + '8' , // 8 0x38 -> DIGIT EIGHT + '9' , // 9 0x39 -> DIGIT NINE + ':' , // : 0x3A -> COLON + ';' , // ; 0x3B -> SEMICOLON + '<' , // < 0x3C -> LESS-THAN SIGN + '=' , // = 0x3D -> EQUALS SIGN + '>' , // > 0x3E -> GREATER-THAN SIGN + '?' , // ? 0x3F -> QUESTION MARK + '\u2500', // ─ 0x40 -> BOX DRAWINGS LIGHT HORIZONTAL + '\u2660', // ♠ 0x41 -> BLACK SPADE SUIT + '\u2502', // │ 0x42 -> BOX DRAWINGS LIGHT VERTICAL + '\u2500', // ─ 0x43 -> BOX DRAWINGS LIGHT HORIZONTAL + '\uf122', //  0x44 -> BOX DRAWINGS LIGHT HORIZONTAL ONE QUARTER UP (CUS) + '\uf123', //  0x45 -> BOX DRAWINGS LIGHT HORIZONTAL TWO QUARTERS UP (CUS) + '\uf124', //  0x46 -> BOX DRAWINGS LIGHT HORIZONTAL ONE QUARTER DOWN (CUS) + '\uf126', //  0x47 -> BOX DRAWINGS LIGHT VERTICAL ONE QUARTER LEFT (CUS) + '\uf128', //  0x48 -> BOX DRAWINGS LIGHT VERTICAL ONE QUARTER RIGHT (CUS) + '\u256e', // ╮ 0x49 -> BOX DRAWINGS LIGHT ARC DOWN AND LEFT + '\u2570', // ╰ 0x4A -> BOX DRAWINGS LIGHT ARC UP AND RIGHT + '\u256f', // ╯ 0x4B -> BOX DRAWINGS LIGHT ARC UP AND LEFT + '\uf12a', //  0x4C -> ONE EIGHTH BLOCK UP AND RIGHT (CUS) + '\u2572', // ╲ 0x4D -> BOX DRAWINGS LIGHT DIAGONAL UPPER LEFT TO LOWER RIGHT + '\u2571', // ╱ 0x4E -> BOX DRAWINGS LIGHT DIAGONAL UPPER RIGHT TO LOWER LEFT + '\uf12b', //  0x4F -> ONE EIGHTH BLOCK DOWN AND RIGHT (CUS) + '\uf12c', //  0x50 -> ONE EIGHTH BLOCK DOWN AND LEFT (CUS) + '\u25cf', // ● 0x51 -> BLACK CIRCLE + '\uf125', //  0x52 -> BOX DRAWINGS LIGHT HORIZONTAL TWO QUARTERS DOWN (CUS) + '\u2665', // ♥ 0x53 -> BLACK HEART SUIT + '\uf127', //  0x54 -> BOX DRAWINGS LIGHT VERTICAL TWO QUARTERS LEFT (CUS) + '\u256d', // ╭ 0x55 -> BOX DRAWINGS LIGHT ARC DOWN AND RIGHT + '\u2573', // ╳ 0x56 -> BOX DRAWINGS LIGHT DIAGONAL CROSS + '\u25cb', // ○ 0x57 -> WHITE CIRCLE + '\u2663', // ♣ 0x58 -> BLACK CLUB SUIT + '\uf129', //  0x59 -> BOX DRAWINGS LIGHT VERTICAL TWO QUARTERS RIGHT (CUS) + '\u2666', // ♦ 0x5A -> BLACK DIAMOND SUIT + '\u253c', // ┼ 0x5B -> BOX DRAWINGS LIGHT VERTICAL AND HORIZONTAL + '\uf12e', //  0x5C -> LEFT HALF BLOCK MEDIUM SHADE (CUS) + '\u2502', // │ 0x5D -> BOX DRAWINGS LIGHT VERTICAL + '\u03c0', // π 0x5E -> GREEK SMALL LETTER PI + '\u25e5', // ◥ 0x5F -> BLACK UPPER RIGHT TRIANGLE + '\u00a0', // 0x60 -> NO-BREAK SPACE + '\u258c', // ▌ 0x61 -> LEFT HALF BLOCK + '\u2584', // ▄ 0x62 -> LOWER HALF BLOCK + '\u2594', // ▔ 0x63 -> UPPER ONE EIGHTH BLOCK + '\u2581', // ▁ 0x64 -> LOWER ONE EIGHTH BLOCK + '\u258f', // ▏ 0x65 -> LEFT ONE EIGHTH BLOCK + '\u2592', // ▒ 0x66 -> MEDIUM SHADE + '\u2595', // ▕ 0x67 -> RIGHT ONE EIGHTH BLOCK + '\uf12f', //  0x68 -> LOWER HALF BLOCK MEDIUM SHADE (CUS) + '\u25e4', // ◤ 0x69 -> BLACK UPPER LEFT TRIANGLE + '\uf130', //  0x6A -> RIGHT ONE QUARTER BLOCK (CUS) + '\u251c', // ├ 0x6B -> BOX DRAWINGS LIGHT VERTICAL AND RIGHT + '\u2597', // ▗ 0x6C -> QUADRANT LOWER RIGHT + '\u2514', // └ 0x6D -> BOX DRAWINGS LIGHT UP AND RIGHT + '\u2510', // ┐ 0x6E -> BOX DRAWINGS LIGHT DOWN AND LEFT + '\u2582', // ▂ 0x6F -> LOWER ONE QUARTER BLOCK + '\u250c', // ┌ 0x70 -> BOX DRAWINGS LIGHT DOWN AND RIGHT + '\u2534', // ┴ 0x71 -> BOX DRAWINGS LIGHT UP AND HORIZONTAL + '\u252c', // ┬ 0x72 -> BOX DRAWINGS LIGHT DOWN AND HORIZONTAL + '\u2524', // ┤ 0x73 -> BOX DRAWINGS LIGHT VERTICAL AND LEFT + '\u258e', // ▎ 0x74 -> LEFT ONE QUARTER BLOCK + '\u258d', // ▍ 0x75 -> LEFT THREE EIGTHS BLOCK + '\uf131', //  0x76 -> RIGHT THREE EIGHTHS BLOCK (CUS) + '\uf132', //  0x77 -> UPPER ONE QUARTER BLOCK (CUS) + '\uf133', //  0x78 -> UPPER THREE EIGHTS BLOCK (CUS) + '\u2583', // ▃ 0x79 -> LOWER THREE EIGHTHS BLOCK + '\uf12d', //  0x7A -> ONE EIGHTH BLOCK UP AND LEFT (CUS) + '\u2596', // ▖ 0x7B -> QUADRANT LOWER LEFT + '\u259d', // ▝ 0x7C -> QUADRANT UPPER RIGHT + '\u2518', // ┘ 0x7D -> BOX DRAWINGS LIGHT UP AND LEFT + '\u2598', // ▘ 0x7E -> QUADRANT UPPER LEFT + '\u259a', // ▚ 0x7F -> QUADRANT UPPER LEFT AND LOWER RIGHT + '\ufffe', // 0x80 -> UNDEFINED + '\ufffe', // 0x81 -> UNDEFINED + '\ufffe', // 0x82 -> UNDEFINED + '\ufffe', // 0x83 -> UNDEFINED + '\ufffe', // 0x84 -> UNDEFINED + '\ufffe', // 0x85 -> UNDEFINED + '\ufffe', // 0x86 -> UNDEFINED + '\ufffe', // 0x87 -> UNDEFINED + '\ufffe', // 0x88 -> UNDEFINED + '\ufffe', // 0x89 -> UNDEFINED + '\ufffe', // 0x8A -> UNDEFINED + '\ufffe', // 0x8B -> UNDEFINED + '\ufffe', // 0x8C -> UNDEFINED + '\ufffe', // 0x8D -> UNDEFINED + '\ufffe', // 0x8E -> UNDEFINED + '\ufffe', // 0x8F -> UNDEFINED + '\ufffe', // 0x90 -> UNDEFINED + '\ufffe', // 0x91 -> UNDEFINED + '\ufffe', // 0x92 -> UNDEFINED + '\ufffe', // 0x93 -> UNDEFINED + '\ufffe', // 0x94 -> UNDEFINED + '\ufffe', // 0x95 -> UNDEFINED + '\ufffe', // 0x96 -> UNDEFINED + '\ufffe', // 0x97 -> UNDEFINED + '\ufffe', // 0x98 -> UNDEFINED + '\ufffe', // 0x99 -> UNDEFINED + '\ufffe', // 0x9A -> UNDEFINED + '\ufffe', // 0x9B -> UNDEFINED + '\ufffe', // 0x9C -> UNDEFINED + '\ufffe', // 0x9D -> UNDEFINED + '\ufffe', // 0x9E -> UNDEFINED + '\ufffe', // 0x9F -> UNDEFINED + '\ufffe', // 0xA0 -> UNDEFINED + '\ufffe', // 0xA1 -> UNDEFINED + '\ufffe', // 0xA2 -> UNDEFINED + '\ufffe', // 0xA3 -> UNDEFINED + '\ufffe', // 0xA4 -> UNDEFINED + '\ufffe', // 0xA5 -> UNDEFINED + '\ufffe', // 0xA6 -> UNDEFINED + '\ufffe', // 0xA7 -> UNDEFINED + '\ufffe', // 0xA8 -> UNDEFINED + '\ufffe', // 0xA9 -> UNDEFINED + '\ufffe', // 0xAA -> UNDEFINED + '\ufffe', // 0xAB -> UNDEFINED + '\ufffe', // 0xAC -> UNDEFINED + '\ufffe', // 0xAD -> UNDEFINED + '\ufffe', // 0xAE -> UNDEFINED + '\ufffe', // 0xAF -> UNDEFINED + '\ufffe', // 0xB0 -> UNDEFINED + '\ufffe', // 0xB1 -> UNDEFINED + '\ufffe', // 0xB2 -> UNDEFINED + '\ufffe', // 0xB3 -> UNDEFINED + '\ufffe', // 0xB4 -> UNDEFINED + '\ufffe', // 0xB5 -> UNDEFINED + '\ufffe', // 0xB6 -> UNDEFINED + '\ufffe', // 0xB7 -> UNDEFINED + '\ufffe', // 0xB8 -> UNDEFINED + '\ufffe', // 0xB9 -> UNDEFINED + '\ufffe', // 0xBA -> UNDEFINED + '\ufffe', // 0xBB -> UNDEFINED + '\ufffe', // 0xBC -> UNDEFINED + '\ufffe', // 0xBD -> UNDEFINED + '\ufffe', // 0xBE -> UNDEFINED + '\ufffe', // 0xBF -> UNDEFINED + '\ufffe', // 0xC0 -> UNDEFINED + '\ufffe', // 0xC1 -> UNDEFINED + '\ufffe', // 0xC2 -> UNDEFINED + '\ufffe', // 0xC3 -> UNDEFINED + '\ufffe', // 0xC4 -> UNDEFINED + '\ufffe', // 0xC5 -> UNDEFINED + '\ufffe', // 0xC6 -> UNDEFINED + '\ufffe', // 0xC7 -> UNDEFINED + '\ufffe', // 0xC8 -> UNDEFINED + '\ufffe', // 0xC9 -> UNDEFINED + '\ufffe', // 0xCA -> UNDEFINED + '\ufffe', // 0xCB -> UNDEFINED + '\ufffe', // 0xCC -> UNDEFINED + '\ufffe', // 0xCD -> UNDEFINED + '\ufffe', // 0xCE -> UNDEFINED + '\ufffe', // 0xCF -> UNDEFINED + '\ufffe', // 0xD0 -> UNDEFINED + '\ufffe', // 0xD1 -> UNDEFINED + '\ufffe', // 0xD2 -> UNDEFINED + '\ufffe', // 0xD3 -> UNDEFINED + '\ufffe', // 0xD4 -> UNDEFINED + '\ufffe', // 0xD5 -> UNDEFINED + '\ufffe', // 0xD6 -> UNDEFINED + '\ufffe', // 0xD7 -> UNDEFINED + '\ufffe', // 0xD8 -> UNDEFINED + '\ufffe', // 0xD9 -> UNDEFINED + '\ufffe', // 0xDA -> UNDEFINED + '\ufffe', // 0xDB -> UNDEFINED + '\ufffe', // 0xDC -> UNDEFINED + '\ufffe', // 0xDD -> UNDEFINED + '\ufffe', // 0xDE -> UNDEFINED + '\ufffe', // 0xDF -> UNDEFINED + '\ufffe', // 0xE0 -> UNDEFINED + '\ufffe', // 0xE1 -> UNDEFINED + '\ufffe', // 0xE2 -> UNDEFINED + '\ufffe', // 0xE3 -> UNDEFINED + '\ufffe', // 0xE4 -> UNDEFINED + '\ufffe', // 0xE5 -> UNDEFINED + '\ufffe', // 0xE6 -> UNDEFINED + '\ufffe', // 0xE7 -> UNDEFINED + '\ufffe', // 0xE8 -> UNDEFINED + '\ufffe', // 0xE9 -> UNDEFINED + '\ufffe', // 0xEA -> UNDEFINED + '\ufffe', // 0xEB -> UNDEFINED + '\ufffe', // 0xEC -> UNDEFINED + '\ufffe', // 0xED -> UNDEFINED + '\ufffe', // 0xEE -> UNDEFINED + '\ufffe', // 0xEF -> UNDEFINED + '\ufffe', // 0xF0 -> UNDEFINED + '\ufffe', // 0xF1 -> UNDEFINED + '\ufffe', // 0xF2 -> UNDEFINED + '\ufffe', // 0xF3 -> UNDEFINED + '\ufffe', // 0xF4 -> UNDEFINED + '\ufffe', // 0xF5 -> UNDEFINED + '\ufffe', // 0xF6 -> UNDEFINED + '\ufffe', // 0xF7 -> UNDEFINED + '\ufffe', // 0xF8 -> UNDEFINED + '\ufffe', // 0xF9 -> UNDEFINED + '\ufffe', // 0xFA -> UNDEFINED + '\ufffe', // 0xFB -> UNDEFINED + '\ufffe', // 0xFC -> UNDEFINED + '\ufffe', // 0xFD -> UNDEFINED + '\ufffe', // 0xFE -> UNDEFINED + '\ufffe' // 0xFF -> UNDEFINED + ) + + // encoding: from unicode to Petscii/Screencodes (0-255) + private val encodingPetsciiLowercase = decodingPetsciiLowercase.withIndex().associate{it.value to it.index} + private val encodingPetsciiUppercase = decodingPetsciiUppercase.withIndex().associate{it.value to it.index} + private val encodingScreencodeLowercase = decodingScreencodeLowercase.withIndex().associate{it.value to it.index} + private val encodingScreencodeUppercase = decodingScreencodeUppercase.withIndex().associate{it.value to it.index} + + + fun encodePetscii(text: String, lowercase: Boolean = false): List { + val lookup = if(lowercase) encodingPetsciiLowercase else encodingPetsciiUppercase + return text.map { + val petscii = lookup[it] + petscii?.toShort() ?: if(it=='\u0000') + 0.toShort() + else { + val case = if (lowercase) "lower" else "upper" + throw CharConversionException("no ${case}case Petscii character for '$it'") + } + } + } + + fun decodePetscii(petscii: Iterable, lowercase: Boolean = false): String { + val decodeTable = if(lowercase) decodingPetsciiLowercase else decodingPetsciiUppercase + return petscii.map { decodeTable[it.toInt()] }.joinToString("") + } + + fun encodeScreencode(text: String, lowercase: Boolean = false): List { + val lookup = if(lowercase) encodingScreencodeLowercase else encodingScreencodeUppercase + return text.map{ + val screencode = lookup[it] + screencode?.toShort() ?: if(it=='\u0000') + 0.toShort() + else { + val case = if (lowercase) "lower" else "upper" + throw CharConversionException("no ${case}Screencode character for '$it'") + } + } + } + + fun decodeScreencode(screencode: Iterable, lowercase: Boolean = false): String { + val decodeTable = if(lowercase) decodingScreencodeLowercase else decodingScreencodeUppercase + return screencode.map { decodeTable[it.toInt()] }.joinToString("") + } + + fun petscii2scr(petscii_code: Short, inverseVideo: Boolean): Short { + val code = when { + petscii_code <= 0x1f -> petscii_code + 128 + petscii_code <= 0x3f -> petscii_code.toInt() + petscii_code <= 0x5f -> petscii_code - 64 + petscii_code <= 0x7f -> petscii_code - 32 + petscii_code <= 0x9f -> petscii_code + 64 + petscii_code <= 0xbf -> petscii_code - 64 + petscii_code <= 0xfe -> petscii_code - 128 + petscii_code == 255.toShort() -> 95 + else -> throw CharConversionException("petscii code out of range") + } + if(inverseVideo) + return (code or 0x80).toShort() + return code.toShort() + } + + fun scr2petscii(screencode: Short): Short { + val petscii = when { + screencode <= 0x1f -> screencode + 64 + screencode <= 0x3f -> screencode.toInt() + screencode <= 0x5d -> screencode +123 + screencode == 0x5e.toShort() -> 255 + screencode == 0x5f.toShort() -> 223 + screencode <= 0x7f -> screencode + 64 + screencode <= 0xbf -> screencode - 128 + screencode <= 0xfe -> screencode - 64 + screencode == 255.toShort() -> 191 + else -> throw CharConversionException("screencode out of range") + } + return petscii.toShort() + } +} diff --git a/sim65/src/Sim65Main.kt b/sim65/src/Sim65Main.kt index a922b1a85..7af939813 100644 --- a/sim65/src/Sim65Main.kt +++ b/sim65/src/Sim65Main.kt @@ -3,6 +3,7 @@ package sim65 import kotlinx.cli.* import sim65.C64KernalStubs.handleBreakpoint import sim65.components.* +import sim65.components.Cpu6502.Companion.IRQ_vector import sim65.components.Cpu6502.Companion.RESET_vector import kotlin.system.exitProcess @@ -20,42 +21,38 @@ internal fun printSoftwareHeader() { private fun startSimulator(args: Array) { - val cli = CommandLineInterface("sim65", printHelpByDefault = false) - val enableIllegal by cli.flagArgument("-ill", "enable the illegal instructions") - try { - cli.parse(args) - } catch (e: Exception) { - exitProcess(1) - } - - val cpu = Cpu6502(enableIllegal, stopOnBrk=true) + val cpu = Cpu6502(stopOnBrk = false) cpu.tracing = false - - // create the system bus and add device to it. - // note that the order is relevant w.r.t. where reads and writes are going. - val bus = Bus() - bus.add(cpu) - val ram = Ram(0, 0xffff) - ram.set(0xc000, 0xa9) // lda #0 - ram.set(0xc001, 0x00) - ram.set(0xc002, 0x85) // sta $02 - ram.set(0xc003, 0x02) - ram.set(0xc004, 0x4c) // jmp $0816 - ram.set(0xc005, 0x16) - ram.set(0xc006, 0x08) - ram.set(RESET_vector, 0x00) - ram.set(RESET_vector+1, 0xc0) - bus.add(ram) - - ram.loadPrg("c64tests/0start") - C64KernalStubs.ram = ram - cpu.breakpoint(0xffd2, ::handleBreakpoint) cpu.breakpoint(0xffe4, ::handleBreakpoint) cpu.breakpoint(0xe16f, ::handleBreakpoint) + + // create the system bus and add device to it. + // note that the order is relevant w.r.t. where reads and writes are going. + val ram = Ram(0, 0xffff) + ram.set(0x02, 0) + ram.set(0xa002, 0) + ram.set(0xa003, 0x80) + ram.set(IRQ_vector, 0x48) + ram.set(IRQ_vector+1, 0xff) + ram.set(RESET_vector, 0x01) + ram.set(RESET_vector+1, 0x08) + ram.set(0x01fe, 0xff) + ram.set(0x01ff, 0x7f) + ram.set(0x8000, 2) + ram.set(0xa474, 2) + ram.loadPrg("c64tests/nopn") + C64KernalStubs.ram = ram + + val bus = Bus() + bus.add(cpu) + bus.add(ram) bus.reset() + require(cpu.SP==0xfd) + require(cpu.Status.asByte().toInt()==0b00100100) + try { while (true) { bus.clock() diff --git a/sim65/src/Sim65MainBCDtest.kt b/sim65/src/Sim65MainBCDtest.kt index ad3c4dd60..b63f6c7f9 100644 --- a/sim65/src/Sim65MainBCDtest.kt +++ b/sim65/src/Sim65MainBCDtest.kt @@ -19,15 +19,6 @@ internal fun printSoftwareHeader2() { private fun startSimulator2(args: Array) { - val cli = CommandLineInterface("sim65", printHelpByDefault = false) - val enableIllegal by cli.flagArgument("-ill", "enable the illegal instructions") - - try { - cli.parse(args) - } catch (e: Exception) { - exitProcess(1) - } - val bootRom = listOf( 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, @@ -50,7 +41,7 @@ private fun startSimulator2(args: Array) { 0x00,0xa0 // IRQ vector ).toTypedArray() - val cpu = Cpu6502(enableIllegal, true) + val cpu = Cpu6502(true) cpu.tracing = true // create the system bus and add device to it. @@ -78,16 +69,16 @@ private fun startSimulator2(args: Array) { } - if(ram.read(0x0400)==0.toShort()) + if(ram[0x0400] ==0.toShort()) println("BCD TEST: OK!") else { - val code = ram.read(0x0400) - val v1 = ram.read(0x0401) - val v2 = ram.read(0x0402) - val predictedA = ram.read(0x00fc) - val actualA = ram.read(0x00fd) - val predictedF = ram.read(0x00fe) - val actualF = ram.read(0x00ff) + val code = ram[0x0400] + val v1 = ram[0x0401] + val v2 = ram[0x0402] + val predictedA = ram[0x00fc] + val actualA = ram[0x00fd] + val predictedF = ram[0x00fe] + val actualF = ram[0x00ff] println("BCD TEST: FAIL!! code=${hexB(code)} value1=${hexB(v1)} value2=${hexB(v2)}") println(" predictedA=${hexB(predictedA)}") println(" actualA=${hexB(actualA)}") diff --git a/sim65/src/components/Bus.kt b/sim65/src/components/Bus.kt index b05a10683..d9495be6a 100644 --- a/sim65/src/components/Bus.kt +++ b/sim65/src/components/Bus.kt @@ -32,7 +32,7 @@ class Bus { fun read(address: Address): UByte { memComponents.forEach { if(address>=it.startAddress && address<=it.endAddress) - return it.read(address) + return it[address] } return 0xff } @@ -40,7 +40,7 @@ class Bus { fun write(address: Address, data: UByte) { memComponents.forEach { if(address>=it.startAddress && address<=it.endAddress) - it.write(address, data) + it[address] = data } } } diff --git a/sim65/src/components/Component.kt b/sim65/src/components/Component.kt index a0d01071e..921e946e2 100644 --- a/sim65/src/components/Component.kt +++ b/sim65/src/components/Component.kt @@ -1,6 +1,6 @@ package sim65.components -import sim65.C64Screencodes +import sim65.Petscii abstract class BusComponent { lateinit var bus: Bus @@ -10,8 +10,8 @@ abstract class BusComponent { } abstract class MemMappedComponent(val startAddress: Address, val endAddress: Address): BusComponent() { - abstract fun read(address: Address): UByte - abstract fun write(address: Address, data: UByte) + abstract operator fun get(address: Address): UByte + abstract operator fun set(address: Address, data: UByte) abstract fun cloneMem(): Array init { @@ -22,12 +22,12 @@ abstract class MemMappedComponent(val startAddress: Address, val endAddress: Add fun dump(from: Address, to: Address) { (from .. to).chunked(16).forEach { print("\$${it.first().toString(16).padStart(4, '0')} ") - val bytes = it.map { address -> read(address) } + val bytes = it.map { address -> get(address) } bytes.forEach { byte -> print(byte.toString(16).padStart(2, '0') + " ") } print(" ") - print(C64Screencodes.decodeScreencode(bytes, false).replace('\ufffe', '.')) + print(Petscii.decodeScreencode(bytes, false).replace('\ufffe', '.')) println() } } diff --git a/sim65/src/components/Cpu6502.kt b/sim65/src/components/Cpu6502.kt index 81446d2c1..e618d2157 100644 --- a/sim65/src/components/Cpu6502.kt +++ b/sim65/src/components/Cpu6502.kt @@ -21,7 +21,7 @@ interface ICpu { // TODO: make a 65c02 variant as well (and re-enable the unit tests for that). -class Cpu6502(private val illegalInstrsAllowed: Boolean, private val stopOnBrk: Boolean) : BusComponent(), ICpu { +class Cpu6502(private val stopOnBrk: Boolean) : BusComponent(), ICpu { override var tracing: Boolean = false override var totalCycles: Int = 0 private set @@ -68,7 +68,11 @@ class Cpu6502(private val illegalInstrsAllowed: Boolean, private val stopOnBrk: IzY } - class Instruction(val mnemonic: String, val mode: AddrMode, val cycles: Int, val official: Boolean, val execute: () -> Unit) + class Instruction(val opcode: UByte, val mnemonic: String, val mode: AddrMode, val cycles: Int, val official: Boolean, val execute: () -> Unit) { + override fun toString(): String { + return "[${hexB(opcode)}: $mnemonic $mode]" + } + } class StatusRegister( var C: Boolean = false, @@ -166,73 +170,69 @@ class Cpu6502(private val illegalInstrsAllowed: Boolean, private val stopOnBrk: var line = "\$${hexW(address)} ${hexB(byte)} " address++ val opcode = opcodes[byte.toInt()] - if (!opcode.official && !illegalInstrsAllowed) { - line += "$spacing1 ???" - } else { - when (opcode.mode) { - AddrMode.Acc -> { - line += "$spacing1 ${opcode.mnemonic} a" - } - AddrMode.Imp -> { - line += "$spacing1 ${opcode.mnemonic}" - } - AddrMode.Imm -> { - val value = memory[address++] - line += "${hexB(value)} $spacing2 ${opcode.mnemonic} #\$${hexB(value)}" - } - AddrMode.Zp -> { - val zpAddr = memory[address++] - line += "${hexB(zpAddr)} $spacing2 ${opcode.mnemonic} \$${hexB(zpAddr)}" - } - AddrMode.ZpX -> { - val zpAddr = memory[address++] - line += "${hexB(zpAddr)} $spacing2 ${opcode.mnemonic} \$${hexB(zpAddr)},x" - } - AddrMode.ZpY -> { - val zpAddr = memory[address++] - line += "${hexB(zpAddr)} $spacing2 ${opcode.mnemonic} \$${hexB(zpAddr)},y" - } - AddrMode.Rel -> { - val rel = memory[address++] - val target = - if (rel <= 0x7f) - address + rel - else - address - (256 - rel) - line += "${hexB(rel)} $spacing2 ${opcode.mnemonic} \$${hexW(target, true)}" - } - AddrMode.Abs -> { - val lo = memory[address++] - val hi = memory[address++] - val absAddr = lo.toInt() or (hi.toInt() shl 8) - line += "${hexB(lo)} ${hexB(hi)} $spacing3 ${opcode.mnemonic} \$${hexW(absAddr)}" - } - AddrMode.AbsX -> { - val lo = memory[address++] - val hi = memory[address++] - val absAddr = lo.toInt() or (hi.toInt() shl 8) - line += "${hexB(lo)} ${hexB(hi)} $spacing3 ${opcode.mnemonic} \$${hexW(absAddr)},x" - } - AddrMode.AbsY -> { - val lo = memory[address++] - val hi = memory[address++] - val absAddr = lo.toInt() or (hi.toInt() shl 8) - line += "${hexB(lo)} ${hexB(hi)} $spacing3 ${opcode.mnemonic} \$${hexW(absAddr)},y" - } - AddrMode.Ind -> { - val lo = memory[address++] - val hi = memory[address++] - val indirectAddr = lo.toInt() or (hi.toInt() shl 8) - line += "${hexB(lo)} ${hexB(hi)} $spacing3 ${opcode.mnemonic} (\$${hexW(indirectAddr)})" - } - AddrMode.IzX -> { - val zpAddr = memory[address++] - line += "${hexB(zpAddr)} $spacing2 ${opcode.mnemonic} (\$${hexB(zpAddr)},x)" - } - AddrMode.IzY -> { - val zpAddr = memory[address++] - line += "${hexB(zpAddr)} $spacing2 ${opcode.mnemonic} (\$${hexB(zpAddr)}),y" - } + when (opcode.mode) { + AddrMode.Acc -> { + line += "$spacing1 ${opcode.mnemonic} a" + } + AddrMode.Imp -> { + line += "$spacing1 ${opcode.mnemonic}" + } + AddrMode.Imm -> { + val value = memory[address++] + line += "${hexB(value)} $spacing2 ${opcode.mnemonic} #\$${hexB(value)}" + } + AddrMode.Zp -> { + val zpAddr = memory[address++] + line += "${hexB(zpAddr)} $spacing2 ${opcode.mnemonic} \$${hexB(zpAddr)}" + } + AddrMode.ZpX -> { + val zpAddr = memory[address++] + line += "${hexB(zpAddr)} $spacing2 ${opcode.mnemonic} \$${hexB(zpAddr)},x" + } + AddrMode.ZpY -> { + val zpAddr = memory[address++] + line += "${hexB(zpAddr)} $spacing2 ${opcode.mnemonic} \$${hexB(zpAddr)},y" + } + AddrMode.Rel -> { + val rel = memory[address++] + val target = + if (rel <= 0x7f) + address + rel + else + address - (256 - rel) + line += "${hexB(rel)} $spacing2 ${opcode.mnemonic} \$${hexW(target, true)}" + } + AddrMode.Abs -> { + val lo = memory[address++] + val hi = memory[address++] + val absAddr = lo.toInt() or (hi.toInt() shl 8) + line += "${hexB(lo)} ${hexB(hi)} $spacing3 ${opcode.mnemonic} \$${hexW(absAddr)}" + } + AddrMode.AbsX -> { + val lo = memory[address++] + val hi = memory[address++] + val absAddr = lo.toInt() or (hi.toInt() shl 8) + line += "${hexB(lo)} ${hexB(hi)} $spacing3 ${opcode.mnemonic} \$${hexW(absAddr)},x" + } + AddrMode.AbsY -> { + val lo = memory[address++] + val hi = memory[address++] + val absAddr = lo.toInt() or (hi.toInt() shl 8) + line += "${hexB(lo)} ${hexB(hi)} $spacing3 ${opcode.mnemonic} \$${hexW(absAddr)},y" + } + AddrMode.Ind -> { + val lo = memory[address++] + val hi = memory[address++] + val indirectAddr = lo.toInt() or (hi.toInt() shl 8) + line += "${hexB(lo)} ${hexB(hi)} $spacing3 ${opcode.mnemonic} (\$${hexW(indirectAddr)})" + } + AddrMode.IzX -> { + val zpAddr = memory[address++] + line += "${hexB(zpAddr)} $spacing2 ${opcode.mnemonic} (\$${hexB(zpAddr)},x)" + } + AddrMode.IzY -> { + val zpAddr = memory[address++] + line += "${hexB(zpAddr)} $spacing2 ${opcode.mnemonic} (\$${hexB(zpAddr)}),y" } } result.add(line) @@ -266,10 +266,6 @@ class Cpu6502(private val illegalInstrsAllowed: Boolean, private val stopOnBrk: currentInstruction = opcodes[currentOpcode] if (tracing) printState() - if (!currentInstruction.official && !illegalInstrsAllowed) { - throw InstructionError("illegal instructions not enabled") - } - breakpoints[PC]?.let { val oldPC = PC val oldOpcode = currentOpcode @@ -425,17 +421,17 @@ class Cpu6502(private val illegalInstrsAllowed: Boolean, private val stopOnBrk: pushStack(status.asByte().toInt()) } - private fun pushStack(data: Int) { + internal fun pushStack(data: Int) { write(SP or 0x0100, data) SP = (SP - 1) and 0xff } - private fun popStack(): Int { + internal fun popStack(): Int { SP = (SP + 1) and 0xff return read(SP or 0x0100) } - private fun popStackAddr(): Address { + internal fun popStackAddr(): Address { val lo = popStack() val hi = popStack() return lo or (hi shl 8) @@ -447,262 +443,262 @@ class Cpu6502(private val illegalInstrsAllowed: Boolean, private val stopOnBrk: // opcodes table from http://www.oxyron.de/html/opcodes02.html private val opcodes = listOf( - /* 00 */ Instruction("brk", AddrMode.Imp, 7, true, ::iBrk), - /* 01 */ Instruction("ora", AddrMode.IzX, 6, true, ::iOra), - /* 02 */ Instruction("???", AddrMode.Imp, 0, false, ::iInvalid), - /* 03 */ Instruction("slo", AddrMode.IzX, 8, false, ::iSlo), - /* 04 */ Instruction("nop", AddrMode.Zp, 3, false, ::iNop), - /* 05 */ Instruction("ora", AddrMode.Zp, 3, true, ::iOra), - /* 06 */ Instruction("asl", AddrMode.Zp, 5, true, ::iAsl), - /* 07 */ Instruction("slo", AddrMode.Zp, 5, false, ::iSlo), - /* 08 */ Instruction("php", AddrMode.Imp, 3, true, ::iPhp), - /* 09 */ Instruction("ora", AddrMode.Imm, 2, true, ::iOra), - /* 0a */ Instruction("asl", AddrMode.Acc, 2, true, ::iAsl), - /* 0b */ Instruction("anc", AddrMode.Imm, 2, false, ::iAnc), - /* 0c */ Instruction("nop", AddrMode.Abs, 4, false, ::iNop), - /* 0d */ Instruction("ora", AddrMode.Abs, 4, true, ::iOra), - /* 0e */ Instruction("asl", AddrMode.Abs, 6, true, ::iAsl), - /* 0f */ Instruction("slo", AddrMode.Abs, 6, false, ::iSlo), - /* 10 */ Instruction("bpl", AddrMode.Rel, 2, true, ::iBpl), - /* 11 */ Instruction("ora", AddrMode.IzY, 5, true, ::iOra), - /* 12 */ Instruction("???", AddrMode.Imp, 0, false, ::iInvalid), - /* 13 */ Instruction("slo", AddrMode.IzY, 6, false, ::iSlo), - /* 14 */ Instruction("nop", AddrMode.ZpX, 4, false, ::iNop), - /* 15 */ Instruction("ora", AddrMode.ZpX, 4, true, ::iOra), - /* 16 */ Instruction("asl", AddrMode.ZpX, 6, true, ::iAsl), - /* 17 */ Instruction("slo", AddrMode.ZpX, 6, false, ::iSlo), - /* 18 */ Instruction("clc", AddrMode.Imp, 2, true, ::iClc), - /* 19 */ Instruction("ora", AddrMode.AbsY, 4, true, ::iOra), - /* 1a */ Instruction("nop", AddrMode.Imp, 2, false, ::iNop), - /* 1b */ Instruction("slo", AddrMode.AbsY, 7, false, ::iSlo), - /* 1c */ Instruction("nop", AddrMode.AbsX, 4, false, ::iNop), - /* 1d */ Instruction("ora", AddrMode.AbsX, 4, true, ::iOra), - /* 1e */ Instruction("asl", AddrMode.AbsX, 7, true, ::iAsl), - /* 1f */ Instruction("slo", AddrMode.AbsX, 7, false, ::iSlo), - /* 20 */ Instruction("jsr", AddrMode.Abs, 6, true, ::iJsr), - /* 21 */ Instruction("and", AddrMode.IzX, 6, true, ::iAnd), - /* 22 */ Instruction("???", AddrMode.Imp, 0, false, ::iInvalid), - /* 23 */ Instruction("rla", AddrMode.IzX, 8, false, ::iRla), - /* 24 */ Instruction("bit", AddrMode.Zp, 3, true, ::iBit), - /* 25 */ Instruction("and", AddrMode.Zp, 3, true, ::iAnd), - /* 26 */ Instruction("rol", AddrMode.Zp, 5, true, ::iRol), - /* 27 */ Instruction("rla", AddrMode.Zp, 5, false, ::iRla), - /* 28 */ Instruction("plp", AddrMode.Imp, 4, true, ::iPlp), - /* 29 */ Instruction("and", AddrMode.Imm, 2, true, ::iAnd), - /* 2a */ Instruction("rol", AddrMode.Acc, 2, true, ::iRol), - /* 2b */ Instruction("anc", AddrMode.Imm, 2, false, ::iAnc), - /* 2c */ Instruction("bit", AddrMode.Abs, 4, true, ::iBit), - /* 2d */ Instruction("and", AddrMode.Abs, 4, true, ::iAnd), - /* 2e */ Instruction("rol", AddrMode.Abs, 6, true, ::iRol), - /* 2f */ Instruction("rla", AddrMode.Abs, 6, false, ::iRla), - /* 30 */ Instruction("bmi", AddrMode.Rel, 2, true, ::iBmi), - /* 31 */ Instruction("and", AddrMode.IzY, 5, true, ::iAnd), - /* 32 */ Instruction("???", AddrMode.Imp, 0, false, ::iInvalid), - /* 33 */ Instruction("rla", AddrMode.IzY, 8, false, ::iRla), - /* 34 */ Instruction("nop", AddrMode.ZpX, 4, false, ::iNop), - /* 35 */ Instruction("and", AddrMode.ZpX, 4, true, ::iAnd), - /* 36 */ Instruction("rol", AddrMode.ZpX, 6, true, ::iRol), - /* 37 */ Instruction("rla", AddrMode.ZpX, 6, false, ::iRla), - /* 38 */ Instruction("sec", AddrMode.Imp, 2, true, ::iSec), - /* 39 */ Instruction("and", AddrMode.AbsY, 4, true, ::iAnd), - /* 3a */ Instruction("nop", AddrMode.Imp, 2, false, ::iNop), - /* 3b */ Instruction("rla", AddrMode.AbsY, 7, false, ::iRla), - /* 3c */ Instruction("nop", AddrMode.AbsX, 4, false, ::iNop), - /* 3d */ Instruction("and", AddrMode.AbsX, 4, true, ::iAnd), - /* 3e */ Instruction("rol", AddrMode.AbsX, 7, true, ::iRol), - /* 3f */ Instruction("rla", AddrMode.AbsX, 7, false, ::iRla), - /* 40 */ Instruction("rti", AddrMode.Imp, 6, true, ::iRti), - /* 41 */ Instruction("eor", AddrMode.IzX, 6, true, ::iEor), - /* 42 */ Instruction("???", AddrMode.Imp, 0, false, ::iInvalid), - /* 43 */ Instruction("sre", AddrMode.IzX, 8, false, ::iSre), - /* 44 */ Instruction("nop", AddrMode.Zp, 3, false, ::iNop), - /* 45 */ Instruction("eor", AddrMode.Zp, 3, true, ::iEor), - /* 46 */ Instruction("lsr", AddrMode.Zp, 5, true, ::iLsr), - /* 47 */ Instruction("sre", AddrMode.Zp, 5, false, ::iSre), - /* 48 */ Instruction("pha", AddrMode.Imp, 3, true, ::iPha), - /* 49 */ Instruction("eor", AddrMode.Imm, 2, true, ::iEor), - /* 4a */ Instruction("lsr", AddrMode.Acc, 2, true, ::iLsr), - /* 4b */ Instruction("alr", AddrMode.Imm, 2, false, ::iAlr), - /* 4c */ Instruction("jmp", AddrMode.Abs, 3, true, ::iJmp), - /* 4d */ Instruction("eor", AddrMode.Abs, 4, true, ::iEor), - /* 4e */ Instruction("lsr", AddrMode.Abs, 6, true, ::iLsr), - /* 4f */ Instruction("sre", AddrMode.Abs, 6, false, ::iSre), - /* 50 */ Instruction("bvc", AddrMode.Rel, 2, true, ::iBvc), - /* 51 */ Instruction("eor", AddrMode.IzY, 5, true, ::iEor), - /* 52 */ Instruction("???", AddrMode.Imp, 0, false, ::iInvalid), - /* 53 */ Instruction("sre", AddrMode.IzY, 8, false, ::iSre), - /* 54 */ Instruction("nop", AddrMode.ZpX, 4, false, ::iNop), - /* 55 */ Instruction("eor", AddrMode.ZpX, 4, true, ::iEor), - /* 56 */ Instruction("lsr", AddrMode.ZpX, 6, true, ::iLsr), - /* 57 */ Instruction("sre", AddrMode.ZpX, 6, false, ::iSre), - /* 58 */ Instruction("cli", AddrMode.Imp, 2, true, ::iCli), - /* 59 */ Instruction("eor", AddrMode.AbsY, 4, true, ::iEor), - /* 5a */ Instruction("nop", AddrMode.Imp, 2, false, ::iNop), - /* 5b */ Instruction("sre", AddrMode.AbsY, 7, false, ::iSre), - /* 5c */ Instruction("nop", AddrMode.AbsX, 4, false, ::iNop), - /* 5d */ Instruction("eor", AddrMode.AbsX, 4, true, ::iEor), - /* 5e */ Instruction("lsr", AddrMode.AbsX, 7, true, ::iLsr), - /* 5f */ Instruction("sre", AddrMode.AbsX, 7, false, ::iSre), - /* 60 */ Instruction("rts", AddrMode.Imp, 6, true, ::iRts), - /* 61 */ Instruction("adc", AddrMode.IzX, 6, true, ::iAdc), - /* 62 */ Instruction("???", AddrMode.Imp, 0, false, ::iInvalid), - /* 63 */ Instruction("rra", AddrMode.IzX, 8, false, ::iRra), - /* 64 */ Instruction("nop", AddrMode.Zp, 3, false, ::iNop), - /* 65 */ Instruction("adc", AddrMode.Zp, 3, true, ::iAdc), - /* 66 */ Instruction("ror", AddrMode.Zp, 5, true, ::iRor), - /* 67 */ Instruction("rra", AddrMode.Zp, 5, false, ::iRra), - /* 68 */ Instruction("pla", AddrMode.Imp, 4, true, ::iPla), - /* 69 */ Instruction("adc", AddrMode.Imm, 2, true, ::iAdc), - /* 6a */ Instruction("ror", AddrMode.Acc, 2, true, ::iRor), - /* 6b */ Instruction("arr", AddrMode.Imm, 2, false, ::iArr), - /* 6c */ Instruction("jmp", AddrMode.Ind, 5, true, ::iJmp), - /* 6d */ Instruction("adc", AddrMode.Abs, 4, true, ::iAdc), - /* 6e */ Instruction("ror", AddrMode.Abs, 6, true, ::iRor), - /* 6f */ Instruction("rra", AddrMode.Abs, 6, false, ::iRra), - /* 70 */ Instruction("bvs", AddrMode.Rel, 2, true, ::iBvs), - /* 71 */ Instruction("adc", AddrMode.IzY, 5, true, ::iAdc), - /* 72 */ Instruction("???", AddrMode.Imp, 0, false, ::iInvalid), - /* 73 */ Instruction("rra", AddrMode.IzY, 8, false, ::iRra), - /* 74 */ Instruction("nop", AddrMode.ZpX, 4, false, ::iNop), - /* 75 */ Instruction("adc", AddrMode.ZpX, 4, true, ::iAdc), - /* 76 */ Instruction("ror", AddrMode.ZpX, 6, true, ::iRor), - /* 77 */ Instruction("rra", AddrMode.ZpX, 6, false, ::iRra), - /* 78 */ Instruction("sei", AddrMode.Imp, 2, true, ::iSei), - /* 79 */ Instruction("adc", AddrMode.AbsY, 4, true, ::iAdc), - /* 7a */ Instruction("nop", AddrMode.Imp, 2, false, ::iNop), - /* 7b */ Instruction("rra", AddrMode.AbsY, 7, false, ::iRra), - /* 7c */ Instruction("nop", AddrMode.AbsX, 4, false, ::iNop), - /* 7d */ Instruction("adc", AddrMode.AbsX, 4, true, ::iAdc), - /* 7e */ Instruction("ror", AddrMode.AbsX, 7, true, ::iRor), - /* 7f */ Instruction("rra", AddrMode.AbsX, 7, false, ::iRra), - /* 80 */ Instruction("nop", AddrMode.Imm, 2, false, ::iNop), - /* 81 */ Instruction("sta", AddrMode.IzX, 6, true, ::iSta), - /* 82 */ Instruction("nop", AddrMode.Imm, 2, false, ::iNop), - /* 83 */ Instruction("sax", AddrMode.IzX, 6, false, ::iSax), - /* 84 */ Instruction("sty", AddrMode.Zp, 3, true, ::iSty), - /* 85 */ Instruction("sta", AddrMode.Zp, 3, true, ::iSta), - /* 86 */ Instruction("stx", AddrMode.Zp, 3, true, ::iStx), - /* 87 */ Instruction("sax", AddrMode.Zp, 3, false, ::iSax), - /* 88 */ Instruction("dey", AddrMode.Imp, 2, true, ::iDey), - /* 89 */ Instruction("nop", AddrMode.Imm, 2, false, ::iNop), - /* 8a */ Instruction("txa", AddrMode.Imp, 2, true, ::iTxa), - /* 8b */ Instruction("xaa", AddrMode.Imm, 2, false, ::iXaa), - /* 8c */ Instruction("sty", AddrMode.Abs, 4, true, ::iSty), - /* 8d */ Instruction("sta", AddrMode.Abs, 4, true, ::iSta), - /* 8e */ Instruction("stx", AddrMode.Abs, 4, true, ::iStx), - /* 8f */ Instruction("sax", AddrMode.Abs, 4, true, ::iSax), - /* 90 */ Instruction("bcc", AddrMode.Rel, 2, true, ::iBcc), - /* 91 */ Instruction("sta", AddrMode.IzY, 6, true, ::iSta), - /* 92 */ Instruction("???", AddrMode.Imp, 0, false, ::iInvalid), - /* 93 */ Instruction("ahx", AddrMode.IzY, 6, false, ::iAhx), - /* 94 */ Instruction("sty", AddrMode.ZpX, 4, true, ::iSty), - /* 95 */ Instruction("sta", AddrMode.ZpX, 4, true, ::iSta), - /* 96 */ Instruction("stx", AddrMode.ZpY, 4, true, ::iStx), - /* 97 */ Instruction("sax", AddrMode.ZpY, 4, false, ::iSax), - /* 98 */ Instruction("tya", AddrMode.Imp, 2, true, ::iTya), - /* 99 */ Instruction("sta", AddrMode.AbsY, 5, true, ::iSta), - /* 9a */ Instruction("txs", AddrMode.Imp, 2, true, ::iTxs), - /* 9b */ Instruction("tas", AddrMode.AbsY, 5, false, ::iTas), - /* 9c */ Instruction("shy", AddrMode.AbsX, 5, false, ::iShy), - /* 9d */ Instruction("sta", AddrMode.AbsX, 5, true, ::iSta), - /* 9e */ Instruction("shx", AddrMode.AbsY, 5, false, ::iShx), - /* 9f */ Instruction("ahx", AddrMode.AbsY, 5, false, ::iAhx), - /* a0 */ Instruction("ldy", AddrMode.Imm, 2, true, ::iLdy), - /* a1 */ Instruction("lda", AddrMode.IzX, 6, true, ::iLda), - /* a2 */ Instruction("ldx", AddrMode.Imm, 2, true, ::iLdx), - /* a3 */ Instruction("lax", AddrMode.IzX, 6, false, ::iLax), - /* a4 */ Instruction("ldy", AddrMode.Zp, 3, true, ::iLdy), - /* a5 */ Instruction("lda", AddrMode.Zp, 3, true, ::iLda), - /* a6 */ Instruction("ldx", AddrMode.Zp, 3, true, ::iLdx), - /* a7 */ Instruction("lax", AddrMode.Zp, 3, false, ::iLax), - /* a8 */ Instruction("tay", AddrMode.Imp, 2, true, ::iTay), - /* a9 */ Instruction("lda", AddrMode.Imm, 2, true, ::iLda), - /* aa */ Instruction("tax", AddrMode.Imp, 2, true, ::iTax), - /* ab */ Instruction("lax", AddrMode.Imm, 2, false, ::iLax), - /* ac */ Instruction("ldy", AddrMode.Abs, 4, true, ::iLdy), - /* ad */ Instruction("lda", AddrMode.Abs, 4, true, ::iLda), - /* ae */ Instruction("ldx", AddrMode.Abs, 4, true, ::iLdx), - /* af */ Instruction("lax", AddrMode.Abs, 4, false, ::iLax), - /* b0 */ Instruction("bcs", AddrMode.Rel, 2, true, ::iBcs), - /* b1 */ Instruction("lda", AddrMode.IzY, 5, true, ::iLda), - /* b2 */ Instruction("???", AddrMode.Imp, 0, false, ::iInvalid), - /* b3 */ Instruction("lax", AddrMode.IzY, 5, false, ::iLax), - /* b4 */ Instruction("ldy", AddrMode.ZpX, 4, true, ::iLdy), - /* b5 */ Instruction("lda", AddrMode.ZpX, 4, true, ::iLda), - /* b6 */ Instruction("ldx", AddrMode.ZpY, 4, true, ::iLdx), - /* b7 */ Instruction("lax", AddrMode.ZpY, 4, false, ::iLax), - /* b8 */ Instruction("clv", AddrMode.Imp, 2, true, ::iClv), - /* b9 */ Instruction("lda", AddrMode.AbsY, 4, true, ::iLda), - /* ba */ Instruction("tsx", AddrMode.Imp, 2, true, ::iTsx), - /* bb */ Instruction("las", AddrMode.AbsY, 4, false, ::iLas), - /* bc */ Instruction("ldy", AddrMode.AbsX, 4, true, ::iLdy), - /* bd */ Instruction("lda", AddrMode.AbsX, 4, true, ::iLda), - /* be */ Instruction("ldx", AddrMode.AbsY, 4, true, ::iLdx), - /* bf */ Instruction("lax", AddrMode.AbsY, 4, false, ::iLax), - /* c0 */ Instruction("cpy", AddrMode.Imm, 2, true, ::iCpy), - /* c1 */ Instruction("cmp", AddrMode.IzX, 6, true, ::iCmp), - /* c2 */ Instruction("nop", AddrMode.Imm, 2, false, ::iNop), - /* c3 */ Instruction("dcp", AddrMode.IzX, 8, false, ::iDcp), - /* c4 */ Instruction("cpy", AddrMode.Zp, 3, true, ::iCpy), - /* c5 */ Instruction("cmp", AddrMode.Zp, 3, true, ::iCmp), - /* c6 */ Instruction("dec", AddrMode.Zp, 5, true, ::iDec), - /* c7 */ Instruction("dcp", AddrMode.Zp, 5, false, ::iDcp), - /* c8 */ Instruction("iny", AddrMode.Imp, 2, true, ::iIny), - /* c9 */ Instruction("cmp", AddrMode.Imm, 2, true, ::iCmp), - /* ca */ Instruction("dex", AddrMode.Imp, 2, true, ::iDex), - /* cb */ Instruction("axs", AddrMode.Imm, 2, false, ::iAxs), - /* cc */ Instruction("cpy", AddrMode.Abs, 4, true, ::iCpy), - /* cd */ Instruction("cmp", AddrMode.Abs, 4, true, ::iCmp), - /* ce */ Instruction("dec", AddrMode.Abs, 6, true, ::iDec), - /* cf */ Instruction("dcp", AddrMode.Abs, 6, false, ::iDcp), - /* d0 */ Instruction("bne", AddrMode.Rel, 2, true, ::iBne), - /* d1 */ Instruction("cmp", AddrMode.IzY, 5, true, ::iCmp), - /* d2 */ Instruction("???", AddrMode.Imp, 0, false, ::iInvalid), - /* d3 */ Instruction("dcp", AddrMode.IzY, 8, false, ::iDcp), - /* d4 */ Instruction("nop", AddrMode.ZpX, 4, false, ::iNop), - /* d5 */ Instruction("cmp", AddrMode.ZpX, 4, true, ::iCmp), - /* d6 */ Instruction("dec", AddrMode.ZpX, 6, true, ::iDec), - /* d7 */ Instruction("dcp", AddrMode.ZpX, 6, false, ::iDcp), - /* d8 */ Instruction("cld", AddrMode.Imp, 2, true, ::iCld), - /* d9 */ Instruction("cmp", AddrMode.AbsY, 4, true, ::iCmp), - /* da */ Instruction("nop", AddrMode.Imp, 2, false, ::iNop), - /* db */ Instruction("dcp", AddrMode.AbsY, 7, false, ::iDcp), - /* dc */ Instruction("nop", AddrMode.AbsX, 4, false, ::iNop), - /* dd */ Instruction("cmp", AddrMode.AbsX, 4, true, ::iCmp), - /* de */ Instruction("dec", AddrMode.AbsX, 7, true, ::iDec), - /* df */ Instruction("dcp", AddrMode.AbsX, 7, false, ::iDcp), - /* e0 */ Instruction("cpx", AddrMode.Imm, 2, true, ::iCpx), - /* e1 */ Instruction("sbc", AddrMode.IzX, 6, true, ::iSbc), - /* e2 */ Instruction("nop", AddrMode.Imm, 2, false, ::iNop), - /* e3 */ Instruction("isc", AddrMode.IzX, 8, false, ::iIsc), - /* e4 */ Instruction("cpx", AddrMode.Zp, 3, true, ::iCpx), - /* e5 */ Instruction("sbc", AddrMode.Zp, 3, true, ::iSbc), - /* e6 */ Instruction("inc", AddrMode.Zp, 5, true, ::iInc), - /* e7 */ Instruction("isc", AddrMode.Zp, 5, false, ::iIsc), - /* e8 */ Instruction("inx", AddrMode.Imp, 2, true, ::iInx), - /* e9 */ Instruction("sbc", AddrMode.Imm, 2, true, ::iSbc), - /* ea */ Instruction("nop", AddrMode.Imp, 2, true, ::iNop), - /* eb */ Instruction("sbc", AddrMode.Imm, 2, false, ::iSbc), - /* ec */ Instruction("cpx", AddrMode.Abs, 4, true, ::iCpx), - /* ed */ Instruction("sbc", AddrMode.Abs, 4, true, ::iSbc), - /* ee */ Instruction("inc", AddrMode.Abs, 6, true, ::iInc), - /* ef */ Instruction("isc", AddrMode.Abs, 6, true, ::iIsc), - /* f0 */ Instruction("beq", AddrMode.Rel, 2, true, ::iBeq), - /* f1 */ Instruction("sbc", AddrMode.IzY, 5, true, ::iSbc), - /* f2 */ Instruction("???", AddrMode.Imp, 0, false, ::iInvalid), - /* f3 */ Instruction("isc", AddrMode.IzY, 8, false, ::iIsc), - /* f4 */ Instruction("nop", AddrMode.ZpX, 4, false, ::iNop), - /* f5 */ Instruction("sbc", AddrMode.ZpX, 4, true, ::iSbc), - /* f6 */ Instruction("inc", AddrMode.ZpX, 6, true, ::iInc), - /* f7 */ Instruction("isc", AddrMode.ZpX, 6, false, ::iIsc), - /* f8 */ Instruction("sed", AddrMode.Imp, 2, true, ::iSed), - /* f9 */ Instruction("sbc", AddrMode.AbsY, 4, true, ::iSbc), - /* fa */ Instruction("nop", AddrMode.Imp, 2, false, ::iNop), - /* fb */ Instruction("isc", AddrMode.AbsY, 7, false, ::iIsc), - /* fc */ Instruction("nop", AddrMode.AbsX, 4, false, ::iNop), - /* fd */ Instruction("sbc", AddrMode.AbsX, 4, true, ::iSbc), - /* fe */ Instruction("inc", AddrMode.AbsX, 7, true, ::iInc), - /* ff */ Instruction("isc", AddrMode.AbsX, 7, false, ::iIsc) + Instruction(0x00, "brk", AddrMode.Imp, 7, true, ::iBrk), + Instruction(0x01, "ora", AddrMode.IzX, 6, true, ::iOra), + Instruction(0x02, "???", AddrMode.Imp, 0, false, ::iInvalid), + Instruction(0x03, "slo", AddrMode.IzX, 8, false, ::iSlo), + Instruction(0x04, "nop", AddrMode.Zp, 3, false, ::iNop), + Instruction(0x05, "ora", AddrMode.Zp, 3, true, ::iOra), + Instruction(0x06, "asl", AddrMode.Zp, 5, true, ::iAsl), + Instruction(0x07, "slo", AddrMode.Zp, 5, false, ::iSlo), + Instruction(0x08, "php", AddrMode.Imp, 3, true, ::iPhp), + Instruction(0x09, "ora", AddrMode.Imm, 2, true, ::iOra), + Instruction(0x0a, "asl", AddrMode.Acc, 2, true, ::iAsl), + Instruction(0x0b, "anc", AddrMode.Imm, 2, false, ::iAnc), + Instruction(0x0c, "nop", AddrMode.Abs, 4, false, ::iNop), + Instruction(0x0d, "ora", AddrMode.Abs, 4, true, ::iOra), + Instruction(0x0e, "asl", AddrMode.Abs, 6, true, ::iAsl), + Instruction(0x0f, "slo", AddrMode.Abs, 6, false, ::iSlo), + Instruction(0x10, "bpl", AddrMode.Rel, 2, true, ::iBpl), + Instruction(0x11, "ora", AddrMode.IzY, 5, true, ::iOra), + Instruction(0x12, "???", AddrMode.Imp, 0, false, ::iInvalid), + Instruction(0x13, "slo", AddrMode.IzY, 6, false, ::iSlo), + Instruction(0x14, "nop", AddrMode.ZpX, 4, false, ::iNop), + Instruction(0x15, "ora", AddrMode.ZpX, 4, true, ::iOra), + Instruction(0x16, "asl", AddrMode.ZpX, 6, true, ::iAsl), + Instruction(0x17, "slo", AddrMode.ZpX, 6, false, ::iSlo), + Instruction(0x18, "clc", AddrMode.Imp, 2, true, ::iClc), + Instruction(0x19, "ora", AddrMode.AbsY, 4, true, ::iOra), + Instruction(0x1a, "nop", AddrMode.Imp, 2, false, ::iNop), + Instruction(0x1b, "slo", AddrMode.AbsY, 7, false, ::iSlo), + Instruction(0x1c, "nop", AddrMode.AbsX, 4, false, ::iNop), + Instruction(0x1d, "ora", AddrMode.AbsX, 4, true, ::iOra), + Instruction(0x1e, "asl", AddrMode.AbsX, 7, true, ::iAsl), + Instruction(0x1f, "slo", AddrMode.AbsX, 7, false, ::iSlo), + Instruction(0x20, "jsr", AddrMode.Abs, 6, true, ::iJsr), + Instruction(0x21, "and", AddrMode.IzX, 6, true, ::iAnd), + Instruction(0x22, "???", AddrMode.Imp, 0, false, ::iInvalid), + Instruction(0x23, "rla", AddrMode.IzX, 8, false, ::iRla), + Instruction(0x24, "bit", AddrMode.Zp, 3, true, ::iBit), + Instruction(0x25, "and", AddrMode.Zp, 3, true, ::iAnd), + Instruction(0x26, "rol", AddrMode.Zp, 5, true, ::iRol), + Instruction(0x27, "rla", AddrMode.Zp, 5, false, ::iRla), + Instruction(0x28, "plp", AddrMode.Imp, 4, true, ::iPlp), + Instruction(0x29, "and", AddrMode.Imm, 2, true, ::iAnd), + Instruction(0x2a, "rol", AddrMode.Acc, 2, true, ::iRol), + Instruction(0x2b, "anc", AddrMode.Imm, 2, false, ::iAnc), + Instruction(0x2c, "bit", AddrMode.Abs, 4, true, ::iBit), + Instruction(0x2d, "and", AddrMode.Abs, 4, true, ::iAnd), + Instruction(0x2e, "rol", AddrMode.Abs, 6, true, ::iRol), + Instruction(0x2f, "rla", AddrMode.Abs, 6, false, ::iRla), + Instruction(0x30, "bmi", AddrMode.Rel, 2, true, ::iBmi), + Instruction(0x31, "and", AddrMode.IzY, 5, true, ::iAnd), + Instruction(0x32, "???", AddrMode.Imp, 0, false, ::iInvalid), + Instruction(0x33, "rla", AddrMode.IzY, 8, false, ::iRla), + Instruction(0x34, "nop", AddrMode.ZpX, 4, false, ::iNop), + Instruction(0x35, "and", AddrMode.ZpX, 4, true, ::iAnd), + Instruction(0x36, "rol", AddrMode.ZpX, 6, true, ::iRol), + Instruction(0x37, "rla", AddrMode.ZpX, 6, false, ::iRla), + Instruction(0x38, "sec", AddrMode.Imp, 2, true, ::iSec), + Instruction(0x39, "and", AddrMode.AbsY, 4, true, ::iAnd), + Instruction(0x3a, "nop", AddrMode.Imp, 2, false, ::iNop), + Instruction(0x3b, "rla", AddrMode.AbsY, 7, false, ::iRla), + Instruction(0x3c, "nop", AddrMode.AbsX, 4, false, ::iNop), + Instruction(0x3d, "and", AddrMode.AbsX, 4, true, ::iAnd), + Instruction(0x3e, "rol", AddrMode.AbsX, 7, true, ::iRol), + Instruction(0x3f, "rla", AddrMode.AbsX, 7, false, ::iRla), + Instruction(0x40, "rti", AddrMode.Imp, 6, true, ::iRti), + Instruction(0x41, "eor", AddrMode.IzX, 6, true, ::iEor), + Instruction(0x42, "???", AddrMode.Imp, 0, false, ::iInvalid), + Instruction(0x43, "sre", AddrMode.IzX, 8, false, ::iSre), + Instruction(0x44, "nop", AddrMode.Zp, 3, false, ::iNop), + Instruction(0x45, "eor", AddrMode.Zp, 3, true, ::iEor), + Instruction(0x46, "lsr", AddrMode.Zp, 5, true, ::iLsr), + Instruction(0x47, "sre", AddrMode.Zp, 5, false, ::iSre), + Instruction(0x48, "pha", AddrMode.Imp, 3, true, ::iPha), + Instruction(0x49, "eor", AddrMode.Imm, 2, true, ::iEor), + Instruction(0x4a, "lsr", AddrMode.Acc, 2, true, ::iLsr), + Instruction(0x4b, "alr", AddrMode.Imm, 2, false, ::iAlr), + Instruction(0x4c, "jmp", AddrMode.Abs, 3, true, ::iJmp), + Instruction(0x4d, "eor", AddrMode.Abs, 4, true, ::iEor), + Instruction(0x4e, "lsr", AddrMode.Abs, 6, true, ::iLsr), + Instruction(0x4f, "sre", AddrMode.Abs, 6, false, ::iSre), + Instruction(0x50, "bvc", AddrMode.Rel, 2, true, ::iBvc), + Instruction(0x51, "eor", AddrMode.IzY, 5, true, ::iEor), + Instruction(0x52, "???", AddrMode.Imp, 0, false, ::iInvalid), + Instruction(0x53, "sre", AddrMode.IzY, 8, false, ::iSre), + Instruction(0x54, "nop", AddrMode.ZpX, 4, false, ::iNop), + Instruction(0x55, "eor", AddrMode.ZpX, 4, true, ::iEor), + Instruction(0x56, "lsr", AddrMode.ZpX, 6, true, ::iLsr), + Instruction(0x57, "sre", AddrMode.ZpX, 6, false, ::iSre), + Instruction(0x58, "cli", AddrMode.Imp, 2, true, ::iCli), + Instruction(0x59, "eor", AddrMode.AbsY, 4, true, ::iEor), + Instruction(0x5a, "nop", AddrMode.Imp, 2, false, ::iNop), + Instruction(0x5b, "sre", AddrMode.AbsY, 7, false, ::iSre), + Instruction(0x5c, "nop", AddrMode.AbsX, 4, false, ::iNop), + Instruction(0x5d, "eor", AddrMode.AbsX, 4, true, ::iEor), + Instruction(0x5e, "lsr", AddrMode.AbsX, 7, true, ::iLsr), + Instruction(0x5f, "sre", AddrMode.AbsX, 7, false, ::iSre), + Instruction(0x60, "rts", AddrMode.Imp, 6, true, ::iRts), + Instruction(0x61, "adc", AddrMode.IzX, 6, true, ::iAdc), + Instruction(0x62, "???", AddrMode.Imp, 0, false, ::iInvalid), + Instruction(0x63, "rra", AddrMode.IzX, 8, false, ::iRra), + Instruction(0x64, "nop", AddrMode.Zp, 3, false, ::iNop), + Instruction(0x65, "adc", AddrMode.Zp, 3, true, ::iAdc), + Instruction(0x66, "ror", AddrMode.Zp, 5, true, ::iRor), + Instruction(0x67, "rra", AddrMode.Zp, 5, false, ::iRra), + Instruction(0x68, "pla", AddrMode.Imp, 4, true, ::iPla), + Instruction(0x69, "adc", AddrMode.Imm, 2, true, ::iAdc), + Instruction(0x6a, "ror", AddrMode.Acc, 2, true, ::iRor), + Instruction(0x6b, "arr", AddrMode.Imm, 2, false, ::iArr), + Instruction(0x6c, "jmp", AddrMode.Ind, 5, true, ::iJmp), + Instruction(0x6d, "adc", AddrMode.Abs, 4, true, ::iAdc), + Instruction(0x6e, "ror", AddrMode.Abs, 6, true, ::iRor), + Instruction(0x6f, "rra", AddrMode.Abs, 6, false, ::iRra), + Instruction(0x70, "bvs", AddrMode.Rel, 2, true, ::iBvs), + Instruction(0x71, "adc", AddrMode.IzY, 5, true, ::iAdc), + Instruction(0x72, "???", AddrMode.Imp, 0, false, ::iInvalid), + Instruction(0x73, "rra", AddrMode.IzY, 8, false, ::iRra), + Instruction(0x74, "nop", AddrMode.ZpX, 4, false, ::iNop), + Instruction(0x75, "adc", AddrMode.ZpX, 4, true, ::iAdc), + Instruction(0x76, "ror", AddrMode.ZpX, 6, true, ::iRor), + Instruction(0x77, "rra", AddrMode.ZpX, 6, false, ::iRra), + Instruction(0x78, "sei", AddrMode.Imp, 2, true, ::iSei), + Instruction(0x79, "adc", AddrMode.AbsY, 4, true, ::iAdc), + Instruction(0x7a, "nop", AddrMode.Imp, 2, false, ::iNop), + Instruction(0x7b, "rra", AddrMode.AbsY, 7, false, ::iRra), + Instruction(0x7c, "nop", AddrMode.AbsX, 4, false, ::iNop), + Instruction(0x7d, "adc", AddrMode.AbsX, 4, true, ::iAdc), + Instruction(0x7e, "ror", AddrMode.AbsX, 7, true, ::iRor), + Instruction(0x7f, "rra", AddrMode.AbsX, 7, false, ::iRra), + Instruction(0x80, "nop", AddrMode.Imm, 2, false, ::iNop), + Instruction(0x81, "sta", AddrMode.IzX, 6, true, ::iSta), + Instruction(0x82, "nop", AddrMode.Imm, 2, false, ::iNop), + Instruction(0x83, "sax", AddrMode.IzX, 6, false, ::iSax), + Instruction(0x84, "sty", AddrMode.Zp, 3, true, ::iSty), + Instruction(0x85, "sta", AddrMode.Zp, 3, true, ::iSta), + Instruction(0x86, "stx", AddrMode.Zp, 3, true, ::iStx), + Instruction(0x87, "sax", AddrMode.Zp, 3, false, ::iSax), + Instruction(0x88, "dey", AddrMode.Imp, 2, true, ::iDey), + Instruction(0x89, "nop", AddrMode.Imm, 2, false, ::iNop), + Instruction(0x8a, "txa", AddrMode.Imp, 2, true, ::iTxa), + Instruction(0x8b, "xaa", AddrMode.Imm, 2, false, ::iXaa), + Instruction(0x8c, "sty", AddrMode.Abs, 4, true, ::iSty), + Instruction(0x8d, "sta", AddrMode.Abs, 4, true, ::iSta), + Instruction(0x8e, "stx", AddrMode.Abs, 4, true, ::iStx), + Instruction(0x8f, "sax", AddrMode.Abs, 4, true, ::iSax), + Instruction(0x90, "bcc", AddrMode.Rel, 2, true, ::iBcc), + Instruction(0x91, "sta", AddrMode.IzY, 6, true, ::iSta), + Instruction(0x92, "???", AddrMode.Imp, 0, false, ::iInvalid), + Instruction(0x93, "ahx", AddrMode.IzY, 6, false, ::iAhx), + Instruction(0x94, "sty", AddrMode.ZpX, 4, true, ::iSty), + Instruction(0x95, "sta", AddrMode.ZpX, 4, true, ::iSta), + Instruction(0x96, "stx", AddrMode.ZpY, 4, true, ::iStx), + Instruction(0x97, "sax", AddrMode.ZpY, 4, false, ::iSax), + Instruction(0x98, "tya", AddrMode.Imp, 2, true, ::iTya), + Instruction(0x99, "sta", AddrMode.AbsY, 5, true, ::iSta), + Instruction(0x9a, "txs", AddrMode.Imp, 2, true, ::iTxs), + Instruction(0x9b, "tas", AddrMode.AbsY, 5, false, ::iTas), + Instruction(0x9c, "shy", AddrMode.AbsX, 5, false, ::iShy), + Instruction(0x9d, "sta", AddrMode.AbsX, 5, true, ::iSta), + Instruction(0x9e, "shx", AddrMode.AbsY, 5, false, ::iShx), + Instruction(0x9f, "ahx", AddrMode.AbsY, 5, false, ::iAhx), + Instruction(0xa0, "ldy", AddrMode.Imm, 2, true, ::iLdy), + Instruction(0xa1, "lda", AddrMode.IzX, 6, true, ::iLda), + Instruction(0xa2, "ldx", AddrMode.Imm, 2, true, ::iLdx), + Instruction(0xa3, "lax", AddrMode.IzX, 6, false, ::iLax), + Instruction(0xa4, "ldy", AddrMode.Zp, 3, true, ::iLdy), + Instruction(0xa5, "lda", AddrMode.Zp, 3, true, ::iLda), + Instruction(0xa6, "ldx", AddrMode.Zp, 3, true, ::iLdx), + Instruction(0xa7, "lax", AddrMode.Zp, 3, false, ::iLax), + Instruction(0xa8, "tay", AddrMode.Imp, 2, true, ::iTay), + Instruction(0xa9, "lda", AddrMode.Imm, 2, true, ::iLda), + Instruction(0xaa, "tax", AddrMode.Imp, 2, true, ::iTax), + Instruction(0xab, "lax", AddrMode.Imm, 2, false, ::iLax), + Instruction(0xac, "ldy", AddrMode.Abs, 4, true, ::iLdy), + Instruction(0xad, "lda", AddrMode.Abs, 4, true, ::iLda), + Instruction(0xae, "ldx", AddrMode.Abs, 4, true, ::iLdx), + Instruction(0xaf, "lax", AddrMode.Abs, 4, false, ::iLax), + Instruction(0xb0, "bcs", AddrMode.Rel, 2, true, ::iBcs), + Instruction(0xb1, "lda", AddrMode.IzY, 5, true, ::iLda), + Instruction(0xb2, "???", AddrMode.Imp, 0, false, ::iInvalid), + Instruction(0xb3, "lax", AddrMode.IzY, 5, false, ::iLax), + Instruction(0xb4, "ldy", AddrMode.ZpX, 4, true, ::iLdy), + Instruction(0xb5, "lda", AddrMode.ZpX, 4, true, ::iLda), + Instruction(0xb6, "ldx", AddrMode.ZpY, 4, true, ::iLdx), + Instruction(0xb7, "lax", AddrMode.ZpY, 4, false, ::iLax), + Instruction(0xb8, "clv", AddrMode.Imp, 2, true, ::iClv), + Instruction(0xb9, "lda", AddrMode.AbsY, 4, true, ::iLda), + Instruction(0xba, "tsx", AddrMode.Imp, 2, true, ::iTsx), + Instruction(0xbb, "las", AddrMode.AbsY, 4, false, ::iLas), + Instruction(0xbc, "ldy", AddrMode.AbsX, 4, true, ::iLdy), + Instruction(0xbd, "lda", AddrMode.AbsX, 4, true, ::iLda), + Instruction(0xbe, "ldx", AddrMode.AbsY, 4, true, ::iLdx), + Instruction(0xbf, "lax", AddrMode.AbsY, 4, false, ::iLax), + Instruction(0xc0, "cpy", AddrMode.Imm, 2, true, ::iCpy), + Instruction(0xc1, "cmp", AddrMode.IzX, 6, true, ::iCmp), + Instruction(0xc2, "nop", AddrMode.Imm, 2, false, ::iNop), + Instruction(0xc3, "dcp", AddrMode.IzX, 8, false, ::iDcp), + Instruction(0xc4, "cpy", AddrMode.Zp, 3, true, ::iCpy), + Instruction(0xc5, "cmp", AddrMode.Zp, 3, true, ::iCmp), + Instruction(0xc6, "dec", AddrMode.Zp, 5, true, ::iDec), + Instruction(0xc7, "dcp", AddrMode.Zp, 5, false, ::iDcp), + Instruction(0xc8, "iny", AddrMode.Imp, 2, true, ::iIny), + Instruction(0xc9, "cmp", AddrMode.Imm, 2, true, ::iCmp), + Instruction(0xca, "dex", AddrMode.Imp, 2, true, ::iDex), + Instruction(0xcb, "axs", AddrMode.Imm, 2, false, ::iAxs), + Instruction(0xcc, "cpy", AddrMode.Abs, 4, true, ::iCpy), + Instruction(0xcd, "cmp", AddrMode.Abs, 4, true, ::iCmp), + Instruction(0xce, "dec", AddrMode.Abs, 6, true, ::iDec), + Instruction(0xcf, "dcp", AddrMode.Abs, 6, false, ::iDcp), + Instruction(0xd0, "bne", AddrMode.Rel, 2, true, ::iBne), + Instruction(0xd1, "cmp", AddrMode.IzY, 5, true, ::iCmp), + Instruction(0xd2, "???", AddrMode.Imp, 0, false, ::iInvalid), + Instruction(0xd3, "dcp", AddrMode.IzY, 8, false, ::iDcp), + Instruction(0xd4, "nop", AddrMode.ZpX, 4, false, ::iNop), + Instruction(0xd5, "cmp", AddrMode.ZpX, 4, true, ::iCmp), + Instruction(0xd6, "dec", AddrMode.ZpX, 6, true, ::iDec), + Instruction(0xd7, "dcp", AddrMode.ZpX, 6, false, ::iDcp), + Instruction(0xd8, "cld", AddrMode.Imp, 2, true, ::iCld), + Instruction(0xd9, "cmp", AddrMode.AbsY, 4, true, ::iCmp), + Instruction(0xda, "nop", AddrMode.Imp, 2, false, ::iNop), + Instruction(0xdb, "dcp", AddrMode.AbsY, 7, false, ::iDcp), + Instruction(0xdc, "nop", AddrMode.AbsX, 4, false, ::iNop), + Instruction(0xdd, "cmp", AddrMode.AbsX, 4, true, ::iCmp), + Instruction(0xde, "dec", AddrMode.AbsX, 7, true, ::iDec), + Instruction(0xdf, "dcp", AddrMode.AbsX, 7, false, ::iDcp), + Instruction(0xe0, "cpx", AddrMode.Imm, 2, true, ::iCpx), + Instruction(0xe1, "sbc", AddrMode.IzX, 6, true, ::iSbc), + Instruction(0xe2, "nop", AddrMode.Imm, 2, false, ::iNop), + Instruction(0xe3, "isc", AddrMode.IzX, 8, false, ::iIsc), + Instruction(0xe4, "cpx", AddrMode.Zp, 3, true, ::iCpx), + Instruction(0xe5, "sbc", AddrMode.Zp, 3, true, ::iSbc), + Instruction(0xe6, "inc", AddrMode.Zp, 5, true, ::iInc), + Instruction(0xe7, "isc", AddrMode.Zp, 5, false, ::iIsc), + Instruction(0xe8, "inx", AddrMode.Imp, 2, true, ::iInx), + Instruction(0xe9, "sbc", AddrMode.Imm, 2, true, ::iSbc), + Instruction(0xea, "nop", AddrMode.Imp, 2, true, ::iNop), + Instruction(0xeb, "sbc", AddrMode.Imm, 2, false, ::iSbc), + Instruction(0xec, "cpx", AddrMode.Abs, 4, true, ::iCpx), + Instruction(0xed, "sbc", AddrMode.Abs, 4, true, ::iSbc), + Instruction(0xee, "inc", AddrMode.Abs, 6, true, ::iInc), + Instruction(0xef, "isc", AddrMode.Abs, 6, true, ::iIsc), + Instruction(0xf0, "beq", AddrMode.Rel, 2, true, ::iBeq), + Instruction(0xf1, "sbc", AddrMode.IzY, 5, true, ::iSbc), + Instruction(0xf2, "???", AddrMode.Imp, 0, false, ::iInvalid), + Instruction(0xf3, "isc", AddrMode.IzY, 8, false, ::iIsc), + Instruction(0xf4, "nop", AddrMode.ZpX, 4, false, ::iNop), + Instruction(0xf5, "sbc", AddrMode.ZpX, 4, true, ::iSbc), + Instruction(0xf6, "inc", AddrMode.ZpX, 6, true, ::iInc), + Instruction(0xf7, "isc", AddrMode.ZpX, 6, false, ::iIsc), + Instruction(0xf8, "sed", AddrMode.Imp, 2, true, ::iSed), + Instruction(0xf9, "sbc", AddrMode.AbsY, 4, true, ::iSbc), + Instruction(0xfa, "nop", AddrMode.Imp, 2, false, ::iNop), + Instruction(0xfb, "isc", AddrMode.AbsY, 7, false, ::iIsc), + Instruction(0xfc, "nop", AddrMode.AbsX, 4, false, ::iNop), + Instruction(0xfd, "sbc", AddrMode.AbsX, 4, true, ::iSbc), + Instruction(0xfe, "inc", AddrMode.AbsX, 7, true, ::iInc), + Instruction(0xff, "isc", AddrMode.AbsX, 7, false, ::iIsc) ).toTypedArray() @@ -1101,75 +1097,75 @@ class Cpu6502(private val illegalInstrsAllowed: Boolean, private val stopOnBrk: // unofficial/illegal instructions private fun iAhx() { - TODO() + TODO("ahx - ('illegal' instruction)") } private fun iAlr() { - TODO() + TODO("alr=asr - ('illegal' instruction)") } private fun iAnc() { - TODO() + TODO("anc - ('illegal' instruction)") } private fun iArr() { - TODO() + TODO("arr - ('illegal' instruction)") } private fun iAxs() { - TODO() + TODO("axs - ('illegal' instruction)") } private fun iDcp() { - TODO() + TODO("dcp - ('illegal' instruction)") } private fun iIsc() { - TODO() + TODO("isc=isb - ('illegal' instruction)") } private fun iLas() { - TODO() + TODO("las=lar - ('illegal' instruction)") } private fun iLax() { - TODO() + TODO("lax - ('illegal' instruction)") } private fun iRla() { - TODO() + TODO("rla - ('illegal' instruction)") } private fun iRra() { - TODO() + TODO("rra - ('illegal' instruction)") } private fun iSax() { - TODO() + TODO("sax - ('illegal' instruction)") } private fun iShx() { - TODO() + TODO("shx - ('illegal' instruction)") } private fun iShy() { - TODO() + TODO("shy - ('illegal' instruction)") } private fun iSlo() { - TODO() + TODO("slo=aso - ('illegal' instruction)") } private fun iSre() { - TODO() + TODO("sre=lse - ('illegal' instruction)") } private fun iTas() { - TODO() + TODO("tas - ('illegal' instruction)") } private fun iXaa() { - TODO() + TODO("xaa - ('illegal' instruction)") } } diff --git a/sim65/src/components/Parallel.kt b/sim65/src/components/Parallel.kt index f2f5d5b7f..6b063b3a4 100644 --- a/sim65/src/components/Parallel.kt +++ b/sim65/src/components/Parallel.kt @@ -1,6 +1,6 @@ package sim65.components -import sim65.C64Screencodes +import sim65.Petscii /** * A parallel output device (basically, prints bytes as characters to the screen) @@ -17,19 +17,19 @@ class Parallel(startAddress: Address, endAddress: Address) : MemMappedComponent( override fun clock() {} override fun reset() {} - override fun read(address: Address): UByte { + override operator fun get(address: Address): UByte { return if (address == startAddress) dataByte else 0 } - override fun write(address: Address, data: UByte) { + override operator fun set(address: Address, data: UByte) { if (address == startAddress) dataByte = data else if (address == endAddress) { if ((data.toInt() and 1) == 1) { - val char = C64Screencodes.decodeScreencode(listOf(dataByte), false).first() + val char = Petscii.decodeScreencode(listOf(dataByte), false).first() println("PARALLEL WRITE: '$char'") } } diff --git a/sim65/src/components/Ram.kt b/sim65/src/components/Ram.kt index 8cd4c3eb5..15ce4ad94 100644 --- a/sim65/src/components/Ram.kt +++ b/sim65/src/components/Ram.kt @@ -5,15 +5,12 @@ import java.io.File class Ram(startAddress: Address, endAddress: Address): MemMappedComponent(startAddress, endAddress) { private val memory = ShortArray(endAddress-startAddress+1) - override fun read(address: Address): UByte = memory[address-startAddress] + override operator fun get(address: Address): UByte = memory[address-startAddress] - override fun write(address: Address, data: UByte) { + override operator fun set(address: Address, data: UByte) { memory[address-startAddress] = data } - operator fun get(address: Address) = read(address) - operator fun set(address: Address, data: UByte) = write(address, data) - override fun cloneMem(): Array = memory.toTypedArray() override fun clock() { } diff --git a/sim65/src/components/Rom.kt b/sim65/src/components/Rom.kt index 9eee82b94..54f271031 100644 --- a/sim65/src/components/Rom.kt +++ b/sim65/src/components/Rom.kt @@ -7,8 +7,8 @@ class Rom(startAddress: Address, endAddress: Address, data: Array): MemMa require(endAddress-startAddress+1 == data.size) { "rom address range doesn't match size of data bytes" } } - override fun read(address: Address): UByte = memory[address-startAddress] - override fun write(address: Address, data: UByte) { } + override operator fun get(address: Address): UByte = memory[address-startAddress] + override operator fun set(address: Address, data: UByte) { } override fun cloneMem(): Array = memory.toTypedArray() override fun clock() { } override fun reset() { } diff --git a/sim65/src/components/Timer.kt b/sim65/src/components/Timer.kt index 5cbf2a42f..044a44ed6 100644 --- a/sim65/src/components/Timer.kt +++ b/sim65/src/components/Timer.kt @@ -17,11 +17,11 @@ class Timer(startAddress: Address, endAddress: Address): MemMappedComponent(star cycle = 0 } - override fun read(address: Address): UByte { + override operator fun get(address: Address): UByte { TODO("not implemented") //To change body of created functions use File | Settings | File Templates. } - override fun write(address: Address, data: UByte) { + override operator fun set(address: Address, data: UByte) { TODO("not implemented") //To change body of created functions use File | Settings | File Templates. } diff --git a/sim65/test/Test6502CpuBasics.kt b/sim65/test/Test6502CpuBasics.kt index ef0f5bf76..21b8ff4c4 100644 --- a/sim65/test/Test6502CpuBasics.kt +++ b/sim65/test/Test6502CpuBasics.kt @@ -7,7 +7,7 @@ class Test6502CpuBasics { @Test fun testCpuFlagsAfterReset() { - val cpu = Cpu6502(true, true) + val cpu = Cpu6502(true) val bus = Bus() bus.add(cpu) cpu.reset() diff --git a/sim65/test/TestCommon6502.kt b/sim65/test/TestCommon6502.kt index 869cdb888..f8f6eaf19 100644 --- a/sim65/test/TestCommon6502.kt +++ b/sim65/test/TestCommon6502.kt @@ -45,7 +45,7 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. abstract class TestCommon6502 { // Tests common to 6502-based microprocessors - val mpu = Cpu6502(true, true) // TODO make a 65C02 cpu as well and let the subclasses testsuites define the appropriate instance + val mpu = Cpu6502(stopOnBrk = false) // TODO make a 65C02 cpu as well and let the subclasses testsuites define the appropriate instance val memory = Ram(0, 0xffff) val bus = Bus() @@ -53,8 +53,8 @@ abstract class TestCommon6502 { bus.add(mpu) bus.add(memory) memory.fill(0xaa) - memory.write(Cpu6502.RESET_vector, 0) - memory.write(Cpu6502.RESET_vector+1, 0) + memory[Cpu6502.RESET_vector] = 0 + memory[Cpu6502.RESET_vector + 1] = 0 mpu.reset() mpu.Status.I = false // allow interrupts again } @@ -74,7 +74,7 @@ abstract class TestCommon6502 { // test helpers fun writeMem(memory: MemMappedComponent, startAddress: Address, data: Iterable) { var addr = startAddress - data.forEach { memory.write(addr++, it) } + data.forEach { memory[addr++] = it } } @@ -91,6 +91,7 @@ abstract class TestCommon6502 { } // ADC Absolute + @Test fun test_adc_bcd_off_absolute_carry_clear_in_accumulator_zeroes() { mpu.A = 0 @@ -218,9 +219,9 @@ abstract class TestCommon6502 { } // ADC Zero Page + @Test fun test_adc_bcd_off_zp_carry_clear_in_accumulator_zeroes() { - mpu.A = 0 // $0000 ADC $00B0 writeMem(memory, 0x0000, listOf(0x65, 0xB0)) @@ -231,12 +232,10 @@ abstract class TestCommon6502 { assertFalse(mpu.Status.C) assertFalse(mpu.Status.N) assertTrue(mpu.Status.Z) - } @Test fun test_adc_bcd_off_zp_carry_set_in_accumulator_zero() { - mpu.A = 0 mpu.Status.C = true // $0000 ADC $00B0 @@ -248,12 +247,10 @@ abstract class TestCommon6502 { assertFalse(mpu.Status.N) assertFalse(mpu.Status.Z) assertFalse(mpu.Status.C) - } @Test fun test_adc_bcd_off_zp_carry_clear_in_no_carry_clear_out() { - mpu.A = 0x01 // $0000 ADC $00B0 writeMem(memory, 0x0000, listOf(0x65, 0xB0)) @@ -264,12 +261,10 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.N) assertFalse(mpu.Status.C) assertFalse(mpu.Status.Z) - } @Test fun test_adc_bcd_off_zp_carry_clear_in_carry_set_out() { - mpu.A = 0x02 // $0000 ADC $00B0 writeMem(memory, 0x0000, listOf(0x65, 0xB0)) @@ -280,12 +275,10 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.C) assertFalse(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_adc_bcd_off_zp_overflow_clr_no_carry_01_plus_01() { - mpu.Status.C = false mpu.A = 0x01 // $0000 ADC $00B0 @@ -295,12 +288,10 @@ abstract class TestCommon6502 { assertEquals(0x0002, mpu.PC) assertEquals(0x02, mpu.A) assertFalse(mpu.Status.V) - } @Test fun test_adc_bcd_off_zp_overflow_clr_no_carry_01_plus_ff() { - mpu.Status.C = false mpu.A = 0x01 // $0000 ADC $00B0 @@ -310,12 +301,10 @@ abstract class TestCommon6502 { assertEquals(0x0002, mpu.PC) assertEquals(0x00, mpu.A) assertFalse(mpu.Status.V) - } @Test fun test_adc_bcd_off_zp_overflow_set_no_carry_7f_plus_01() { - mpu.Status.C = false mpu.A = 0x7f // $0000 ADC $00B0 @@ -325,12 +314,10 @@ abstract class TestCommon6502 { assertEquals(0x0002, mpu.PC) assertEquals(0x80, mpu.A) assertTrue(mpu.Status.V) - } @Test fun test_adc_bcd_off_zp_overflow_set_no_carry_80_plus_ff() { - mpu.Status.C = false mpu.A = 0x80 // $0000 ADC $00B0 @@ -340,12 +327,10 @@ abstract class TestCommon6502 { assertEquals(0x0002, mpu.PC) assertEquals(0x7f, mpu.A) assertTrue(mpu.Status.V) - } @Test fun test_adc_bcd_off_zp_overflow_set_on_40_plus_40() { - mpu.A = 0x40 mpu.Status.V = false // $0000 ADC $00B0 @@ -357,14 +342,12 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.N) assertTrue(mpu.Status.V) assertFalse(mpu.Status.Z) - - // ADC Immediate - } + // ADC Immediate + @Test fun test_adc_bcd_off_immediate_carry_clear_in_accumulator_zeroes() { - mpu.A = 0 // $0000 ADC #$00 writeMem(memory, 0x0000, listOf(0x69, 0x00)) @@ -374,12 +357,10 @@ abstract class TestCommon6502 { assertFalse(mpu.Status.C) assertFalse(mpu.Status.N) assertTrue(mpu.Status.Z) - } @Test fun test_adc_bcd_off_immediate_carry_set_in_accumulator_zero() { - mpu.A = 0 mpu.Status.C = true // $0000 ADC #$00 @@ -390,12 +371,10 @@ abstract class TestCommon6502 { assertFalse(mpu.Status.N) assertFalse(mpu.Status.Z) assertFalse(mpu.Status.C) - } @Test fun test_adc_bcd_off_immediate_carry_clear_in_no_carry_clear_out() { - mpu.A = 0x01 // $0000 ADC #$FE writeMem(memory, 0x0000, listOf(0x69, 0xFE)) @@ -405,12 +384,10 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.N) assertFalse(mpu.Status.C) assertFalse(mpu.Status.Z) - } @Test fun test_adc_bcd_off_immediate_carry_clear_in_carry_set_out() { - mpu.A = 0x02 // $0000 ADC #$FF writeMem(memory, 0x0000, listOf(0x69, 0xFF)) @@ -420,12 +397,10 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.C) assertFalse(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_adc_bcd_off_immediate_overflow_clr_no_carry_01_plus_01() { - mpu.Status.C = false mpu.A = 0x01 // $0000 ADC #$01 @@ -434,12 +409,10 @@ abstract class TestCommon6502 { assertEquals(0x0002, mpu.PC) assertEquals(0x02, mpu.A) assertFalse(mpu.Status.V) - } @Test fun test_adc_bcd_off_immediate_overflow_clr_no_carry_01_plus_ff() { - mpu.Status.C = false mpu.A = 0x01 // $0000 ADC #$FF @@ -448,12 +421,10 @@ abstract class TestCommon6502 { assertEquals(0x0002, mpu.PC) assertEquals(0x00, mpu.A) assertFalse(mpu.Status.V) - } @Test fun test_adc_bcd_off_immediate_overflow_set_no_carry_7f_plus_01() { - mpu.Status.C = false mpu.A = 0x7f // $0000 ADC #$01 @@ -462,12 +433,10 @@ abstract class TestCommon6502 { assertEquals(0x0002, mpu.PC) assertEquals(0x80, mpu.A) assertTrue(mpu.Status.V) - } @Test fun test_adc_bcd_off_immediate_overflow_set_no_carry_80_plus_ff() { - mpu.Status.C = false mpu.A = 0x80 // $0000 ADC #$FF @@ -476,12 +445,10 @@ abstract class TestCommon6502 { assertEquals(0x0002, mpu.PC) assertEquals(0x7f, mpu.A) assertTrue(mpu.Status.V) - } @Test fun test_adc_bcd_off_immediate_overflow_set_on_40_plus_40() { - mpu.A = 0x40 // $0000 ADC #$40 writeMem(memory, 0x0000, listOf(0x69, 0x40)) @@ -491,12 +458,10 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.N) assertTrue(mpu.Status.V) assertFalse(mpu.Status.Z) - } @Test fun test_adc_bcd_on_immediate_79_plus_00_carry_set() { - mpu.Status.D = true mpu.Status.C = true mpu.A = 0x79 @@ -513,7 +478,6 @@ abstract class TestCommon6502 { @Test fun test_adc_bcd_on_immediate_6f_plus_00_carry_set() { - mpu.Status.D = true mpu.Status.C = true mpu.A = 0x6f @@ -526,12 +490,10 @@ abstract class TestCommon6502 { assertFalse(mpu.Status.V) assertFalse(mpu.Status.Z) assertFalse(mpu.Status.C) - } @Test fun test_adc_bcd_on_immediate_9c_plus_9d() { - mpu.Status.D = true mpu.Status.C = false mpu.Status.N = true @@ -556,7 +518,6 @@ abstract class TestCommon6502 { @Test fun test_adc_bcd_off_abs_x_carry_clear_in_accumulator_zeroes() { - mpu.A = 0x00 mpu.X = 0x03 // $0000 ADC $C000,X @@ -568,12 +529,10 @@ abstract class TestCommon6502 { assertFalse(mpu.Status.C) assertFalse(mpu.Status.N) assertTrue(mpu.Status.Z) - } @Test fun test_adc_bcd_off_abs_x_carry_set_in_accumulator_zero() { - mpu.A = 0 mpu.X = 0x03 mpu.Status.C = true @@ -586,12 +545,10 @@ abstract class TestCommon6502 { assertFalse(mpu.Status.N) assertFalse(mpu.Status.Z) assertFalse(mpu.Status.C) - } @Test fun test_adc_bcd_off_abs_x_carry_clear_in_no_carry_clear_out() { - mpu.A = 0x01 mpu.X = 0x03 // $0000 ADC $C000,X @@ -603,12 +560,10 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.N) assertFalse(mpu.Status.C) assertFalse(mpu.Status.Z) - } @Test fun test_adc_bcd_off_abs_x_carry_clear_in_carry_set_out() { - mpu.A = 0x02 mpu.X = 0x03 // $0000 ADC $C000,X @@ -620,12 +575,10 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.C) assertFalse(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_adc_bcd_off_abs_x_overflow_clr_no_carry_01_plus_01() { - mpu.Status.C = false mpu.A = 0x01 // $0000 ADC $C000,X @@ -635,12 +588,10 @@ abstract class TestCommon6502 { assertEquals(0x0003, mpu.PC) assertEquals(0x02, mpu.A) assertFalse(mpu.Status.V) - } @Test fun test_adc_bcd_off_abs_x_overflow_clr_no_carry_01_plus_ff() { - mpu.Status.C = false mpu.A = 0x01 // $0000 ADC $C000,X @@ -650,12 +601,10 @@ abstract class TestCommon6502 { assertEquals(0x0003, mpu.PC) assertEquals(0x00, mpu.A) assertFalse(mpu.Status.V) - } @Test fun test_adc_bcd_off_abs_x_overflow_set_no_carry_7f_plus_01() { - mpu.Status.C = false mpu.A = 0x7f // $0000 ADC $C000,X @@ -665,12 +614,10 @@ abstract class TestCommon6502 { assertEquals(0x0003, mpu.PC) assertEquals(0x80, mpu.A) assertTrue(mpu.Status.V) - } @Test fun test_adc_bcd_off_abs_x_overflow_set_no_carry_80_plus_ff() { - mpu.Status.C = false mpu.A = 0x80 // $0000 ADC $C000,X @@ -680,12 +627,10 @@ abstract class TestCommon6502 { assertEquals(0x0003, mpu.PC) assertEquals(0x7f, mpu.A) assertTrue(mpu.Status.V) - } @Test fun test_adc_bcd_off_abs_x_overflow_set_on_40_plus_40() { - mpu.Status.V = false mpu.A = 0x40 mpu.X = 0x03 @@ -698,14 +643,12 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.N) assertTrue(mpu.Status.V) assertFalse(mpu.Status.Z) - - // ADC Absolute, Y-Indexed - } + // ADC Absolute, Y-Indexed + @Test fun test_adc_bcd_off_abs_y_carry_clear_in_accumulator_zeroes() { - mpu.A = 0x00 mpu.Y = 0x03 // $0000 ADC $C000,Y @@ -717,12 +660,10 @@ abstract class TestCommon6502 { assertFalse(mpu.Status.C) assertFalse(mpu.Status.N) assertTrue(mpu.Status.Z) - } @Test fun test_adc_bcd_off_abs_y_carry_set_in_accumulator_zero() { - mpu.A = 0 mpu.Y = 0x03 mpu.Status.C = true @@ -735,12 +676,10 @@ abstract class TestCommon6502 { assertFalse(mpu.Status.N) assertFalse(mpu.Status.Z) assertFalse(mpu.Status.C) - } @Test fun test_adc_bcd_off_abs_y_carry_clear_in_no_carry_clear_out() { - mpu.A = 0x01 mpu.Y = 0x03 // $0000 ADC $C000,Y @@ -752,12 +691,10 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.N) assertFalse(mpu.Status.C) assertFalse(mpu.Status.Z) - } @Test fun test_adc_bcd_off_abs_y_carry_clear_in_carry_set_out() { - mpu.A = 0x02 mpu.Y = 0x03 // $0000 ADC $C000,Y @@ -769,12 +706,10 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.C) assertFalse(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_adc_bcd_off_abs_y_overflow_clr_no_carry_01_plus_01() { - mpu.Status.C = false mpu.A = 0x01 // $0000 ADC $C000,Y @@ -784,12 +719,10 @@ abstract class TestCommon6502 { assertEquals(0x0003, mpu.PC) assertEquals(0x02, mpu.A) assertFalse(mpu.Status.V) - } @Test fun test_adc_bcd_off_abs_y_overflow_clr_no_carry_01_plus_ff() { - mpu.Status.C = false mpu.A = 0x01 // $0000 ADC $C000,Y @@ -799,12 +732,10 @@ abstract class TestCommon6502 { assertEquals(0x0003, mpu.PC) assertEquals(0x00, mpu.A) assertFalse(mpu.Status.V) - } @Test fun test_adc_bcd_off_abs_y_overflow_set_no_carry_7f_plus_01() { - mpu.Status.C = false mpu.A = 0x7f // $0000 ADC $C000,Y @@ -814,12 +745,10 @@ abstract class TestCommon6502 { assertEquals(0x0003, mpu.PC) assertEquals(0x80, mpu.A) assertTrue(mpu.Status.V) - } @Test fun test_adc_bcd_off_abs_y_overflow_set_no_carry_80_plus_ff() { - mpu.Status.C = false mpu.A = 0x80 // $0000 ADC $C000,Y @@ -829,12 +758,10 @@ abstract class TestCommon6502 { assertEquals(0x0003, mpu.PC) assertEquals(0x7f, mpu.A) assertTrue(mpu.Status.V) - } @Test fun test_adc_bcd_off_abs_y_overflow_set_on_40_plus_40() { - mpu.Status.V = false mpu.A = 0x40 mpu.Y = 0x03 @@ -847,14 +774,12 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.N) assertTrue(mpu.Status.V) assertFalse(mpu.Status.Z) - - // ADC Zero Page, X-Indexed - } + // ADC Zero Page, X-Indexed + @Test fun test_adc_bcd_off_zp_x_carry_clear_in_accumulator_zeroes() { - mpu.A = 0x00 mpu.X = 0x03 // $0000 ADC $0010,X @@ -866,12 +791,10 @@ abstract class TestCommon6502 { assertFalse(mpu.Status.C) assertFalse(mpu.Status.N) assertTrue(mpu.Status.Z) - } @Test fun test_adc_bcd_off_zp_x_carry_set_in_accumulator_zero() { - mpu.A = 0 mpu.X = 0x03 mpu.Status.C = true @@ -884,12 +807,10 @@ abstract class TestCommon6502 { assertFalse(mpu.Status.N) assertFalse(mpu.Status.Z) assertFalse(mpu.Status.C) - } @Test fun test_adc_bcd_off_zp_x_carry_clear_in_no_carry_clear_out() { - mpu.A = 0x01 mpu.X = 0x03 // $0000 ADC $0010,X @@ -901,12 +822,10 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.N) assertFalse(mpu.Status.C) assertFalse(mpu.Status.Z) - } @Test fun test_adc_bcd_off_zp_x_carry_clear_in_carry_set_out() { - mpu.A = 0x02 mpu.X = 0x03 // $0000 ADC $0010,X @@ -918,12 +837,10 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.C) assertFalse(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_adc_bcd_off_zp_x_overflow_clr_no_carry_01_plus_01() { - mpu.Status.C = false mpu.A = 0x01 mpu.X = 0x03 @@ -934,12 +851,10 @@ abstract class TestCommon6502 { assertEquals(0x0002, mpu.PC) assertEquals(0x02, mpu.A) assertFalse(mpu.Status.V) - } @Test fun test_adc_bcd_off_zp_x_overflow_clr_no_carry_01_plus_ff() { - mpu.Status.C = false mpu.A = 0x01 mpu.X = 0x03 @@ -950,12 +865,10 @@ abstract class TestCommon6502 { assertEquals(0x0002, mpu.PC) assertEquals(0x00, mpu.A) assertFalse(mpu.Status.V) - } @Test fun test_adc_bcd_off_zp_x_overflow_set_no_carry_7f_plus_01() { - mpu.Status.C = false mpu.A = 0x7f mpu.X = 0x03 @@ -966,7 +879,6 @@ abstract class TestCommon6502 { assertEquals(0x0002, mpu.PC) assertEquals(0x80, mpu.A) assertTrue(mpu.Status.V) - } @Test @@ -982,12 +894,10 @@ abstract class TestCommon6502 { assertEquals(0x0002, mpu.PC) assertEquals(0x7f, mpu.A) assertTrue(mpu.Status.V) - } @Test fun test_adc_bcd_off_zp_x_overflow_set_on_40_plus_40() { - mpu.Status.V = false mpu.A = 0x40 mpu.X = 0x03 @@ -1000,14 +910,12 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.N) assertTrue(mpu.Status.V) assertFalse(mpu.Status.Z) - - // ADC Indirect, Indexed (X) - } + // ADC Indirect, Indexed (X) + @Test fun test_adc_bcd_off_ind_indexed_carry_clear_in_accumulator_zeroes() { - mpu.A = 0x00 mpu.X = 0x03 // $0000 ADC ($0010,X) @@ -1021,12 +929,10 @@ abstract class TestCommon6502 { assertFalse(mpu.Status.C) assertFalse(mpu.Status.N) assertTrue(mpu.Status.Z) - } @Test fun test_adc_bcd_off_ind_indexed_carry_set_in_accumulator_zero() { - mpu.A = 0 mpu.X = 0x03 mpu.Status.C = true @@ -1041,12 +947,10 @@ abstract class TestCommon6502 { assertFalse(mpu.Status.N) assertFalse(mpu.Status.Z) assertFalse(mpu.Status.C) - } @Test fun test_adc_bcd_off_ind_indexed_carry_clear_in_no_carry_clear_out() { - mpu.A = 0x01 mpu.X = 0x03 // $0000 ADC ($0010,X) @@ -1060,12 +964,10 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.N) assertFalse(mpu.Status.C) assertFalse(mpu.Status.Z) - } @Test fun test_adc_bcd_off_ind_indexed_carry_clear_in_carry_set_out() { - mpu.A = 0x02 mpu.X = 0x03 // $0000 ADC ($0010,X) @@ -1079,12 +981,10 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.C) assertFalse(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_adc_bcd_off_ind_indexed_overflow_clr_no_carry_01_plus_01() { - mpu.Status.C = false mpu.A = 0x01 mpu.X = 0x03 @@ -1097,12 +997,10 @@ abstract class TestCommon6502 { assertEquals(0x0002, mpu.PC) assertEquals(0x02, mpu.A) assertFalse(mpu.Status.V) - } @Test fun test_adc_bcd_off_ind_indexed_overflow_clr_no_carry_01_plus_ff() { - mpu.Status.C = false mpu.A = 0x01 mpu.X = 0x03 @@ -1115,12 +1013,10 @@ abstract class TestCommon6502 { assertEquals(0x0002, mpu.PC) assertEquals(0x00, mpu.A) assertFalse(mpu.Status.V) - } @Test fun test_adc_bcd_off_ind_indexed_overflow_set_no_carry_7f_plus_01() { - mpu.Status.C = false mpu.A = 0x7f mpu.X = 0x03 @@ -1133,12 +1029,10 @@ abstract class TestCommon6502 { assertEquals(0x0002, mpu.PC) assertEquals(0x80, mpu.A) assertTrue(mpu.Status.V) - } @Test fun test_adc_bcd_off_ind_indexed_overflow_set_no_carry_80_plus_ff() { - mpu.Status.C = false mpu.A = 0x80 mpu.X = 0x03 @@ -1151,12 +1045,10 @@ abstract class TestCommon6502 { assertEquals(0x0002, mpu.PC) assertEquals(0x7f, mpu.A) assertTrue(mpu.Status.V) - } @Test fun test_adc_bcd_off_ind_indexed_overflow_set_on_40_plus_40() { - mpu.Status.V = false mpu.A = 0x40 mpu.X = 0x03 @@ -1171,14 +1063,12 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.N) assertTrue(mpu.Status.V) assertFalse(mpu.Status.Z) - - // ADC Indexed, Indirect (Y) - } + // ADC Indexed, Indirect (Y) + @Test fun test_adc_bcd_off_indexed_ind_carry_clear_in_accumulator_zeroes() { - mpu.A = 0x00 mpu.Y = 0x03 // $0000 ADC ($0010),Y @@ -1192,12 +1082,10 @@ abstract class TestCommon6502 { assertFalse(mpu.Status.C) assertFalse(mpu.Status.N) assertTrue(mpu.Status.Z) - } @Test fun test_adc_bcd_off_indexed_ind_carry_set_in_accumulator_zero() { - mpu.A = 0 mpu.Y = 0x03 mpu.Status.C = true @@ -1212,12 +1100,10 @@ abstract class TestCommon6502 { assertFalse(mpu.Status.N) assertFalse(mpu.Status.Z) assertFalse(mpu.Status.C) - } @Test fun test_adc_bcd_off_indexed_ind_carry_clear_in_no_carry_clear_out() { - mpu.A = 0x01 mpu.Y = 0x03 // $0000 ADC ($0010),Y @@ -1231,12 +1117,10 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.N) assertFalse(mpu.Status.C) assertFalse(mpu.Status.Z) - } @Test fun test_adc_bcd_off_indexed_ind_carry_clear_in_carry_set_out() { - mpu.A = 0x02 mpu.Y = 0x03 // $0000 ADC ($0010),Y @@ -1250,12 +1134,10 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.C) assertFalse(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_adc_bcd_off_indexed_ind_overflow_clr_no_carry_01_plus_01() { - mpu.Status.C = false mpu.A = 0x01 mpu.Y = 0x03 @@ -1268,12 +1150,10 @@ abstract class TestCommon6502 { assertEquals(0x0002, mpu.PC) assertEquals(0x02, mpu.A) assertFalse(mpu.Status.V) - } @Test fun test_adc_bcd_off_indexed_ind_overflow_clr_no_carry_01_plus_ff() { - mpu.Status.C = false mpu.A = 0x01 mpu.Y = 0x03 @@ -1286,12 +1166,10 @@ abstract class TestCommon6502 { assertEquals(0x0002, mpu.PC) assertEquals(0x00, mpu.A) assertFalse(mpu.Status.V) - } @Test fun test_adc_bcd_off_indexed_ind_overflow_set_no_carry_7f_plus_01() { - mpu.Status.C = false mpu.A = 0x7f mpu.Y = 0x03 @@ -1304,12 +1182,10 @@ abstract class TestCommon6502 { assertEquals(0x0002, mpu.PC) assertEquals(0x80, mpu.A) assertTrue(mpu.Status.V) - } @Test fun test_adc_bcd_off_indexed_ind_overflow_set_no_carry_80_plus_ff() { - mpu.Status.C = false mpu.A = 0x80 mpu.Y = 0x03 @@ -1322,12 +1198,10 @@ abstract class TestCommon6502 { assertEquals(0x0002, mpu.PC) assertEquals(0x7f, mpu.A) assertTrue(mpu.Status.V) - } @Test fun test_adc_bcd_off_indexed_ind_overflow_set_on_40_plus_40() { - mpu.Status.V = false mpu.A = 0x40 mpu.Y = 0x03 @@ -1348,7 +1222,6 @@ abstract class TestCommon6502 { @Test fun test_and_absolute_all_zeros_setting_zero_flag() { - mpu.A = 0xFF // $0000 AND $ABCD writeMem(memory, 0x0000, listOf(0x2D, 0xCD, 0xAB)) @@ -1358,12 +1231,10 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.A) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_and_absolute_zeros_and_ones_setting_negative_flag() { - mpu.A = 0xFF // $0000 AND $ABCD writeMem(memory, 0x0000, listOf(0x2D, 0xCD, 0xAB)) @@ -1379,7 +1250,6 @@ abstract class TestCommon6502 { @Test fun test_and_zp_all_zeros_setting_zero_flag() { - mpu.A = 0xFF // $0000 AND $0010 writeMem(memory, 0x0000, listOf(0x25, 0x10)) @@ -1389,12 +1259,10 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.A) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_and_zp_zeros_and_ones_setting_negative_flag() { - mpu.A = 0xFF // $0000 AND $0010 writeMem(memory, 0x0000, listOf(0x25, 0x10)) @@ -1404,14 +1272,12 @@ abstract class TestCommon6502 { assertEquals(0xAA, mpu.A) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - - // AND (Immediate) - } + // AND (Immediate) + @Test fun test_and_immediate_all_zeros_setting_zero_flag() { - mpu.A = 0xFF // $0000 AND #$00 writeMem(memory, 0x0000, listOf(0x29, 0x00)) @@ -1420,12 +1286,10 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.A) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_and_immediate_zeros_and_ones_setting_negative_flag() { - mpu.A = 0xFF // $0000 AND #$AA writeMem(memory, 0x0000, listOf(0x29, 0xAA)) @@ -1434,14 +1298,12 @@ abstract class TestCommon6502 { assertEquals(0xAA, mpu.A) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - - // AND (Absolute, X-Indexed) - } + // AND (Absolute, X-Indexed) + @Test fun test_and_abs_x_all_zeros_setting_zero_flag() { - mpu.A = 0xFF mpu.X = 0x03 // $0000 AND $ABCD,X @@ -1452,12 +1314,10 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.A) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_and_abs_x_zeros_and_ones_setting_negative_flag() { - mpu.A = 0xFF mpu.X = 0x03 // $0000 AND $ABCD,X @@ -1468,14 +1328,12 @@ abstract class TestCommon6502 { assertEquals(0xAA, mpu.A) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - - // AND (Absolute, Y-Indexed) - } + // AND (Absolute, Y-Indexed) + @Test fun test_and_abs_y_all_zeros_setting_zero_flag() { - mpu.A = 0xFF mpu.Y = 0x03 // $0000 AND $ABCD,X @@ -1486,7 +1344,6 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.A) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test @@ -1507,7 +1364,6 @@ abstract class TestCommon6502 { @Test fun test_and_ind_indexed_x_all_zeros_setting_zero_flag() { - mpu.A = 0xFF mpu.X = 0x03 // $0000 AND ($0010,X) @@ -1520,12 +1376,10 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.A) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_and_ind_indexed_x_zeros_and_ones_setting_negative_flag() { - mpu.A = 0xFF mpu.X = 0x03 // $0000 AND ($0010,X) @@ -1538,14 +1392,12 @@ abstract class TestCommon6502 { assertEquals(0xAA, mpu.A) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - - // AND Indexed, Indirect (Y) - } + // AND Indexed, Indirect (Y) + @Test fun test_and_indexed_ind_y_all_zeros_setting_zero_flag() { - mpu.A = 0xFF mpu.Y = 0x03 // $0000 AND ($0010),Y @@ -1558,12 +1410,10 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.A) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_and_indexed_ind_y_zeros_and_ones_setting_negative_flag() { - mpu.A = 0xFF mpu.Y = 0x03 // $0000 AND ($0010),Y @@ -1576,14 +1426,12 @@ abstract class TestCommon6502 { assertEquals(0xAA, mpu.A) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - - // AND Zero Page, X-Indexed - } + // AND Zero Page, X-Indexed + @Test fun test_and_zp_x_all_zeros_setting_zero_flag() { - mpu.A = 0xFF mpu.X = 0x03 // $0000 AND $0010,X @@ -1594,12 +1442,10 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.A) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_and_zp_x_all_zeros_and_ones_setting_negative_flag() { - mpu.A = 0xFF mpu.X = 0x03 // $0000 AND $0010,X @@ -1610,14 +1456,12 @@ abstract class TestCommon6502 { assertEquals(0xAA, mpu.A) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - - // ASL Accumulator - } + // ASL Accumulator + @Test fun test_asl_accumulator_sets_z_flag() { - mpu.A = 0x00 // $0000 ASL A memory[0x0000] = 0x0A @@ -1626,12 +1470,10 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.A) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_asl_accumulator_sets_n_flag() { - mpu.A = 0x40 // $0000 ASL A memory[0x0000] = 0x0A @@ -1640,12 +1482,10 @@ abstract class TestCommon6502 { assertEquals(0x80, mpu.A) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_asl_accumulator_shifts_out_zero() { - mpu.A = 0x7F // $0000 ASL A memory[0x0000] = 0x0A @@ -1653,12 +1493,10 @@ abstract class TestCommon6502 { assertEquals(0x0001, mpu.PC) assertEquals(0xFE, mpu.A) assertFalse(mpu.Status.C) - } @Test fun test_asl_accumulator_shifts_out_one() { - mpu.A = 0xFF // $0000 ASL A memory[0x0000] = 0x0A @@ -1666,12 +1504,10 @@ abstract class TestCommon6502 { assertEquals(0x0001, mpu.PC) assertEquals(0xFE, mpu.A) assertTrue(mpu.Status.C) - } @Test fun test_asl_accumulator_80_sets_z_flag() { - mpu.A = 0x80 mpu.Status.Z = false // $0000 ASL A @@ -1680,14 +1516,12 @@ abstract class TestCommon6502 { assertEquals(0x0001, mpu.PC) assertEquals(0x00, mpu.A) assertTrue(mpu.Status.Z) - - // ASL Absolute - } + // ASL Absolute + @Test fun test_asl_absolute_sets_z_flag() { - // $0000 ASL $ABCD writeMem(memory, 0x0000, listOf(0x0E, 0xCD, 0xAB)) memory[0xABCD] = 0x00 @@ -1696,12 +1530,10 @@ abstract class TestCommon6502 { assertEquals(0x00, memory[0xABCD]) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_asl_absolute_sets_n_flag() { - // $0000 ASL $ABCD writeMem(memory, 0x0000, listOf(0x0E, 0xCD, 0xAB)) memory[0xABCD] = 0x40 @@ -1710,12 +1542,10 @@ abstract class TestCommon6502 { assertEquals(0x80, memory[0xABCD]) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_asl_absolute_shifts_out_zero() { - mpu.A = 0xAA // $0000 ASL $ABCD writeMem(memory, 0x0000, listOf(0x0E, 0xCD, 0xAB)) @@ -1725,12 +1555,10 @@ abstract class TestCommon6502 { assertEquals(0xAA, mpu.A) assertEquals(0xFE, memory[0xABCD]) assertFalse(mpu.Status.C) - } @Test fun test_asl_absolute_shifts_out_one() { - mpu.A = 0xAA // $0000 ASL $ABCD writeMem(memory, 0x0000, listOf(0x0E, 0xCD, 0xAB)) @@ -1740,14 +1568,12 @@ abstract class TestCommon6502 { assertEquals(0xAA, mpu.A) assertEquals(0xFE, memory[0xABCD]) assertTrue(mpu.Status.C) - - // ASL Zero Page - } + // ASL Zero Page + @Test fun test_asl_zp_sets_z_flag() { - // $0000 ASL $0010 writeMem(memory, 0x0000, listOf(0x06, 0x10)) memory[0x0010] = 0x00 @@ -1756,12 +1582,10 @@ abstract class TestCommon6502 { assertEquals(0x00, memory[0x0010]) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_asl_zp_sets_n_flag() { - // $0000 ASL $0010 writeMem(memory, 0x0000, listOf(0x06, 0x10)) memory[0x0010] = 0x40 @@ -1770,12 +1594,10 @@ abstract class TestCommon6502 { assertEquals(0x80, memory[0x0010]) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_asl_zp_shifts_out_zero() { - mpu.A = 0xAA // $0000 ASL $0010 writeMem(memory, 0x0000, listOf(0x06, 0x10)) @@ -1785,12 +1607,10 @@ abstract class TestCommon6502 { assertEquals(0xAA, mpu.A) assertEquals(0xFE, memory[0x0010]) assertFalse(mpu.Status.C) - } @Test fun test_asl_zp_shifts_out_one() { - mpu.A = 0xAA // $0000 ASL $0010 writeMem(memory, 0x0000, listOf(0x06, 0x10)) @@ -1800,14 +1620,12 @@ abstract class TestCommon6502 { assertEquals(0xAA, mpu.A) assertEquals(0xFE, memory[0x0010]) assertTrue(mpu.Status.C) - - // ASL Absolute, X-Indexed - } + // ASL Absolute, X-Indexed + @Test fun test_asl_abs_x_indexed_sets_z_flag() { - mpu.X = 0x03 // $0000 ASL $ABCD,X writeMem(memory, 0x0000, listOf(0x1E, 0xCD, 0xAB)) @@ -1817,12 +1635,10 @@ abstract class TestCommon6502 { assertEquals(0x00, memory[0xABCD + mpu.X]) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_asl_abs_x_indexed_sets_n_flag() { - mpu.X = 0x03 // $0000 ASL $ABCD,X writeMem(memory, 0x0000, listOf(0x1E, 0xCD, 0xAB)) @@ -1832,12 +1648,10 @@ abstract class TestCommon6502 { assertEquals(0x80, memory[0xABCD + mpu.X]) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_asl_abs_x_indexed_shifts_out_zero() { - mpu.A = 0xAA mpu.X = 0x03 // $0000 ASL $ABCD,X @@ -1848,12 +1662,10 @@ abstract class TestCommon6502 { assertEquals(0xAA, mpu.A) assertEquals(0xFE, memory[0xABCD + mpu.X]) assertFalse(mpu.Status.C) - } @Test fun test_asl_abs_x_indexed_shifts_out_one() { - mpu.A = 0xAA mpu.X = 0x03 // $0000 ASL $ABCD,X @@ -1864,14 +1676,12 @@ abstract class TestCommon6502 { assertEquals(0xAA, mpu.A) assertEquals(0xFE, memory[0xABCD + mpu.X]) assertTrue(mpu.Status.C) - - // ASL Zero Page, X-Indexed - } + // ASL Zero Page, X-Indexed + @Test fun test_asl_zp_x_indexed_sets_z_flag() { - mpu.X = 0x03 // $0000 ASL $0010,X writeMem(memory, 0x0000, listOf(0x16, 0x10)) @@ -1881,12 +1691,10 @@ abstract class TestCommon6502 { assertEquals(0x00, memory[0x0010 + mpu.X]) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_asl_zp_x_indexed_sets_n_flag() { - mpu.X = 0x03 // $0000 ASL $0010,X writeMem(memory, 0x0000, listOf(0x16, 0x10)) @@ -1896,12 +1704,10 @@ abstract class TestCommon6502 { assertEquals(0x80, memory[0x0010 + mpu.X]) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_asl_zp_x_indexed_shifts_out_zero() { - mpu.X = 0x03 mpu.A = 0xAA // $0000 ASL $0010,X @@ -1912,12 +1718,10 @@ abstract class TestCommon6502 { assertEquals(0xAA, mpu.A) assertEquals(0xFE, memory[0x0010 + mpu.X]) assertFalse(mpu.Status.C) - } @Test fun test_asl_zp_x_indexed_shifts_out_one() { - mpu.X = 0x03 mpu.A = 0xAA // $0000 ASL $0010,X @@ -1928,25 +1732,21 @@ abstract class TestCommon6502 { assertEquals(0xAA, mpu.A) assertEquals(0xFE, memory[0x0010 + mpu.X]) assertTrue(mpu.Status.C) - - // BCC - } + // BCC + @Test fun test_bcc_carry_clear_branches_relative_forward() { - mpu.Status.C = false // $0000 BCC +6 writeMem(memory, 0x0000, listOf(0x90, 0x06)) mpu.step() assertEquals(0x0002 + 0x06, mpu.PC) - } @Test fun test_bcc_carry_clear_branches_relative_backward() { - mpu.Status.C = false mpu.PC = 0x0050 val rel = 256 + (-6) // two's complement of 6 @@ -1954,36 +1754,30 @@ abstract class TestCommon6502 { writeMem(memory, 0x0050, listOf(0x90, rel.toShort())) mpu.step() assertEquals(0x0052 - 6, mpu.PC) - } @Test fun test_bcc_carry_set_does_not_branch() { - mpu.Status.C = true // $0000 BCC +6 writeMem(memory, 0x0000, listOf(0x90, 0x06)) mpu.step() assertEquals(0x0002, mpu.PC) - - // BCS - } + // BCS + @Test fun test_bcs_carry_set_branches_relative_forward() { - mpu.Status.C = true // $0000 BCS +6 writeMem(memory, 0x0000, listOf(0xB0, 0x06)) mpu.step() assertEquals(0x0002 + 0x06, mpu.PC) - } @Test fun test_bcs_carry_set_branches_relative_backward() { - mpu.Status.C = true mpu.PC = 0x0050 val rel = 256 + (-6) // two's complement of 6 @@ -1991,36 +1785,30 @@ abstract class TestCommon6502 { writeMem(memory, 0x0050, listOf(0xB0, rel.toShort())) mpu.step() assertEquals(0x0052 - 6, mpu.PC) - } @Test fun test_bcs_carry_clear_does_not_branch() { - mpu.Status.C = false // $0000 BCS +6 writeMem(memory, 0x0000, listOf(0xB0, 0x06)) mpu.step() assertEquals(0x0002, mpu.PC) - - // BEQ - } + // BEQ + @Test fun test_beq_zero_set_branches_relative_forward() { - mpu.Status.Z = true // $0000 BEQ +6 writeMem(memory, 0x0000, listOf(0xF0, 0x06)) mpu.step() assertEquals(0x0002 + 0x06, mpu.PC) - } @Test fun test_beq_zero_set_branches_relative_backward() { - mpu.Status.Z = true mpu.PC = 0x0050 val rel = 256 + (-6) // two's complement of 6 @@ -2028,25 +1816,21 @@ abstract class TestCommon6502 { writeMem(memory, 0x0050, listOf(0xF0, rel.toShort())) mpu.step() assertEquals(0x0052 - 6, mpu.PC) - } @Test fun test_beq_zero_clear_does_not_branch() { - mpu.Status.Z = false // $0000 BEQ +6 writeMem(memory, 0x0000, listOf(0xF0, 0x06)) mpu.step() assertEquals(0x0002, mpu.PC) - - // BIT (Absolute) - } + // BIT (Absolute) + @Test fun test_bit_abs_copies_bit_7_of_memory_to_n_flag_when_0() { - mpu.Status.N = false // $0000 BIT $FEED writeMem(memory, 0x0000, listOf(0x2C, 0xED, 0xFE)) @@ -2054,12 +1838,10 @@ abstract class TestCommon6502 { mpu.A = 0xFF mpu.step() assertTrue(mpu.Status.N) - } @Test fun test_bit_abs_copies_bit_7_of_memory_to_n_flag_when_1() { - mpu.Status.N = true // $0000 BIT $FEED writeMem(memory, 0x0000, listOf(0x2C, 0xED, 0xFE)) @@ -2067,12 +1849,10 @@ abstract class TestCommon6502 { mpu.A = 0xFF mpu.step() assertFalse(mpu.Status.N) - } @Test fun test_bit_abs_copies_bit_6_of_memory_to_v_flag_when_0() { - mpu.Status.V = false // $0000 BIT $FEED writeMem(memory, 0x0000, listOf(0x2C, 0xED, 0xFE)) @@ -2080,12 +1860,10 @@ abstract class TestCommon6502 { mpu.A = 0xFF mpu.step() assertTrue(mpu.Status.V) - } @Test fun test_bit_abs_copies_bit_6_of_memory_to_v_flag_when_1() { - mpu.Status.V = true // $0000 BIT $FEED writeMem(memory, 0x0000, listOf(0x2C, 0xED, 0xFE)) @@ -2093,12 +1871,10 @@ abstract class TestCommon6502 { mpu.A = 0xFF mpu.step() assertFalse(mpu.Status.V) - } @Test fun test_bit_abs_stores_result_of_and_in_z_preserves_a_when_1() { - mpu.Status.Z = false // $0000 BIT $FEED writeMem(memory, 0x0000, listOf(0x2C, 0xED, 0xFE)) @@ -2108,12 +1884,10 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.Z) assertEquals(0x01, mpu.A) assertEquals(0x00, memory[0xFEED]) - } @Test fun test_bit_abs_stores_result_of_and_when_nonzero_in_z_preserves_a() { - mpu.Status.Z = true // $0000 BIT $FEED writeMem(memory, 0x0000, listOf(0x2C, 0xED, 0xFE)) @@ -2123,12 +1897,10 @@ abstract class TestCommon6502 { assertFalse(mpu.Status.Z) // result of AND is non-zero assertEquals(0x01, mpu.A) assertEquals(0x01, memory[0xFEED]) - } @Test fun test_bit_abs_stores_result_of_and_when_zero_in_z_preserves_a() { - mpu.Status.Z = false // $0000 BIT $FEED writeMem(memory, 0x0000, listOf(0x2C, 0xED, 0xFE)) @@ -2138,14 +1910,12 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.Z) // result of AND is zero assertEquals(0x01, mpu.A) assertEquals(0x00, memory[0xFEED]) - - // BIT (Zero Page) - } + // BIT (Zero Page) + @Test fun test_bit_zp_copies_bit_7_of_memory_to_n_flag_when_0() { - mpu.Status.N = false // $0000 BIT $0010 writeMem(memory, 0x0000, listOf(0x24, 0x10)) @@ -2153,14 +1923,12 @@ abstract class TestCommon6502 { mpu.A = 0xFF mpu.step() assertEquals(0x0002, mpu.PC) - assertEquals(3+Cpu6502.resetCycles, mpu.totalCycles) + assertEquals(3 + Cpu6502.resetCycles, mpu.totalCycles) assertTrue(mpu.Status.N) - } @Test fun test_bit_zp_copies_bit_7_of_memory_to_n_flag_when_1() { - mpu.Status.N = true // $0000 BIT $0010 writeMem(memory, 0x0000, listOf(0x24, 0x10)) @@ -2168,14 +1936,12 @@ abstract class TestCommon6502 { mpu.A = 0xFF mpu.step() assertEquals(0x0002, mpu.PC) - assertEquals(3+Cpu6502.resetCycles, mpu.totalCycles) + assertEquals(3 + Cpu6502.resetCycles, mpu.totalCycles) assertFalse(mpu.Status.N) - } @Test fun test_bit_zp_copies_bit_6_of_memory_to_v_flag_when_0() { - mpu.Status.V = false // $0000 BIT $0010 writeMem(memory, 0x0000, listOf(0x24, 0x10)) @@ -2183,14 +1949,12 @@ abstract class TestCommon6502 { mpu.A = 0xFF mpu.step() assertEquals(0x0002, mpu.PC) - assertEquals(3+Cpu6502.resetCycles, mpu.totalCycles) + assertEquals(3 + Cpu6502.resetCycles, mpu.totalCycles) assertTrue(mpu.Status.V) - } @Test fun test_bit_zp_copies_bit_6_of_memory_to_v_flag_when_1() { - mpu.Status.V = true // $0000 BIT $0010 writeMem(memory, 0x0000, listOf(0x24, 0x10)) @@ -2198,14 +1962,12 @@ abstract class TestCommon6502 { mpu.A = 0xFF mpu.step() assertEquals(0x0002, mpu.PC) - assertEquals(3+Cpu6502.resetCycles, mpu.totalCycles) + assertEquals(3 + Cpu6502.resetCycles, mpu.totalCycles) assertFalse(mpu.Status.V) - } @Test fun test_bit_zp_stores_result_of_and_in_z_preserves_a_when_1() { - mpu.Status.Z = false // $0000 BIT $0010 writeMem(memory, 0x0000, listOf(0x24, 0x10)) @@ -2213,16 +1975,14 @@ abstract class TestCommon6502 { mpu.A = 0x01 mpu.step() assertEquals(0x0002, mpu.PC) - assertEquals(3+Cpu6502.resetCycles, mpu.totalCycles) + assertEquals(3 + Cpu6502.resetCycles, mpu.totalCycles) assertTrue(mpu.Status.Z) assertEquals(0x01, mpu.A) assertEquals(0x00, memory[0x0010]) - } @Test fun test_bit_zp_stores_result_of_and_when_nonzero_in_z_preserves_a() { - mpu.Status.Z = true // $0000 BIT $0010 writeMem(memory, 0x0000, listOf(0x24, 0x10)) @@ -2230,16 +1990,14 @@ abstract class TestCommon6502 { mpu.A = 0x01 mpu.step() assertEquals(0x0002, mpu.PC) - assertEquals(3+Cpu6502.resetCycles, mpu.totalCycles) + assertEquals(3 + Cpu6502.resetCycles, mpu.totalCycles) assertFalse(mpu.Status.Z) // result of AND is non-zero assertEquals(0x01, mpu.A) assertEquals(0x01, memory[0x0010]) - } @Test fun test_bit_zp_stores_result_of_and_when_zero_in_z_preserves_a() { - mpu.Status.Z = false // $0000 BIT $0010 writeMem(memory, 0x0000, listOf(0x24, 0x10)) @@ -2247,29 +2005,25 @@ abstract class TestCommon6502 { mpu.A = 0x01 mpu.step() assertEquals(0x0002, mpu.PC) - assertEquals(3+Cpu6502.resetCycles, mpu.totalCycles) + assertEquals(3 + Cpu6502.resetCycles, mpu.totalCycles) assertTrue(mpu.Status.Z) // result of AND is zero assertEquals(0x01, mpu.A) assertEquals(0x00, memory[0x0010]) - - // BMI - } + // BMI + @Test fun test_bmi_negative_set_branches_relative_forward() { - mpu.Status.N = true // $0000 BMI +06 writeMem(memory, 0x0000, listOf(0x30, 0x06)) mpu.step() assertEquals(0x0002 + 0x06, mpu.PC) - } @Test fun test_bmi_negative_set_branches_relative_backward() { - mpu.Status.N = true mpu.PC = 0x0050 // $0000 BMI -6 @@ -2277,36 +2031,30 @@ abstract class TestCommon6502 { writeMem(memory, 0x0050, listOf(0x30, rel.toShort())) mpu.step() assertEquals(0x0052 - 6, mpu.PC) - } @Test fun test_bmi_negative_clear_does_not_branch() { - mpu.Status.N = false // $0000 BEQ +6 writeMem(memory, 0x0000, listOf(0x30, 0x06)) mpu.step() assertEquals(0x0002, mpu.PC) - - // BNE - } + // BNE + @Test fun test_bne_zero_clear_branches_relative_forward() { - mpu.Status.Z = false // $0000 BNE +6 writeMem(memory, 0x0000, listOf(0xD0, 0x06)) mpu.step() assertEquals(0x0002 + 0x06, mpu.PC) - } @Test fun test_bne_zero_clear_branches_relative_backward() { - mpu.Status.Z = false mpu.PC = 0x0050 // $0050 BNE -6 @@ -2314,36 +2062,30 @@ abstract class TestCommon6502 { writeMem(memory, 0x0050, listOf(0xD0, rel.toShort())) mpu.step() assertEquals(0x0052 - 6, mpu.PC) - } @Test fun test_bne_zero_set_does_not_branch() { - mpu.Status.Z = true // $0000 BNE +6 writeMem(memory, 0x0000, listOf(0xD0, 0x06)) mpu.step() assertEquals(0x0002, mpu.PC) - - // BPL - } + // BPL + @Test fun test_bpl_negative_clear_branches_relative_forward() { - mpu.Status.N = false // $0000 BPL +06 writeMem(memory, 0x0000, listOf(0x10, 0x06)) mpu.step() assertEquals(0x0002 + 0x06, mpu.PC) - } @Test fun test_bpl_negative_clear_branches_relative_backward() { - mpu.Status.N = false mpu.PC = 0x0050 // $0050 BPL -6 @@ -2351,29 +2093,24 @@ abstract class TestCommon6502 { writeMem(memory, 0x0050, listOf(0x10, rel.toShort())) mpu.step() assertEquals(0x0052 - 6, mpu.PC) - } @Test fun test_bpl_negative_set_does_not_branch() { - mpu.Status.N = true // $0000 BPL +6 writeMem(memory, 0x0000, listOf(0x10, 0x06)) mpu.step() assertEquals(0x0002, mpu.PC) - - // BRK - } + // BRK + @Test fun test_brk_pushes_pc_plus_2_and_status_then_sets_pc_to_irq_vector() { - writeMem(memory, 0xFFFE, listOf(0xCD, 0xAB)) mpu.SP = 0xff mpu.Status.I = false - // $C000 BRK memory[0xC000] = 0x00 mpu.PC = 0xC000 @@ -2431,7 +2168,6 @@ abstract class TestCommon6502 { @Test fun test_bvs_overflow_set_branches_relative_backward() { - mpu.Status.V = true mpu.PC = 0x0050 val rel = 256 + (-6) // two's complement of 6 @@ -2439,7 +2175,6 @@ abstract class TestCommon6502 { writeMem(memory, 0x0050, listOf(0x70, rel.toShort())) mpu.step() assertEquals(0x0052 - 6, mpu.PC) - } @Test @@ -2513,7 +2248,6 @@ abstract class TestCommon6502 { @Test fun test_cmp_imm_sets_zero_carry_clears_neg_flags_if_equal() { // Comparison: A == m - // $0000 CMP #10 , A will be 10 writeMem(memory, 0x0000, listOf(0xC9, 10)) mpu.A = 10 @@ -2527,7 +2261,6 @@ abstract class TestCommon6502 { @Test fun test_cmp_imm_clears_zero_carry_takes_neg_if_less_unsigned() { // Comparison: A < m (unsigned) - // $0000 CMP #10 , A will be 1 writeMem(memory, 0x0000, listOf(0xC9, 10)) mpu.A = 1 @@ -2536,13 +2269,11 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.N) // 0x01-0x0A=0xF7 assertFalse(mpu.Status.Z) assertFalse(mpu.Status.C) - } @Test fun test_cmp_imm_clears_zero_sets_carry_takes_neg_if_less_signed() { // Comparison: A < #nn (signed), A negative - // $0000 CMP #1, A will be -1 (0xFF) writeMem(memory, 0x0000, listOf(0xC9, 1)) mpu.A = 0xFF @@ -2551,13 +2282,11 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.N) // 0xFF-0x01=0xFE assertFalse(mpu.Status.Z) assertTrue(mpu.Status.C) // A>m unsigned - } @Test fun test_cmp_imm_clears_zero_carry_takes_neg_if_less_signed_nega() { // Comparison: A < m (signed), A and m both negative - // $0000 CMP #0xFF (-1), A will be -2 (0xFE) writeMem(memory, 0x0000, listOf(0xC9, 0xFF)) mpu.A = 0xFE @@ -2566,13 +2295,11 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.N) // 0xFE-0xFF=0xFF assertFalse(mpu.Status.Z) assertFalse(mpu.Status.C) // A m (unsigned) - // $0000 CMP #1 , A will be 10 writeMem(memory, 0x0000, listOf(0xC9, 1)) mpu.A = 10 @@ -2586,7 +2313,6 @@ abstract class TestCommon6502 { @Test fun test_cmp_imm_clears_zero_carry_takes_neg_if_more_signed() { // Comparison: A > m (signed), memory negative - // $0000 CMP #$FF (-1), A will be 2 writeMem(memory, 0x0000, listOf(0xC9, 0xFF)) mpu.A = 2 @@ -2600,7 +2326,6 @@ abstract class TestCommon6502 { @Test fun test_cmp_imm_clears_zero_carry_takes_neg_if_more_signed_nega() { // Comparison: A > m (signed), A and m both negative - // $0000 CMP #$FE (-2), A will be -1 (0xFF) writeMem(memory, 0x0000, listOf(0xC9, 0xFE)) mpu.A = 0xFF @@ -2612,10 +2337,10 @@ abstract class TestCommon6502 { } // CPX Immediate + @Test fun test_cpx_imm_sets_zero_carry_clears_neg_flags_if_equal() { // Comparison: X == m - // $0000 CPX #$20 writeMem(memory, 0x0000, listOf(0xE0, 0x20)) mpu.X = 0x20 @@ -2627,10 +2352,10 @@ abstract class TestCommon6502 { } // CPY Immediate + @Test fun test_cpy_imm_sets_zero_carry_clears_neg_flags_if_equal() { // Comparison: Y == m - // $0000 CPY #$30 writeMem(memory, 0x0000, listOf(0xC0, 0x30)) mpu.Y = 0x30 @@ -2644,7 +2369,6 @@ abstract class TestCommon6502 { // DEC Absolute @Test fun test_dec_abs_decrements_memory() { - // $0000 DEC 0xABCD writeMem(memory, 0x0000, listOf(0xCE, 0xCD, 0xAB)) memory[0xABCD] = 0x10 @@ -2657,7 +2381,6 @@ abstract class TestCommon6502 { @Test fun test_dec_abs_below_00_rolls_over_and_sets_negative_flag() { - // $0000 DEC 0xABCD writeMem(memory, 0x0000, listOf(0xCE, 0xCD, 0xAB)) memory[0xABCD] = 0x00 @@ -2670,7 +2393,6 @@ abstract class TestCommon6502 { @Test fun test_dec_abs_sets_zero_flag_when_decrementing_to_zero() { - // $0000 DEC 0xABCD writeMem(memory, 0x0000, listOf(0xCE, 0xCD, 0xAB)) memory[0xABCD] = 0x01 @@ -2682,9 +2404,9 @@ abstract class TestCommon6502 { } // DEC Zero Page + @Test fun test_dec_zp_decrements_memory() { - // $0000 DEC 0x0010 writeMem(memory, 0x0000, listOf(0xC6, 0x10)) memory[0x0010] = 0x10 @@ -2693,12 +2415,10 @@ abstract class TestCommon6502 { assertEquals(0x0F, memory[0x0010]) assertFalse(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_dec_zp_below_00_rolls_over_and_sets_negative_flag() { - // $0000 DEC 0x0010 writeMem(memory, 0x0000, listOf(0xC6, 0x10)) memory[0x0010] = 0x00 @@ -2711,7 +2431,6 @@ abstract class TestCommon6502 { @Test fun test_dec_zp_sets_zero_flag_when_decrementing_to_zero() { - // $0000 DEC 0x0010 writeMem(memory, 0x0000, listOf(0xC6, 0x10)) memory[0x0010] = 0x01 @@ -2723,9 +2442,9 @@ abstract class TestCommon6502 { } // DEC Absolute, X-Indexed + @Test fun test_dec_abs_x_decrements_memory() { - // $0000 DEC 0xABCD,X writeMem(memory, 0x0000, listOf(0xDE, 0xCD, 0xAB)) mpu.X = 0x03 @@ -2739,7 +2458,6 @@ abstract class TestCommon6502 { @Test fun test_dec_abs_x_below_00_rolls_over_and_sets_negative_flag() { - // $0000 DEC 0xABCD,X writeMem(memory, 0x0000, listOf(0xDE, 0xCD, 0xAB)) memory[0xABCD + mpu.X] = 0x00 @@ -2752,7 +2470,6 @@ abstract class TestCommon6502 { @Test fun test_dec_abs_x_sets_zero_flag_when_decrementing_to_zero() { - // $0000 DEC 0xABCD,X writeMem(memory, 0x0000, listOf(0xDE, 0xCD, 0xAB)) memory[0xABCD + mpu.X] = 0x01 @@ -2764,9 +2481,9 @@ abstract class TestCommon6502 { } // DEC Zero Page, X-Indexed + @Test fun test_dec_zp_x_decrements_memory() { - // $0000 DEC 0x0010,X writeMem(memory, 0x0000, listOf(0xD6, 0x10)) mpu.X = 0x03 @@ -2780,7 +2497,6 @@ abstract class TestCommon6502 { @Test fun test_dec_zp_x_below_00_rolls_over_and_sets_negative_flag() { - // $0000 DEC 0x0010,X writeMem(memory, 0x0000, listOf(0xD6, 0x10)) mpu.X = 0x03 @@ -2794,7 +2510,6 @@ abstract class TestCommon6502 { @Test fun test_dec_zp_x_sets_zero_flag_when_decrementing_to_zero() { - // $0000 DEC 0x0010,X writeMem(memory, 0x0000, listOf(0xD6, 0x10)) mpu.X = 0x03 @@ -2807,6 +2522,7 @@ abstract class TestCommon6502 { } // DEX + @Test fun test_dex_decrements_x() { mpu.X = 0x10 @@ -2844,6 +2560,7 @@ abstract class TestCommon6502 { } // DEY + @Test fun test_dey_decrements_y() { mpu.Y = 0x10 @@ -2869,7 +2586,6 @@ abstract class TestCommon6502 { @Test fun test_dey_sets_zero_flag_when_decrementing_to_zero() { - mpu.Y = 0x01 // $0000 DEY memory[0x0000] = 0x88 @@ -2880,9 +2596,9 @@ abstract class TestCommon6502 { } // EOR Absolute + @Test fun test_eor_absolute_flips_bits_over_setting_z_flag() { - mpu.A = 0xFF writeMem(memory, 0x0000, listOf(0x4D, 0xCD, 0xAB)) memory[0xABCD] = 0xFF @@ -2891,12 +2607,10 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.A) assertEquals(0xFF, memory[0xABCD]) assertTrue(mpu.Status.Z) - } @Test fun test_eor_absolute_flips_bits_over_setting_n_flag() { - mpu.A = 0x00 writeMem(memory, 0x0000, listOf(0x4D, 0xCD, 0xAB)) memory[0xABCD] = 0xFF @@ -2906,14 +2620,12 @@ abstract class TestCommon6502 { assertEquals(0xFF, memory[0xABCD]) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - - // EOR Zero Page - } + // EOR Zero Page + @Test fun test_eor_zp_flips_bits_over_setting_z_flag() { - mpu.A = 0xFF writeMem(memory, 0x0000, listOf(0x45, 0x10)) memory[0x0010] = 0xFF @@ -2922,12 +2634,10 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.A) assertEquals(0xFF, memory[0x0010]) assertTrue(mpu.Status.Z) - } @Test fun test_eor_zp_flips_bits_over_setting_n_flag() { - mpu.A = 0x00 writeMem(memory, 0x0000, listOf(0x45, 0x10)) memory[0x0010] = 0xFF @@ -2937,26 +2647,22 @@ abstract class TestCommon6502 { assertEquals(0xFF, memory[0x0010]) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - - // EOR Immediate - } + // EOR Immediate + @Test fun test_eor_immediate_flips_bits_over_setting_z_flag() { - mpu.A = 0xFF writeMem(memory, 0x0000, listOf(0x49, 0xFF)) mpu.step() assertEquals(0x0002, mpu.PC) assertEquals(0x00, mpu.A) assertTrue(mpu.Status.Z) - } @Test fun test_eor_immediate_flips_bits_over_setting_n_flag() { - mpu.A = 0x00 writeMem(memory, 0x0000, listOf(0x49, 0xFF)) mpu.step() @@ -2964,14 +2670,12 @@ abstract class TestCommon6502 { assertEquals(0xFF, mpu.A) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - - // EOR Absolute, X-Indexed - } + // EOR Absolute, X-Indexed + @Test fun test_eor_abs_x_indexed_flips_bits_over_setting_z_flag() { - mpu.A = 0xFF mpu.X = 0x03 writeMem(memory, 0x0000, listOf(0x5D, 0xCD, 0xAB)) @@ -2981,12 +2685,10 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.A) assertEquals(0xFF, memory[0xABCD + mpu.X]) assertTrue(mpu.Status.Z) - } @Test fun test_eor_abs_x_indexed_flips_bits_over_setting_n_flag() { - mpu.A = 0x00 mpu.X = 0x03 writeMem(memory, 0x0000, listOf(0x5D, 0xCD, 0xAB)) @@ -2997,14 +2699,12 @@ abstract class TestCommon6502 { assertEquals(0xFF, memory[0xABCD + mpu.X]) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - - // EOR Absolute, Y-Indexed - } + // EOR Absolute, Y-Indexed + @Test fun test_eor_abs_y_indexed_flips_bits_over_setting_z_flag() { - mpu.A = 0xFF mpu.Y = 0x03 writeMem(memory, 0x0000, listOf(0x59, 0xCD, 0xAB)) @@ -3014,12 +2714,10 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.A) assertEquals(0xFF, memory[0xABCD + mpu.Y]) assertTrue(mpu.Status.Z) - } @Test fun test_eor_abs_y_indexed_flips_bits_over_setting_n_flag() { - mpu.A = 0x00 mpu.Y = 0x03 writeMem(memory, 0x0000, listOf(0x59, 0xCD, 0xAB)) @@ -3030,14 +2728,12 @@ abstract class TestCommon6502 { assertEquals(0xFF, memory[0xABCD + mpu.Y]) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - - // EOR Indirect, Indexed (X) - } + // EOR Indirect, Indexed (X) + @Test fun test_eor_ind_indexed_x_flips_bits_over_setting_z_flag() { - mpu.A = 0xFF mpu.X = 0x03 writeMem(memory, 0x0000, listOf(0x41, 0x10)) // => EOR listOf($0010,X) @@ -3048,12 +2744,10 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.A) assertEquals(0xFF, memory[0xABCD]) assertTrue(mpu.Status.Z) - } @Test fun test_eor_ind_indexed_x_flips_bits_over_setting_n_flag() { - mpu.A = 0x00 mpu.X = 0x03 writeMem(memory, 0x0000, listOf(0x41, 0x10)) // => EOR listOf($0010,X) @@ -3065,14 +2759,12 @@ abstract class TestCommon6502 { assertEquals(0xFF, memory[0xABCD]) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - - // EOR Indexed, Indirect (Y) - } + // EOR Indexed, Indirect (Y) + @Test fun test_eor_indexed_ind_y_flips_bits_over_setting_z_flag() { - mpu.A = 0xFF mpu.Y = 0x03 writeMem(memory, 0x0000, listOf(0x51, 0x10)) // => EOR listOf($0010),Y @@ -3083,12 +2775,10 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.A) assertEquals(0xFF, memory[0xABCD + mpu.Y]) assertTrue(mpu.Status.Z) - } @Test fun test_eor_indexed_ind_y_flips_bits_over_setting_n_flag() { - mpu.A = 0x00 mpu.Y = 0x03 writeMem(memory, 0x0000, listOf(0x51, 0x10)) // => EOR listOf($0010),Y @@ -3100,14 +2790,12 @@ abstract class TestCommon6502 { assertEquals(0xFF, memory[0xABCD + mpu.Y]) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - - // EOR Zero Page, X-Indexed - } + // EOR Zero Page, X-Indexed + @Test fun test_eor_zp_x_indexed_flips_bits_over_setting_z_flag() { - mpu.A = 0xFF mpu.X = 0x03 writeMem(memory, 0x0000, listOf(0x55, 0x10)) @@ -3117,12 +2805,10 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.A) assertEquals(0xFF, memory[0x0010 + mpu.X]) assertTrue(mpu.Status.Z) - } @Test fun test_eor_zp_x_indexed_flips_bits_over_setting_n_flag() { - mpu.A = 0x00 mpu.X = 0x03 writeMem(memory, 0x0000, listOf(0x55, 0x10)) @@ -3133,14 +2819,12 @@ abstract class TestCommon6502 { assertEquals(0xFF, memory[0x0010 + mpu.X]) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - - // INC Absolute - } + // INC Absolute + @Test fun test_inc_abs_increments_memory() { - writeMem(memory, 0x0000, listOf(0xEE, 0xCD, 0xAB)) memory[0xABCD] = 0x09 mpu.step() @@ -3148,12 +2832,10 @@ abstract class TestCommon6502 { assertEquals(0x0A, memory[0xABCD]) assertFalse(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_inc_abs_increments_memory_rolls_over_and_sets_zero_flag() { - writeMem(memory, 0x0000, listOf(0xEE, 0xCD, 0xAB)) memory[0xABCD] = 0xFF mpu.step() @@ -3161,12 +2843,10 @@ abstract class TestCommon6502 { assertEquals(0x00, memory[0xABCD]) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_inc_abs_sets_negative_flag_when_incrementing_above_7F() { - writeMem(memory, 0x0000, listOf(0xEE, 0xCD, 0xAB)) memory[0xABCD] = 0x7F mpu.step() @@ -3174,14 +2854,12 @@ abstract class TestCommon6502 { assertEquals(0x80, memory[0xABCD]) assertFalse(mpu.Status.Z) assertTrue(mpu.Status.N) - - // INC Zero Page - } + // INC Zero Page + @Test fun test_inc_zp_increments_memory() { - writeMem(memory, 0x0000, listOf(0xE6, 0x10)) memory[0x0010] = 0x09 mpu.step() @@ -3189,12 +2867,10 @@ abstract class TestCommon6502 { assertEquals(0x0A, memory[0x0010]) assertFalse(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_inc_zp_increments_memory_rolls_over_and_sets_zero_flag() { - writeMem(memory, 0x0000, listOf(0xE6, 0x10)) memory[0x0010] = 0xFF mpu.step() @@ -3202,12 +2878,10 @@ abstract class TestCommon6502 { assertEquals(0x00, memory[0x0010]) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_inc_zp_sets_negative_flag_when_incrementing_above_7F() { - writeMem(memory, 0x0000, listOf(0xE6, 0x10)) memory[0x0010] = 0x7F mpu.step() @@ -3215,14 +2889,12 @@ abstract class TestCommon6502 { assertEquals(0x80, memory[0x0010]) assertFalse(mpu.Status.Z) assertTrue(mpu.Status.N) - - // INC Absolute, X-Indexed - } + // INC Absolute, X-Indexed + @Test fun test_inc_abs_x_increments_memory() { - writeMem(memory, 0x0000, listOf(0xFE, 0xCD, 0xAB)) mpu.X = 0x03 memory[0xABCD + mpu.X] = 0x09 @@ -3231,12 +2903,10 @@ abstract class TestCommon6502 { assertEquals(0x0A, memory[0xABCD + mpu.X]) assertFalse(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_inc_abs_x_increments_memory_rolls_over_and_sets_zero_flag() { - writeMem(memory, 0x0000, listOf(0xFE, 0xCD, 0xAB)) mpu.X = 0x03 memory[0xABCD + mpu.X] = 0xFF @@ -3245,12 +2915,10 @@ abstract class TestCommon6502 { assertEquals(0x00, memory[0xABCD + mpu.X]) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_inc_abs_x_sets_negative_flag_when_incrementing_above_7F() { - writeMem(memory, 0x0000, listOf(0xFE, 0xCD, 0xAB)) mpu.X = 0x03 memory[0xABCD + mpu.X] = 0x7F @@ -3259,14 +2927,12 @@ abstract class TestCommon6502 { assertEquals(0x80, memory[0xABCD + mpu.X]) assertFalse(mpu.Status.Z) assertTrue(mpu.Status.N) - - // INC Zero Page, X-Indexed - } + // INC Zero Page, X-Indexed + @Test fun test_inc_zp_x_increments_memory() { - writeMem(memory, 0x0000, listOf(0xF6, 0x10)) mpu.X = 0x03 memory[0x0010 + mpu.X] = 0x09 @@ -3275,12 +2941,10 @@ abstract class TestCommon6502 { assertEquals(0x0A, memory[0x0010 + mpu.X]) assertFalse(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_inc_zp_x_increments_memory_rolls_over_and_sets_zero_flag() { - writeMem(memory, 0x0000, listOf(0xF6, 0x10)) memory[0x0010 + mpu.X] = 0xFF mpu.step() @@ -3288,12 +2952,10 @@ abstract class TestCommon6502 { assertEquals(0x00, memory[0x0010 + mpu.X]) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_inc_zp_x_sets_negative_flag_when_incrementing_above_7F() { - writeMem(memory, 0x0000, listOf(0xF6, 0x10)) memory[0x0010 + mpu.X] = 0x7F mpu.step() @@ -3301,14 +2963,12 @@ abstract class TestCommon6502 { assertEquals(0x80, memory[0x0010 + mpu.X]) assertFalse(mpu.Status.Z) assertTrue(mpu.Status.N) - - // INX - } + // INX + @Test fun test_inx_increments_x() { - mpu.X = 0x09 memory[0x0000] = 0xE8 // => INX mpu.step() @@ -3316,19 +2976,16 @@ abstract class TestCommon6502 { assertEquals(0x0A, mpu.X) assertFalse(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_inx_above_FF_rolls_over_and_sets_zero_flag() { - mpu.X = 0xFF memory[0x0000] = 0xE8 // => INX mpu.step() assertEquals(0x0001, mpu.PC) assertEquals(0x00, mpu.X) assertTrue(mpu.Status.Z) - } @Test @@ -3345,7 +3002,6 @@ abstract class TestCommon6502 { @Test fun test_iny_increments_y() { - mpu.Y = 0x09 memory[0x0000] = 0xC8 // => INY mpu.step() @@ -3357,58 +3013,49 @@ abstract class TestCommon6502 { @Test fun test_iny_above_FF_rolls_over_and_sets_zero_flag() { - mpu.Y = 0xFF memory[0x0000] = 0xC8 // => INY mpu.step() assertEquals(0x0001, mpu.PC) assertEquals(0x00, mpu.Y) assertTrue(mpu.Status.Z) - } @Test fun test_iny_sets_negative_flag_when_incrementing_above_7F() { - mpu.Y = 0x7f memory[0x0000] = 0xC8 // => INY mpu.step() assertEquals(0x0001, mpu.PC) assertEquals(0x80, mpu.Y) assertTrue(mpu.Status.N) - - // JMP Absolute - } + // JMP Absolute + @Test fun test_jmp_abs_jumps_to_absolute_address() { - // $0000 JMP $ABCD writeMem(memory, 0x0000, listOf(0x4C, 0xCD, 0xAB)) mpu.step() assertEquals(0xABCD, mpu.PC) - - // JMP Indirect - } + // JMP Indirect + @Test fun test_jmp_ind_jumps_to_indirect_address() { - // $0000 JMP ($ABCD) writeMem(memory, 0x0000, listOf(0x6C, 0x00, 0x02)) writeMem(memory, 0x0200, listOf(0xCD, 0xAB)) mpu.step() assertEquals(0xABCD, mpu.PC) - - // JSR - } + // JSR + @Test fun test_jsr_pushes_pc_plus_2_and_sets_pc() { - // $C000 JSR $FFD2 mpu.SP = 0xFF writeMem(memory, 0xC000, listOf(0x20, 0xD2, 0xFF)) @@ -3424,7 +3071,6 @@ abstract class TestCommon6502 { @Test fun test_lda_absolute_loads_a_sets_n_flag() { - mpu.A = 0x00 // $0000 LDA $ABCD writeMem(memory, 0x0000, listOf(0xAD, 0xCD, 0xAB)) @@ -3434,12 +3080,10 @@ abstract class TestCommon6502 { assertEquals(0x80, mpu.A) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_lda_absolute_loads_a_sets_z_flag() { - mpu.A = 0xFF // $0000 LDA $ABCD writeMem(memory, 0x0000, listOf(0xAD, 0xCD, 0xAB)) @@ -3449,14 +3093,12 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.A) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - - // LDA Zero Page - } + // LDA Zero Page + @Test fun test_lda_zp_loads_a_sets_n_flag() { - mpu.A = 0x00 // $0000 LDA $0010 writeMem(memory, 0x0000, listOf(0xA5, 0x10)) @@ -3466,12 +3108,10 @@ abstract class TestCommon6502 { assertEquals(0x80, mpu.A) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_lda_zp_loads_a_sets_z_flag() { - mpu.A = 0xFF // $0000 LDA $0010 writeMem(memory, 0x0000, listOf(0xA5, 0x10)) @@ -3481,14 +3121,12 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.A) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - - // LDA Immediate - } + // LDA Immediate + @Test fun test_lda_immediate_loads_a_sets_n_flag() { - mpu.A = 0x00 // $0000 LDA #$80 writeMem(memory, 0x0000, listOf(0xA9, 0x80)) @@ -3497,12 +3135,10 @@ abstract class TestCommon6502 { assertEquals(0x80, mpu.A) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_lda_immediate_loads_a_sets_z_flag() { - mpu.A = 0xFF // $0000 LDA #$00 writeMem(memory, 0x0000, listOf(0xA9, 0x00)) @@ -3511,14 +3147,12 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.A) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - - // LDA Absolute, X-Indexed - } + // LDA Absolute, X-Indexed + @Test fun test_lda_abs_x_indexed_loads_a_sets_n_flag() { - mpu.A = 0x00 mpu.X = 0x03 // $0000 LDA $ABCD,X @@ -3529,12 +3163,10 @@ abstract class TestCommon6502 { assertEquals(0x80, mpu.A) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_lda_abs_x_indexed_loads_a_sets_z_flag() { - mpu.A = 0xFF mpu.X = 0x03 // $0000 LDA $ABCD,X @@ -3545,12 +3177,10 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.A) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_lda_abs_x_indexed_does_not_page_wrap() { - mpu.A = 0 mpu.X = 0xFF // $0000 LDA $0080,X @@ -3559,14 +3189,12 @@ abstract class TestCommon6502 { mpu.step() assertEquals(0x0003, mpu.PC) assertEquals(0x42, mpu.A) - - // LDA Absolute, Y-Indexed - } + // LDA Absolute, Y-Indexed + @Test fun test_lda_abs_y_indexed_loads_a_sets_n_flag() { - mpu.A = 0x00 mpu.Y = 0x03 // $0000 LDA $ABCD,Y @@ -3577,12 +3205,10 @@ abstract class TestCommon6502 { assertEquals(0x80, mpu.A) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_lda_abs_y_indexed_loads_a_sets_z_flag() { - mpu.A = 0xFF mpu.Y = 0x03 // $0000 LDA $ABCD,Y @@ -3593,12 +3219,10 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.A) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_lda_abs_y_indexed_does_not_page_wrap() { - mpu.A = 0 mpu.Y = 0xFF // $0000 LDA $0080,X @@ -3607,14 +3231,12 @@ abstract class TestCommon6502 { mpu.step() assertEquals(0x0003, mpu.PC) assertEquals(0x42, mpu.A) - - // LDA Indirect, Indexed (X) - } + // LDA Indirect, Indexed (X) + @Test fun test_lda_ind_indexed_x_loads_a_sets_n_flag() { - mpu.A = 0x00 mpu.X = 0x03 // $0000 LDA ($0010,X) @@ -3627,12 +3249,10 @@ abstract class TestCommon6502 { assertEquals(0x80, mpu.A) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_lda_ind_indexed_x_loads_a_sets_z_flag() { - mpu.A = 0x00 mpu.X = 0x03 // $0000 LDA ($0010,X) @@ -3645,14 +3265,12 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.A) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - - // LDA Indexed, Indirect (Y) - } + // LDA Indexed, Indirect (Y) + @Test fun test_lda_indexed_ind_y_loads_a_sets_n_flag() { - mpu.A = 0x00 mpu.Y = 0x03 // $0000 LDA ($0010),Y @@ -3665,12 +3283,24 @@ abstract class TestCommon6502 { assertEquals(0x80, mpu.A) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) + } + @Test + fun test_lda_indexed_ind_y_correct_index() { + mpu.A = 0x00 + mpu.Y = 0xf3 + // $0000 LDA ($0010),Y + // $0010 Vector to $ABCD + writeMem(memory, 0x0000, listOf(0xB1, 0x10)) + writeMem(memory, 0x0010, listOf(0xCD, 0xAB)) + memory[0xABCD + mpu.Y] = 0x80 + mpu.step() + assertEquals(0x0002, mpu.PC) + assertEquals(0x80, mpu.A) } @Test fun test_lda_indexed_ind_y_loads_a_sets_z_flag() { - mpu.A = 0x00 mpu.Y = 0x03 // $0000 LDA ($0010),Y @@ -3683,14 +3313,12 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.A) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - - // LDA Zero Page, X-Indexed - } + // LDA Zero Page, X-Indexed + @Test fun test_lda_zp_x_indexed_loads_a_sets_n_flag() { - mpu.A = 0x00 mpu.X = 0x03 // $0000 LDA $10,X @@ -3701,12 +3329,22 @@ abstract class TestCommon6502 { assertEquals(0x80, mpu.A) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) + } + @Test + fun test_lda_zp_x_indexed_correct_index() { + mpu.A = 0x00 + mpu.X = 0xf3 + // $0000 LDA $10,X + writeMem(memory, 0x0000, listOf(0xB5, 0x10)) + memory[(0x0010 + mpu.X) and 255] = 0x80 + mpu.step() + assertEquals(0x0002, mpu.PC) + assertEquals(0x80, mpu.A) } @Test fun test_lda_zp_x_indexed_loads_a_sets_z_flag() { - mpu.A = 0xFF mpu.X = 0x03 // $0000 LDA $10,X @@ -3717,14 +3355,12 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.A) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - - // LDX Absolute - } + // LDX Absolute + @Test fun test_ldx_absolute_loads_x_sets_n_flag() { - mpu.X = 0x00 // $0000 LDX $ABCD writeMem(memory, 0x0000, listOf(0xAE, 0xCD, 0xAB)) @@ -3734,12 +3370,10 @@ abstract class TestCommon6502 { assertEquals(0x80, mpu.X) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_ldx_absolute_loads_x_sets_z_flag() { - mpu.X = 0xFF // $0000 LDX $ABCD writeMem(memory, 0x0000, listOf(0xAE, 0xCD, 0xAB)) @@ -3749,14 +3383,12 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.X) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - - // LDX Zero Page - } + // LDX Zero Page + @Test fun test_ldx_zp_loads_x_sets_n_flag() { - mpu.X = 0x00 // $0000 LDX $0010 writeMem(memory, 0x0000, listOf(0xA6, 0x10)) @@ -3766,12 +3398,10 @@ abstract class TestCommon6502 { assertEquals(0x80, mpu.X) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_ldx_zp_loads_x_sets_z_flag() { - mpu.X = 0xFF // $0000 LDX $0010 writeMem(memory, 0x0000, listOf(0xA6, 0x10)) @@ -3781,14 +3411,12 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.X) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - - // LDX Immediate - } + // LDX Immediate + @Test fun test_ldx_immediate_loads_x_sets_n_flag() { - mpu.X = 0x00 // $0000 LDX #$80 writeMem(memory, 0x0000, listOf(0xA2, 0x80)) @@ -3797,12 +3425,10 @@ abstract class TestCommon6502 { assertEquals(0x80, mpu.X) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_ldx_immediate_loads_x_sets_z_flag() { - mpu.X = 0xFF // $0000 LDX #$00 writeMem(memory, 0x0000, listOf(0xA2, 0x00)) @@ -3811,14 +3437,12 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.X) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - - // LDX Absolute, Y-Indexed - } + // LDX Absolute, Y-Indexed + @Test fun test_ldx_abs_y_indexed_loads_x_sets_n_flag() { - mpu.X = 0x00 mpu.Y = 0x03 // $0000 LDX $ABCD,Y @@ -3829,12 +3453,10 @@ abstract class TestCommon6502 { assertEquals(0x80, mpu.X) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_ldx_abs_y_indexed_loads_x_sets_z_flag() { - mpu.X = 0xFF mpu.Y = 0x03 // $0000 LDX $ABCD,Y @@ -3845,14 +3467,12 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.X) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - - // LDX Zero Page, Y-Indexed - } + // LDX Zero Page, Y-Indexed + @Test fun test_ldx_zp_y_indexed_loads_x_sets_n_flag() { - mpu.X = 0x00 mpu.Y = 0x03 // $0000 LDX $0010,Y @@ -3863,12 +3483,10 @@ abstract class TestCommon6502 { assertEquals(0x80, mpu.X) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_ldx_zp_y_indexed_loads_x_sets_z_flag() { - mpu.X = 0xFF mpu.Y = 0x03 // $0000 LDX $0010,Y @@ -3879,14 +3497,12 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.X) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - - // LDY Absolute - } + // LDY Absolute + @Test fun test_ldy_absolute_loads_y_sets_n_flag() { - mpu.Y = 0x00 // $0000 LDY $ABCD writeMem(memory, 0x0000, listOf(0xAC, 0xCD, 0xAB)) @@ -3896,12 +3512,10 @@ abstract class TestCommon6502 { assertEquals(0x80, mpu.Y) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_ldy_absolute_loads_y_sets_z_flag() { - mpu.Y = 0xFF // $0000 LDY $ABCD writeMem(memory, 0x0000, listOf(0xAC, 0xCD, 0xAB)) @@ -3911,14 +3525,12 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.Y) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - - // LDY Zero Page - } + // LDY Zero Page + @Test fun test_ldy_zp_loads_y_sets_n_flag() { - mpu.Y = 0x00 // $0000 LDY $0010 writeMem(memory, 0x0000, listOf(0xA4, 0x10)) @@ -3928,12 +3540,10 @@ abstract class TestCommon6502 { assertEquals(0x80, mpu.Y) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_ldy_zp_loads_y_sets_z_flag() { - mpu.Y = 0xFF // $0000 LDY $0010 writeMem(memory, 0x0000, listOf(0xA4, 0x10)) @@ -3943,14 +3553,12 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.Y) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - - // LDY Immediate - } + // LDY Immediate + @Test fun test_ldy_immediate_loads_y_sets_n_flag() { - mpu.Y = 0x00 // $0000 LDY #$80 writeMem(memory, 0x0000, listOf(0xA0, 0x80)) @@ -3959,12 +3567,10 @@ abstract class TestCommon6502 { assertEquals(0x80, mpu.Y) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_ldy_immediate_loads_y_sets_z_flag() { - mpu.Y = 0xFF // $0000 LDY #$00 writeMem(memory, 0x0000, listOf(0xA0, 0x00)) @@ -3973,14 +3579,12 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.Y) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - - // LDY Absolute, X-Indexed - } + // LDY Absolute, X-Indexed + @Test fun test_ldy_abs_x_indexed_loads_x_sets_n_flag() { - mpu.Y = 0x00 mpu.X = 0x03 // $0000 LDY $ABCD,X @@ -3991,12 +3595,10 @@ abstract class TestCommon6502 { assertEquals(0x80, mpu.Y) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_ldy_abs_x_indexed_loads_x_sets_z_flag() { - mpu.Y = 0xFF mpu.X = 0x03 // $0000 LDY $ABCD,X @@ -4007,14 +3609,12 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.Y) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - - // LDY Zero Page, X-Indexed - } + // LDY Zero Page, X-Indexed + @Test fun test_ldy_zp_x_indexed_loads_x_sets_n_flag() { - mpu.Y = 0x00 mpu.X = 0x03 // $0000 LDY $0010,X @@ -4025,12 +3625,10 @@ abstract class TestCommon6502 { assertEquals(0x80, mpu.Y) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_ldy_zp_x_indexed_loads_x_sets_z_flag() { - mpu.Y = 0xFF mpu.X = 0x03 // $0000 LDY $0010,X @@ -4041,14 +3639,12 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.Y) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - - // LSR Accumulator - } + // LSR Accumulator + @Test fun test_lsr_accumulator_rotates_in_zero_not_carry() { - mpu.Status.C = true // $0000 LSR A memory[0x0000] = (0x4A) @@ -4059,12 +3655,10 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.Z) assertFalse(mpu.Status.C) assertFalse(mpu.Status.N) - } @Test fun test_lsr_accumulator_sets_carry_and_zero_flags_after_rotation() { - mpu.Status.C = false // $0000 LSR A memory[0x0000] = (0x4A) @@ -4075,12 +3669,10 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.Z) assertTrue(mpu.Status.C) assertFalse(mpu.Status.N) - } @Test fun test_lsr_accumulator_rotates_bits_right() { - mpu.Status.C = true // $0000 LSR A memory[0x0000] = (0x4A) @@ -4091,14 +3683,12 @@ abstract class TestCommon6502 { assertFalse(mpu.Status.Z) assertFalse(mpu.Status.C) assertFalse(mpu.Status.N) - - // LSR Absolute - } + // LSR Absolute + @Test fun test_lsr_absolute_rotates_in_zero_not_carry() { - mpu.Status.C = true // $0000 LSR $ABCD writeMem(memory, 0x0000, listOf(0x4E, 0xCD, 0xAB)) @@ -4109,12 +3699,10 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.Z) assertFalse(mpu.Status.C) assertFalse(mpu.Status.N) - } @Test fun test_lsr_absolute_sets_carry_and_zero_flags_after_rotation() { - mpu.Status.C = false // $0000 LSR $ABCD writeMem(memory, 0x0000, listOf(0x4E, 0xCD, 0xAB)) @@ -4125,12 +3713,10 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.Z) assertTrue(mpu.Status.C) assertFalse(mpu.Status.N) - } @Test fun test_lsr_absolute_rotates_bits_right() { - mpu.Status.C = true // $0000 LSR $ABCD writeMem(memory, 0x0000, listOf(0x4E, 0xCD, 0xAB)) @@ -4141,14 +3727,12 @@ abstract class TestCommon6502 { assertFalse(mpu.Status.Z) assertFalse(mpu.Status.C) assertFalse(mpu.Status.N) - - // LSR Zero Page - } + // LSR Zero Page + @Test fun test_lsr_zp_rotates_in_zero_not_carry() { - mpu.Status.C = true // $0000 LSR $0010 writeMem(memory, 0x0000, listOf(0x46, 0x10)) @@ -4159,12 +3743,10 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.Z) assertFalse(mpu.Status.C) assertFalse(mpu.Status.N) - } @Test fun test_lsr_zp_sets_carry_and_zero_flags_after_rotation() { - mpu.Status.C = false // $0000 LSR $0010 writeMem(memory, 0x0000, listOf(0x46, 0x10)) @@ -4175,12 +3757,10 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.Z) assertTrue(mpu.Status.C) assertFalse(mpu.Status.N) - } @Test fun test_lsr_zp_rotates_bits_right() { - mpu.Status.C = true // $0000 LSR $0010 writeMem(memory, 0x0000, listOf(0x46, 0x10)) @@ -4191,14 +3771,12 @@ abstract class TestCommon6502 { assertFalse(mpu.Status.Z) assertFalse(mpu.Status.C) assertFalse(mpu.Status.N) - - // LSR Absolute, X-Indexed - } + // LSR Absolute, X-Indexed + @Test fun test_lsr_abs_x_indexed_rotates_in_zero_not_carry() { - mpu.Status.C = true mpu.X = 0x03 // $0000 LSR $ABCD,X @@ -4210,12 +3788,10 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.Z) assertFalse(mpu.Status.C) assertFalse(mpu.Status.N) - } @Test fun test_lsr_abs_x_indexed_sets_c_and_z_flags_after_rotation() { - mpu.Status.C = false mpu.X = 0x03 // $0000 LSR $ABCD,X @@ -4227,12 +3803,10 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.Z) assertTrue(mpu.Status.C) assertFalse(mpu.Status.N) - } @Test fun test_lsr_abs_x_indexed_rotates_bits_right() { - mpu.Status.C = true // $0000 LSR $ABCD,X writeMem(memory, 0x0000, listOf(0x5E, 0xCD, 0xAB)) @@ -4243,14 +3817,12 @@ abstract class TestCommon6502 { assertFalse(mpu.Status.Z) assertFalse(mpu.Status.C) assertFalse(mpu.Status.N) - - // LSR Zero Page, X-Indexed - } + // LSR Zero Page, X-Indexed + @Test fun test_lsr_zp_x_indexed_rotates_in_zero_not_carry() { - mpu.Status.C = true mpu.X = 0x03 // $0000 LSR $0010,X @@ -4262,12 +3834,10 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.Z) assertFalse(mpu.Status.C) assertFalse(mpu.Status.N) - } @Test fun test_lsr_zp_x_indexed_sets_carry_and_zero_flags_after_rotation() { - mpu.Status.C = false mpu.X = 0x03 // $0000 LSR $0010,X @@ -4279,12 +3849,10 @@ abstract class TestCommon6502 { assertTrue(mpu.Status.Z) assertTrue(mpu.Status.C) assertFalse(mpu.Status.N) - } @Test fun test_lsr_zp_x_indexed_rotates_bits_right() { - mpu.Status.C = true mpu.X = 0x03 // $0000 LSR $0010,X @@ -4296,26 +3864,22 @@ abstract class TestCommon6502 { assertFalse(mpu.Status.Z) assertFalse(mpu.Status.C) assertFalse(mpu.Status.N) - - // NOP - } + // NOP + @Test fun test_nop_does_nothing() { - // $0000 NOP memory[0x0000] = 0xEA mpu.step() assertEquals(0x0001, mpu.PC) - - // ORA Absolute - } + // ORA Absolute + @Test fun test_ora_absolute_zeroes_or_zeros_sets_z_flag() { - mpu.Status.Z = false mpu.A = 0x00 // $0000 ORA $ABCD @@ -4325,12 +3889,10 @@ abstract class TestCommon6502 { assertEquals(0x0003, mpu.PC) assertEquals(0x00, mpu.A) assertTrue(mpu.Status.Z) - } @Test fun test_ora_absolute_turns_bits_on_sets_n_flag() { - mpu.Status.N = false mpu.A = 0x03 // $0000 ORA $ABCD @@ -4341,14 +3903,12 @@ abstract class TestCommon6502 { assertEquals(0x83, mpu.A) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - - // ORA Zero Page - } + // ORA Zero Page + @Test fun test_ora_zp_zeroes_or_zeros_sets_z_flag() { - mpu.Status.Z = false mpu.A = 0x00 // $0000 ORA $0010 @@ -4358,12 +3918,10 @@ abstract class TestCommon6502 { assertEquals(0x0002, mpu.PC) assertEquals(0x00, mpu.A) assertTrue(mpu.Status.Z) - } @Test fun test_ora_zp_turns_bits_on_sets_n_flag() { - mpu.Status.N = false mpu.A = 0x03 // $0000 ORA $0010 @@ -4374,14 +3932,12 @@ abstract class TestCommon6502 { assertEquals(0x83, mpu.A) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - - // ORA Immediate - } + // ORA Immediate + @Test fun test_ora_immediate_zeroes_or_zeros_sets_z_flag() { - mpu.Status.Z = false mpu.A = 0x00 // $0000 ORA #$00 @@ -4390,12 +3946,10 @@ abstract class TestCommon6502 { assertEquals(0x0002, mpu.PC) assertEquals(0x00, mpu.A) assertTrue(mpu.Status.Z) - } @Test fun test_ora_immediate_turns_bits_on_sets_n_flag() { - mpu.Status.N = false mpu.A = 0x03 // $0000 ORA #$82 @@ -4405,14 +3959,12 @@ abstract class TestCommon6502 { assertEquals(0x83, mpu.A) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - - // ORA Absolute, X - } + // ORA Absolute, X + @Test fun test_ora_abs_x_indexed_zeroes_or_zeros_sets_z_flag() { - mpu.Status.Z = false mpu.A = 0x00 mpu.X = 0x03 @@ -4423,12 +3975,10 @@ abstract class TestCommon6502 { assertEquals(0x0003, mpu.PC) assertEquals(0x00, mpu.A) assertTrue(mpu.Status.Z) - } @Test fun test_ora_abs_x_indexed_turns_bits_on_sets_n_flag() { - mpu.Status.N = false mpu.A = 0x03 mpu.X = 0x03 @@ -4440,14 +3990,12 @@ abstract class TestCommon6502 { assertEquals(0x83, mpu.A) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - - // ORA Absolute, Y - } + // ORA Absolute, Y + @Test fun test_ora_abs_y_indexed_zeroes_or_zeros_sets_z_flag() { - mpu.Status.Z = false mpu.A = 0x00 mpu.Y = 0x03 @@ -4458,12 +4006,10 @@ abstract class TestCommon6502 { assertEquals(0x0003, mpu.PC) assertEquals(0x00, mpu.A) assertTrue(mpu.Status.Z) - } @Test fun test_ora_abs_y_indexed_turns_bits_on_sets_n_flag() { - mpu.Status.N = false mpu.A = 0x03 mpu.Y = 0x03 @@ -4475,14 +4021,12 @@ abstract class TestCommon6502 { assertEquals(0x83, mpu.A) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - - // ORA Indirect, Indexed (X) - } + // ORA Indirect, Indexed (X) + @Test fun test_ora_ind_indexed_x_zeroes_or_zeros_sets_z_flag() { - mpu.Status.Z = false mpu.A = 0x00 mpu.X = 0x03 @@ -4495,12 +4039,10 @@ abstract class TestCommon6502 { assertEquals(0x0002, mpu.PC) assertEquals(0x00, mpu.A) assertTrue(mpu.Status.Z) - } @Test fun test_ora_ind_indexed_x_turns_bits_on_sets_n_flag() { - mpu.Status.N = false mpu.A = 0x03 mpu.X = 0x03 @@ -4514,14 +4056,12 @@ abstract class TestCommon6502 { assertEquals(0x83, mpu.A) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - - // ORA Indexed, Indirect (Y) - } + // ORA Indexed, Indirect (Y) + @Test fun test_ora_indexed_ind_y_zeroes_or_zeros_sets_z_flag() { - mpu.Status.Z = false mpu.A = 0x00 mpu.Y = 0x03 @@ -4534,12 +4074,10 @@ abstract class TestCommon6502 { assertEquals(0x0002, mpu.PC) assertEquals(0x00, mpu.A) assertTrue(mpu.Status.Z) - } @Test fun test_ora_indexed_ind_y_turns_bits_on_sets_n_flag() { - mpu.Status.N = false mpu.A = 0x03 mpu.Y = 0x03 @@ -4553,14 +4091,12 @@ abstract class TestCommon6502 { assertEquals(0x83, mpu.A) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - - // ORA Zero Page, X - } + // ORA Zero Page, X + @Test fun test_ora_zp_x_indexed_zeroes_or_zeros_sets_z_flag() { - mpu.Status.Z = false mpu.A = 0x00 mpu.X = 0x03 @@ -4571,12 +4107,10 @@ abstract class TestCommon6502 { assertEquals(0x0002, mpu.PC) assertEquals(0x00, mpu.A) assertTrue(mpu.Status.Z) - } @Test fun test_ora_zp_x_indexed_turns_bits_on_sets_n_flag() { - mpu.Status.N = false mpu.A = 0x03 mpu.X = 0x03 @@ -4588,14 +4122,12 @@ abstract class TestCommon6502 { assertEquals(0x83, mpu.A) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - - // PHA - } + // PHA + @Test fun test_pha_pushes_a_and_updates_sp() { - mpu.A = 0xAB // $0000 PHA memory[0x0000] = 0x48 @@ -4607,6 +4139,7 @@ abstract class TestCommon6502 { } // PHP + @Test fun test_php_pushes_processor_status_and_updates_sp() { for (flags in 0 until 0x100) { @@ -4619,13 +4152,12 @@ abstract class TestCommon6502 { assertEquals(0xFC, mpu.SP) assertEquals((flags or fBREAK or fUNUSED), memory[0x1FD].toInt()) } - } // PLA + @Test fun test_pla_pulls_top_byte_from_stack_into_a_and_updates_sp() { - // $0000 PLA memory[0x0000] = 0x68 memory[0x01FF] = 0xAB @@ -4634,14 +4166,12 @@ abstract class TestCommon6502 { assertEquals(0x0001, mpu.PC) assertEquals(0xAB, mpu.A) assertEquals(0xFF, mpu.SP) - - // PLP - } + // PLP + @Test fun test_plp_pulls_top_byte_from_stack_into_flags_and_updates_sp() { - // $0000 PLP memory[0x0000] = 0x28 memory[0x01FF] = 0xBA // must have BREAK and UNUSED set @@ -4650,14 +4180,12 @@ abstract class TestCommon6502 { assertEquals(0x0001, mpu.PC) assertEquals(0xBA, mpu.Status.asByte()) assertEquals(0xFF, mpu.SP) - - // ROL Accumulator - } + // ROL Accumulator + @Test fun test_rol_accumulator_zero_and_carry_zero_sets_z_flag() { - mpu.A = 0x00 mpu.Status.C = false // $0000 ROL A @@ -4667,12 +4195,10 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.A) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_rol_accumulator_80_and_carry_zero_sets_z_flag() { - mpu.A = 0x80 mpu.Status.C = false mpu.Status.Z = false @@ -4687,7 +4213,6 @@ abstract class TestCommon6502 { @Test fun test_rol_accumulator_zero_and_carry_one_clears_z_flag() { - mpu.A = 0x00 mpu.Status.C = true // $0000 ROL A @@ -4697,12 +4222,10 @@ abstract class TestCommon6502 { assertEquals(0x01, mpu.A) assertFalse(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_rol_accumulator_sets_n_flag() { - mpu.A = 0x40 mpu.Status.C = true // $0000 ROL A @@ -4712,12 +4235,10 @@ abstract class TestCommon6502 { assertEquals(0x81, mpu.A) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_rol_accumulator_shifts_out_zero() { - mpu.A = 0x7F mpu.Status.C = false // $0000 ROL A @@ -4726,12 +4247,10 @@ abstract class TestCommon6502 { assertEquals(0x0001, mpu.PC) assertEquals(0xFE, mpu.A) assertFalse(mpu.Status.C) - } @Test fun test_rol_accumulator_shifts_out_one() { - mpu.A = 0xFF mpu.Status.C = false // $0000 ROL A @@ -4740,14 +4259,12 @@ abstract class TestCommon6502 { assertEquals(0x0001, mpu.PC) assertEquals(0xFE, mpu.A) assertTrue(mpu.Status.C) - - // ROL Absolute - } + // ROL Absolute + @Test fun test_rol_absolute_zero_and_carry_zero_sets_z_flag() { - mpu.Status.C = false // $0000 ROL $ABCD writeMem(memory, 0x0000, listOf(0x2E, 0xCD, 0xAB)) @@ -4757,12 +4274,10 @@ abstract class TestCommon6502 { assertEquals(0x00, memory[0xABCD]) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_rol_absolute_80_and_carry_zero_sets_z_flag() { - mpu.Status.C = false mpu.Status.Z = false // $0000 ROL $ABCD @@ -4773,12 +4288,10 @@ abstract class TestCommon6502 { assertEquals(0x00, memory[0xABCD]) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_rol_absolute_zero_and_carry_one_clears_z_flag() { - mpu.A = 0x00 mpu.Status.C = true // $0000 ROL $ABCD @@ -4789,12 +4302,10 @@ abstract class TestCommon6502 { assertEquals(0x01, memory[0xABCD]) assertFalse(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_rol_absolute_sets_n_flag() { - mpu.Status.C = true // $0000 ROL $ABCD writeMem(memory, 0x0000, listOf(0x2E, 0xCD, 0xAB)) @@ -4804,12 +4315,10 @@ abstract class TestCommon6502 { assertEquals(0x81, memory[0xABCD]) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_rol_absolute_shifts_out_zero() { - mpu.Status.C = false // $0000 ROL $ABCD writeMem(memory, 0x0000, listOf(0x2E, 0xCD, 0xAB)) @@ -4818,12 +4327,10 @@ abstract class TestCommon6502 { assertEquals(0x0003, mpu.PC) assertEquals(0xFE, memory[0xABCD]) assertFalse(mpu.Status.C) - } @Test fun test_rol_absolute_shifts_out_one() { - mpu.Status.C = false // $0000 ROL $ABCD writeMem(memory, 0x0000, listOf(0x2E, 0xCD, 0xAB)) @@ -4832,14 +4339,12 @@ abstract class TestCommon6502 { assertEquals(0x0003, mpu.PC) assertEquals(0xFE, memory[0xABCD]) assertTrue(mpu.Status.C) - - // ROL Zero Page - } + // ROL Zero Page + @Test fun test_rol_zp_zero_and_carry_zero_sets_z_flag() { - mpu.Status.C = false // $0000 ROL $0010 writeMem(memory, 0x0000, listOf(0x26, 0x10)) @@ -4849,12 +4354,10 @@ abstract class TestCommon6502 { assertEquals(0x00, memory[0x0010]) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_rol_zp_80_and_carry_zero_sets_z_flag() { - mpu.Status.C = false mpu.Status.Z = false // $0000 ROL $0010 @@ -4865,12 +4368,10 @@ abstract class TestCommon6502 { assertEquals(0x00, memory[0x0010]) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_rol_zp_zero_and_carry_one_clears_z_flag() { - mpu.A = 0x00 mpu.Status.C = true // $0000 ROL $0010 @@ -4881,12 +4382,10 @@ abstract class TestCommon6502 { assertEquals(0x01, memory[0x0010]) assertFalse(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_rol_zp_sets_n_flag() { - mpu.Status.C = true // $0000 ROL $0010 writeMem(memory, 0x0000, listOf(0x26, 0x10)) @@ -4896,12 +4395,10 @@ abstract class TestCommon6502 { assertEquals(0x81, memory[0x0010]) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_rol_zp_shifts_out_zero() { - mpu.Status.C = false // $0000 ROL $0010 writeMem(memory, 0x0000, listOf(0x26, 0x10)) @@ -4910,12 +4407,10 @@ abstract class TestCommon6502 { assertEquals(0x0002, mpu.PC) assertEquals(0xFE, memory[0x0010]) assertFalse(mpu.Status.C) - } @Test fun test_rol_zp_shifts_out_one() { - mpu.Status.C = false // $0000 ROL $0010 writeMem(memory, 0x0000, listOf(0x26, 0x10)) @@ -4924,14 +4419,12 @@ abstract class TestCommon6502 { assertEquals(0x0002, mpu.PC) assertEquals(0xFE, memory[0x0010]) assertTrue(mpu.Status.C) - - // ROL Absolute, X-Indexed - } + // ROL Absolute, X-Indexed + @Test fun test_rol_abs_x_indexed_zero_and_carry_zero_sets_z_flag() { - mpu.Status.C = false mpu.X = 0x03 // $0000 ROL $ABCD,X @@ -4942,12 +4435,10 @@ abstract class TestCommon6502 { assertEquals(0x00, memory[0xABCD + mpu.X]) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_rol_abs_x_indexed_80_and_carry_zero_sets_z_flag() { - mpu.Status.C = false mpu.Status.Z = false mpu.X = 0x03 @@ -4959,12 +4450,10 @@ abstract class TestCommon6502 { assertEquals(0x00, memory[0xABCD + mpu.X]) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_rol_abs_x_indexed_zero_and_carry_one_clears_z_flag() { - mpu.X = 0x03 mpu.Status.C = true // $0000 ROL $ABCD,X @@ -4975,12 +4464,10 @@ abstract class TestCommon6502 { assertEquals(0x01, memory[0xABCD + mpu.X]) assertFalse(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_rol_abs_x_indexed_sets_n_flag() { - mpu.X = 0x03 mpu.Status.C = true // $0000 ROL $ABCD,X @@ -4991,12 +4478,10 @@ abstract class TestCommon6502 { assertEquals(0x81, memory[0xABCD + mpu.X]) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_rol_abs_x_indexed_shifts_out_zero() { - mpu.X = 0x03 mpu.Status.C = false // $0000 ROL $ABCD,X @@ -5006,12 +4491,10 @@ abstract class TestCommon6502 { assertEquals(0x0003, mpu.PC) assertEquals(0xFE, memory[0xABCD + mpu.X]) assertFalse(mpu.Status.C) - } @Test fun test_rol_abs_x_indexed_shifts_out_one() { - mpu.X = 0x03 mpu.Status.C = false // $0000 ROL $ABCD,X @@ -5021,14 +4504,12 @@ abstract class TestCommon6502 { assertEquals(0x0003, mpu.PC) assertEquals(0xFE, memory[0xABCD + mpu.X]) assertTrue(mpu.Status.C) - - // ROL Zero Page, X-Indexed - } + // ROL Zero Page, X-Indexed + @Test fun test_rol_zp_x_indexed_zero_and_carry_zero_sets_z_flag() { - mpu.Status.C = false mpu.X = 0x03 writeMem(memory, 0x0000, listOf(0x36, 0x10)) @@ -5039,12 +4520,10 @@ abstract class TestCommon6502 { assertEquals(0x00, memory[0x0010 + mpu.X]) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_rol_zp_x_indexed_80_and_carry_zero_sets_z_flag() { - mpu.Status.C = false mpu.Status.Z = false mpu.X = 0x03 @@ -5056,12 +4535,10 @@ abstract class TestCommon6502 { assertEquals(0x00, memory[0x0010 + mpu.X]) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_rol_zp_x_indexed_zero_and_carry_one_clears_z_flag() { - mpu.X = 0x03 mpu.Status.C = true writeMem(memory, 0x0000, listOf(0x36, 0x10)) @@ -5072,12 +4549,10 @@ abstract class TestCommon6502 { assertEquals(0x01, memory[0x0010 + mpu.X]) assertFalse(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_rol_zp_x_indexed_sets_n_flag() { - mpu.X = 0x03 mpu.Status.C = true // $0000 ROL $0010,X @@ -5088,12 +4563,10 @@ abstract class TestCommon6502 { assertEquals(0x81, memory[0x0010 + mpu.X]) assertTrue(mpu.Status.N) assertFalse(mpu.Status.Z) - } @Test fun test_rol_zp_x_indexed_shifts_out_zero() { - mpu.X = 0x03 mpu.Status.C = false // $0000 ROL $0010,X @@ -5103,12 +4576,10 @@ abstract class TestCommon6502 { assertEquals(0x0002, mpu.PC) assertEquals(0xFE, memory[0x0010 + mpu.X]) assertFalse(mpu.Status.C) - } @Test fun test_rol_zp_x_indexed_shifts_out_one() { - mpu.X = 0x03 mpu.Status.C = false // $0000 ROL $0010,X @@ -5118,14 +4589,12 @@ abstract class TestCommon6502 { assertEquals(0x0002, mpu.PC) assertEquals(0xFE, memory[0x0010 + mpu.X]) assertTrue(mpu.Status.C) - - // ROR Accumulator - } + // ROR Accumulator + @Test fun test_ror_accumulator_zero_and_carry_zero_sets_z_flag() { - mpu.A = 0x00 mpu.Status.C = false // $0000 ROR A @@ -5135,12 +4604,10 @@ abstract class TestCommon6502 { assertEquals(0x00, mpu.A) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_ror_accumulator_zero_and_carry_one_rotates_in_sets_n_flags() { - mpu.A = 0x00 mpu.Status.C = true // $0000 ROR A @@ -5150,12 +4617,10 @@ abstract class TestCommon6502 { assertEquals(0x80, mpu.A) assertFalse(mpu.Status.Z) assertTrue(mpu.Status.N) - } @Test fun test_ror_accumulator_shifts_out_zero() { - mpu.A = 0x02 mpu.Status.C = true // $0000 ROR A @@ -5164,12 +4629,10 @@ abstract class TestCommon6502 { assertEquals(0x0001, mpu.PC) assertEquals(0x81, mpu.A) assertFalse(mpu.Status.C) - } @Test fun test_ror_accumulator_shifts_out_one() { - mpu.A = 0x03 mpu.Status.C = true // $0000 ROR A @@ -5178,14 +4641,12 @@ abstract class TestCommon6502 { assertEquals(0x0001, mpu.PC) assertEquals(0x81, mpu.A) assertTrue(mpu.Status.C) - - // ROR Absolute - } + // ROR Absolute + @Test fun test_ror_absolute_zero_and_carry_zero_sets_z_flag() { - mpu.Status.C = false // $0000 ROR $ABCD writeMem(memory, 0x0000, listOf(0x6E, 0xCD, 0xAB)) @@ -5195,12 +4656,10 @@ abstract class TestCommon6502 { assertEquals(0x00, memory[0xABCD]) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_ror_absolute_zero_and_carry_one_rotates_in_sets_n_flags() { - mpu.Status.C = true // $0000 ROR $ABCD writeMem(memory, 0x0000, listOf(0x6E, 0xCD, 0xAB)) @@ -5210,12 +4669,10 @@ abstract class TestCommon6502 { assertEquals(0x80, memory[0xABCD]) assertFalse(mpu.Status.Z) assertTrue(mpu.Status.N) - } @Test fun test_ror_absolute_shifts_out_zero() { - mpu.Status.C = true // $0000 ROR $ABCD writeMem(memory, 0x0000, listOf(0x6E, 0xCD, 0xAB)) @@ -5224,12 +4681,10 @@ abstract class TestCommon6502 { assertEquals(0x0003, mpu.PC) assertEquals(0x81, memory[0xABCD]) assertFalse(mpu.Status.C) - } @Test fun test_ror_absolute_shifts_out_one() { - mpu.Status.C = true // $0000 ROR $ABCD writeMem(memory, 0x0000, listOf(0x6E, 0xCD, 0xAB)) @@ -5238,14 +4693,12 @@ abstract class TestCommon6502 { assertEquals(0x0003, mpu.PC) assertEquals(0x81, memory[0xABCD]) assertTrue(mpu.Status.C) - - // ROR Zero Page - } + // ROR Zero Page + @Test fun test_ror_zp_zero_and_carry_zero_sets_z_flag() { - mpu.Status.C = false // $0000 ROR $0010 writeMem(memory, 0x0000, listOf(0x66, 0x10)) @@ -5255,12 +4708,10 @@ abstract class TestCommon6502 { assertEquals(0x00, memory[0x0010]) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_ror_zp_zero_and_carry_one_rotates_in_sets_n_flags() { - mpu.Status.C = true // $0000 ROR $0010 writeMem(memory, 0x0000, listOf(0x66, 0x10)) @@ -5270,12 +4721,10 @@ abstract class TestCommon6502 { assertEquals(0x80, memory[0x0010]) assertFalse(mpu.Status.Z) assertTrue(mpu.Status.N) - } @Test fun test_ror_zp_zero_absolute_shifts_out_zero() { - mpu.Status.C = true // $0000 ROR $0010 writeMem(memory, 0x0000, listOf(0x66, 0x10)) @@ -5284,12 +4733,10 @@ abstract class TestCommon6502 { assertEquals(0x0002, mpu.PC) assertEquals(0x81, memory[0x0010]) assertFalse(mpu.Status.C) - } @Test fun test_ror_zp_shifts_out_one() { - mpu.Status.C = true // $0000 ROR $0010 writeMem(memory, 0x0000, listOf(0x66, 0x10)) @@ -5298,14 +4745,12 @@ abstract class TestCommon6502 { assertEquals(0x0002, mpu.PC) assertEquals(0x81, memory[0x0010]) assertTrue(mpu.Status.C) - - // ROR Absolute, X-Indexed - } + // ROR Absolute, X-Indexed + @Test fun test_ror_abs_x_indexed_zero_and_carry_zero_sets_z_flag() { - mpu.X = 0x03 mpu.Status.C = false // $0000 ROR $ABCD,X @@ -5316,12 +4761,10 @@ abstract class TestCommon6502 { assertEquals(0x00, memory[0xABCD + mpu.X]) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_ror_abs_x_indexed_z_and_c_1_rotates_in_sets_n_flags() { - mpu.X = 0x03 mpu.Status.C = true // $0000 ROR $ABCD,X @@ -5332,12 +4775,10 @@ abstract class TestCommon6502 { assertEquals(0x80, memory[0xABCD + mpu.X]) assertFalse(mpu.Status.Z) assertTrue(mpu.Status.N) - } @Test fun test_ror_abs_x_indexed_shifts_out_zero() { - mpu.X = 0x03 mpu.Status.C = true // $0000 ROR $ABCD,X @@ -5347,12 +4788,10 @@ abstract class TestCommon6502 { assertEquals(0x0003, mpu.PC) assertEquals(0x81, memory[0xABCD + mpu.X]) assertFalse(mpu.Status.C) - } @Test fun test_ror_abs_x_indexed_shifts_out_one() { - mpu.X = 0x03 mpu.Status.C = true // $0000 ROR $ABCD,X @@ -5362,14 +4801,12 @@ abstract class TestCommon6502 { assertEquals(0x0003, mpu.PC) assertEquals(0x81, memory[0xABCD + mpu.X]) assertTrue(mpu.Status.C) - - // ROR Zero Page, X-Indexed - } + // ROR Zero Page, X-Indexed + @Test fun test_ror_zp_x_indexed_zero_and_carry_zero_sets_z_flag() { - mpu.X = 0x03 mpu.Status.C = false // $0000 ROR $0010,X @@ -5380,12 +4817,10 @@ abstract class TestCommon6502 { assertEquals(0x00, memory[0x0010 + mpu.X]) assertTrue(mpu.Status.Z) assertFalse(mpu.Status.N) - } @Test fun test_ror_zp_x_indexed_zero_and_carry_one_rotates_in_sets_n_flags() { - mpu.X = 0x03 mpu.Status.C = true // $0000 ROR $0010,X @@ -5396,12 +4831,10 @@ abstract class TestCommon6502 { assertEquals(0x80, memory[0x0010 + mpu.X]) assertFalse(mpu.Status.Z) assertTrue(mpu.Status.N) - } @Test fun test_ror_zp_x_indexed_zero_absolute_shifts_out_zero() { - mpu.X = 0x03 mpu.Status.C = true // $0000 ROR $0010,X @@ -5411,12 +4844,10 @@ abstract class TestCommon6502 { assertEquals(0x0002, mpu.PC) assertEquals(0x81, memory[0x0010 + mpu.X]) assertFalse(mpu.Status.C) - } @Test fun test_ror_zp_x_indexed_shifts_out_one() { - mpu.X = 0x03 mpu.Status.C = true // $0000 ROR $0010,X @@ -5426,19 +4857,16 @@ abstract class TestCommon6502 { assertEquals(0x0002, mpu.PC) assertEquals(0x81, memory[0x0010 + mpu.X]) assertTrue(mpu.Status.C) - - // RTI - } + // RTI + @Test fun test_rti_restores_status_and_pc_and_updates_sp() { - // $0000 RTI memory[0x0000] = 0x40 writeMem(memory, 0x01FD, listOf(0xFC, 0x03, 0xC0)) // Status, PCL, PCH mpu.SP = 0xFC - mpu.step() assertEquals(0xFF, mpu.SP) assertEquals(0xFC, mpu.Status.asByte()) @@ -5447,51 +4875,45 @@ abstract class TestCommon6502 { @Test fun test_rti_forces_break_and_unused_flags_high() { - // $0000 RTI memory[0x0000] = 0x40 writeMem(memory, 0x01FD, listOf(0x00, 0x03, 0xC0)) // Status, PCL, PCH mpu.SP = 0xFC - mpu.step() assertTrue(mpu.Status.B) // assertEquals(fUNUSED, mpu.Status.asByte().toInt() and fUNUSED) } // RTS + @Test fun test_rts_restores_pc_and_increments_then_updates_sp() { - // $0000 RTS memory[0x0000] = 0x60 writeMem(memory, 0x01FE, listOf(0x03, 0xC0)) // PCL, PCH mpu.PC = 0x0000 mpu.SP = 0xFD - mpu.step() assertEquals(0xC004, mpu.PC) assertEquals(0xFF, mpu.SP) - } @Test fun test_rts_wraps_around_top_of_memory() { - // $1000 RTS memory[0x1000] = 0x60 writeMem(memory, 0x01FE, listOf(0xFF, 0xFF)) // PCL, PCH mpu.PC = 0x1000 mpu.SP = 0xFD - mpu.step() assertEquals(0x0000, mpu.PC) assertEquals(0xFF, mpu.SP) } // SBC Absolute + @Test fun test_sbc_abs_all_zeros_and_no_borrow_is_zero() { - mpu.Status.D = false mpu.Status.C = true // borrow = 0 mpu.A = 0x00 @@ -5551,6 +4973,7 @@ abstract class TestCommon6502 { } // SBC Zero Page + @Test fun test_sbc_zp_all_zeros_and_no_borrow_is_zero() { mpu.Status.D = false @@ -5964,7 +5387,6 @@ abstract class TestCommon6502 { @Test fun test_sbc_ind_y_downto_zero_no_borrow_sets_z_clears_n() { - mpu.Status.D = false mpu.Status.C = true // borrow = 0 mpu.A = 0x01 @@ -5978,12 +5400,10 @@ abstract class TestCommon6502 { assertFalse(mpu.Status.N) assertTrue(mpu.Status.C) assertTrue(mpu.Status.Z) - } @Test fun test_sbc_ind_y_downto_zero_with_borrow_sets_z_clears_n() { - mpu.Status.D = false mpu.Status.C = false // borrow = 1 mpu.A = 0x01 @@ -5997,12 +5417,10 @@ abstract class TestCommon6502 { assertFalse(mpu.Status.N) assertTrue(mpu.Status.C) assertTrue(mpu.Status.Z) - } @Test fun test_sbc_ind_y_downto_four_with_borrow_clears_z_n() { - mpu.Status.D = false mpu.Status.C = false // borrow = 1 mpu.A = 0x07 @@ -6016,14 +5434,12 @@ abstract class TestCommon6502 { assertFalse(mpu.Status.N) assertFalse(mpu.Status.Z) assertTrue(mpu.Status.C) - - // SBC Zero Page, X-Indexed - } + // SBC Zero Page, X-Indexed + @Test fun test_sbc_zp_x_all_zeros_and_no_borrow_is_zero() { - mpu.Status.D = false mpu.Status.C = true // borrow = 0 mpu.A = 0x00 @@ -6036,12 +5452,10 @@ abstract class TestCommon6502 { assertFalse(mpu.Status.N) assertTrue(mpu.Status.C) assertTrue(mpu.Status.Z) - } @Test fun test_sbc_zp_x_downto_zero_no_borrow_sets_z_clears_n() { - mpu.Status.D = false mpu.Status.C = true // borrow = 0 mpu.A = 0x01 @@ -6054,12 +5468,10 @@ abstract class TestCommon6502 { assertFalse(mpu.Status.N) assertTrue(mpu.Status.C) assertTrue(mpu.Status.Z) - } @Test fun test_sbc_zp_x_downto_zero_with_borrow_sets_z_clears_n() { - mpu.Status.D = false mpu.Status.C = false // borrow = 1 mpu.A = 0x01 @@ -6072,12 +5484,10 @@ abstract class TestCommon6502 { assertFalse(mpu.Status.N) assertTrue(mpu.Status.C) assertTrue(mpu.Status.Z) - } @Test fun test_sbc_zp_x_downto_four_with_borrow_clears_z_n() { - mpu.Status.D = false mpu.Status.C = false // borrow = 1 mpu.A = 0x07 @@ -6090,28 +5500,24 @@ abstract class TestCommon6502 { assertFalse(mpu.Status.N) assertFalse(mpu.Status.Z) assertTrue(mpu.Status.C) - - // SEC - } + // SEC + @Test fun test_sec_sets_carry_flag() { - mpu.Status.C = false // $0000 SEC memory[0x0000] = 0x038 mpu.step() assertEquals(0x0001, mpu.PC) assertTrue(mpu.Status.C) - - // SED - } + // SED + @Test fun test_sed_sets_decimal_mode_flag() { - mpu.Status.D = false // $0000 SED memory[0x0000] = 0xF8 @@ -6136,7 +5542,6 @@ abstract class TestCommon6502 { @Test fun test_sta_absolute_stores_a_leaves_a_and_n_flag_unchanged() { - val flags = 0xFF and fNEGATIVE.inv() mpu.Status.fromByte(flags) mpu.A = 0xFF @@ -6148,12 +5553,10 @@ abstract class TestCommon6502 { assertEquals(0xFF, memory[0xABCD]) assertEquals(0xFF, mpu.A) assertEquals(flags, mpu.Status.asByte().toInt()) - } @Test fun test_sta_absolute_stores_a_leaves_a_and_z_flag_unchanged() { - val flags = 0xFF and fZERO.inv() mpu.Status.fromByte(flags) mpu.A = 0x00 @@ -6165,14 +5568,12 @@ abstract class TestCommon6502 { assertEquals(0x00, memory[0xABCD]) assertEquals(0x00, mpu.A) assertEquals(flags, mpu.Status.asByte().toInt()) - - // STA Zero Page - } + // STA Zero Page + @Test fun test_sta_zp_stores_a_leaves_a_and_n_flag_unchanged() { - val flags = 0xFF and fNEGATIVE.inv() mpu.Status.fromByte(flags) mpu.A = 0xFF @@ -6184,12 +5585,10 @@ abstract class TestCommon6502 { assertEquals(0xFF, memory[0x0010]) assertEquals(0xFF, mpu.A) assertEquals(flags, mpu.Status.asByte().toInt()) - } @Test fun test_sta_zp_stores_a_leaves_a_and_z_flag_unchanged() { - val flags = 0xFF and fZERO.inv() mpu.Status.fromByte(flags) mpu.A = 0x00 @@ -6201,14 +5600,12 @@ abstract class TestCommon6502 { assertEquals(0x00, memory[0x0010]) assertEquals(0x00, mpu.A) assertEquals(flags, mpu.Status.asByte().toInt()) - - // STA Absolute, X-Indexed - } + // STA Absolute, X-Indexed + @Test fun test_sta_abs_x_indexed_stores_a_leaves_a_and_n_flag_unchanged() { - val flags = 0xFF and fNEGATIVE.inv() mpu.Status.fromByte(flags) mpu.A = 0xFF @@ -6221,12 +5618,10 @@ abstract class TestCommon6502 { assertEquals(0xFF, memory[0xABCD + mpu.X]) assertEquals(0xFF, mpu.A) assertEquals(flags, mpu.Status.asByte().toInt()) - } @Test fun test_sta_abs_x_indexed_stores_a_leaves_a_and_z_flag_unchanged() { - val flags = 0xFF and fZERO.inv() mpu.Status.fromByte(flags) mpu.A = 0x00 @@ -6245,7 +5640,6 @@ abstract class TestCommon6502 { @Test fun test_sta_abs_y_indexed_stores_a_leaves_a_and_n_flag_unchanged() { - val flags = 0xFF and fNEGATIVE.inv() mpu.Status.fromByte(flags) mpu.A = 0xFF diff --git a/sim65/test/TestDisassembler.kt b/sim65/test/TestDisassembler.kt index c3bf26c73..3b5029c9f 100644 --- a/sim65/test/TestDisassembler.kt +++ b/sim65/test/TestDisassembler.kt @@ -8,7 +8,7 @@ class TestDisassembler { @Test fun testDisassembleAllOpcodes() { - val cpu = Cpu6502(true, true) + val cpu = Cpu6502(true) val memory = Ram(0, 0xffff) memory.load("test/testfiles/disassem_instr_test.prg", 0x1000 - 2) val result = cpu.disassemble(memory, 0x1000, 0x1221)