From 3412a03a5ec20e1d3fb5dbd38888cf0c0eae09fc Mon Sep 17 00:00:00 2001 From: vin Date: Mon, 10 Jun 2024 22:56:06 +0530 Subject: [PATCH] implement untested most of stack-related opcodes --- cpu.c | 127 +++++++++++++++++++++++++++------------------------------- 1 file changed, 59 insertions(+), 68 deletions(-) diff --git a/cpu.c b/cpu.c index 5bd114e..e63760c 100644 --- a/cpu.c +++ b/cpu.c @@ -10,6 +10,11 @@ #define STATUS_UPDATE_NEGATIVE(r) \ (regs.status.negative = ((r & (1 << 7)) > 0)) +#define PUSH(b) \ + (memwrite(0x0100 + regs.sp--, b)) +#define PULL() \ + (peek(0x0100 + regs.sp++)) + struct cpu_flags { uint8_t carry : 1; uint8_t zero : 1; @@ -467,51 +472,48 @@ ora(uint8_t arg) } static void -pha(uint8_t arg) +pha(void) { -/* TODO: complete this */ + PUSH(regs.a); } static void -php(uint8_t arg) +php(void) { -/* TODO: complete this */ + uint8_t status; + + status = (regs.status.carry << 7) | (regs.status.zero << 6) + | (regs.status.interrupt_disable << 5) | (regs.status.decimal_mode << 4) + | (regs.status.brk << 3) | (regs.status.unused << 2) + | (regs.status.overflow << 1) | regs.status.negative; + + PUSH(status); } static void -phx(uint8_t arg) +pla(void) { -/* TODO: complete this */ + regs.a = PULL(); + + STATUS_UPDATE_ZERO(regs.a); + STATUS_UPDATE_NEGATIVE(regs.a); } static void -phy(uint8_t arg) +plp(void) { -/* TODO: complete this */ -} + uint8_t status; -static void -pla(uint8_t arg) -{ -/* TODO: complete this */ -} + status = PULL(); -static void -plp(uint8_t arg) -{ -/* TODO: complete this */ -} - -static void -plx(uint8_t arg) -{ -/* TODO: complete this */ -} - -static void -ply(uint8_t arg) -{ -/* TODO: complete this */ + regs.status.carry = (status & (1 << 7)) > 0; + regs.status.zero = (status & (1 << 6)) > 0; + regs.status.interrupt_disable = (status & (1 << 5)) > 0; + regs.status.decimal_mode = (status & (1 << 4)) > 0; + regs.status.brk = (status & (1 << 3)) > 0; + regs.status.unused = (status & (1 << 2)) > 0; + regs.status.overflow = (status & (1 << 1)) > 0; + regs.status.negative = (status & 1) > 0; } static void @@ -562,19 +564,19 @@ sbc(uint8_t arg) } static void -sec(uint8_t arg) +sec(void) { regs.status.carry = 1; } static void -sed(uint8_t arg) +sed(void) { regs.status.decimal_mode = 1; } static void -sei(uint8_t arg) +sei(void) { regs.status.interrupt_disable = 1; } @@ -607,7 +609,7 @@ tax(void) } static void -tay(uint8_t arg) +tay(void) { regs.y = regs.a; @@ -616,13 +618,16 @@ tay(uint8_t arg) } static void -tsx(uint8_t arg) +tsx(void) { -/* TODO: complete this */ + regs.x = PULL(); + + STATUS_UPDATE_ZERO(regs.x); + STATUS_UPDATE_NEGATIVE(regs.x); } static void -txa(uint8_t arg) +txa(void) { regs.a = regs.x; @@ -631,13 +636,13 @@ txa(uint8_t arg) } static void -txs(uint8_t arg) +txs(void) { -/* TODO: complete this */ + PUSH(regs.x); } static void -tya(uint8_t arg) +tya(void) { regs.a = regs.y; @@ -1121,35 +1126,19 @@ interpret(void) cycles += 5; break; case 0x48: - pha(opcode_arg(AM_ACC)); + pha(); cycles += 3; break; case 0x08: - php(opcode_arg(AM_ACC)); - cycles += 3; - break; - case 0xda: - phx(opcode_arg(AM_ACC)); - cycles += 3; - break; - case 0x5a: - phy(opcode_arg(AM_ACC)); + php(); cycles += 3; break; case 0x68: - pla(opcode_arg(AM_ACC)); + pla(); cycles += 4; break; case 0x28: - plp(opcode_arg(AM_ACC)); - cycles += 4; - break; - case 0xfa: - plx(opcode_arg(AM_ACC)); - cycles += 4; - break; - case 0x7a: - ply(opcode_arg(AM_ACC)); + plp(); cycles += 4; break; case 0x2a: @@ -1237,15 +1226,15 @@ interpret(void) cycles += 5; break; case 0x38: - sec(opcode_arg(AM_ACC)); + sec(); cycles += 2; break; case 0xf8: - sed(opcode_arg(AM_ACC)); + sed(); cycles += 2; break; case 0x78: - sei(opcode_arg(AM_ACC)); + sei(); cycles += 2; break; case 0x85: @@ -1309,23 +1298,23 @@ interpret(void) cycles += 2; break; case 0xa8: - tay(opcode_arg(AM_ACC)); + tay(); cycles += 2; break; case 0xba: - tsx(opcode_arg(AM_ACC)); + tsx(); cycles += 2; break; case 0x8a: - txa(opcode_arg(AM_ACC)); + txa(); cycles += 2; break; case 0x9a: - txs(opcode_arg(AM_ACC)); + txs(); cycles += 2; break; case 0x98: - tya(opcode_arg(AM_ACC)); + tya(); cycles += 2; break; default: @@ -1353,6 +1342,8 @@ cpu_init(void) memset(®s.status, 0, sizeof(regs.status)); regs.status.unused = 1; + + cycles += 7; } int