From f107f4b23d1904ab23fb92a0cda5f54e6c19d145 Mon Sep 17 00:00:00 2001 From: Brad Grantham Date: Mon, 28 Nov 2016 13:27:52 -0800 Subject: [PATCH] More instructions and compatibility Fix ADC abs (was accidentally adding Y to address) Also handle bank switch registers on write Initialize CPU6502 registers to 0 to match fake6502 Avoid spurious differences Implement more instructions ADC (ind), Y ADC abs, X ORA zpg, X --- apple2e.cpp | 50 ++++++++++++++++++++++++++++++++++++++++++++++++-- 1 file changed, 48 insertions(+), 2 deletions(-) diff --git a/apple2e.cpp b/apple2e.cpp index 3491c13..40b88a9 100644 --- a/apple2e.cpp +++ b/apple2e.cpp @@ -568,6 +568,7 @@ struct MAINboard : board_base { keyboard_buffer.push_back(k); } + typedef std::function display_write_func; display_write_func display_write; typedef std::function audio_flush_func; @@ -781,6 +782,15 @@ struct MAINboard : board_base return true; } } + if((addr & 0xFFF0) == 0xC080) { + C08X_bank = ((addr >> 3) & 1) ? BANK1 : BANK2; + C08X_write_RAM = addr & 1; + int read_ROM = ((addr >> 1) & 1) ^ C08X_write_RAM; + C08X_read_RAM = !read_ROM; + if(debug & DEBUG_SWITCH) printf("write %04X switch, %s, %d write_RAM, %d read_RAM\n", addr, (C08X_bank == BANK1) ? "BANK1" : "BANK2", C08X_write_RAM, C08X_read_RAM); + data = 0x00; + return true; + } if(addr == 0xC010) { if(debug & DEBUG_RW) printf("write KBDSTRB\n"); if(!keyboard_buffer.empty()) { @@ -902,6 +912,10 @@ struct CPU6502 } exception; CPU6502(system_clock& clk_) : clk(clk_), + a(0), + x(0), + y(0), + s(0), p(0x20), exception(RESET) { @@ -1408,8 +1422,21 @@ struct CPU6502 break; } + case 0x71: { // ADC (ind), Y + unsigned char zpg = read_pc_inc(bus); + int addr = bus.read(zpg) + bus.read((zpg + 1) & 0xFF) * 256 + y; + if((addr - y) / 256 != addr / 256) + clk++; + m = bus.read(addr); + int carry = isset(C) ? 1 : 0; + flag_change(C, (int)(a + m + carry) > 0xFF); + flag_change(V, adc_overflow(a, m, carry)); + set_flags(N | Z, a = a + m + carry); + break; + } + case 0x6D: { // ADC abs - int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256 + y; + int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256; m = bus.read(addr); int carry = isset(C) ? 1 : 0; flag_change(C, (int)(a + m + carry) > 0xFF); @@ -1428,6 +1455,18 @@ struct CPU6502 break; } + case 0x7D: { // ADC abs, X + int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256 + x; + if((addr - x) / 256 != addr / 256) + clk++; + m = bus.read(addr); + int carry = isset(C) ? 1 : 0; + flag_change(C, (int)(a + m + carry) > 0xFF); + flag_change(V, adc_overflow(a, m, carry)); + set_flags(N | Z, a = a + m + carry); + break; + } + case 0x79: { // ADC abs, Y int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256 + y; if((addr - y) / 256 != addr / 256) @@ -1534,6 +1573,13 @@ struct CPU6502 break; } + case 0x15: { // ORA zpg, X + int zpg = (read_pc_inc(bus) + x) & 0xFF; + m = bus.read(zpg); + set_flags(N | Z, a = a | m); + break; + } + case 0x0D: { // ORA abs int addr = read_pc_inc(bus) + read_pc_inc(bus) * 256; m = bus.read(addr); @@ -2030,7 +2076,7 @@ void cleanup(void) fflush(stderr); } -bool use_fake6502 = true; +bool use_fake6502 = false; string read_bus_and_disassemble(bus_frontend &bus, int pc) {