summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorvin <git@vineetk.net>2024-06-10 22:56:06 +0530
committervin <git@vineetk.net>2024-06-10 23:27:11 +0530
commit3412a03a5ec20e1d3fb5dbd38888cf0c0eae09fc (patch)
tree4b2a01e16a25a1887d4a4c64039e25c975c4e38a
parentdbb952a52b1b7168b4d1e98e9819d632ad16e087 (diff)
implement untested most of stack-related opcodes
-rw-r--r--cpu.c123
1 files changed, 57 insertions, 66 deletions
diff --git a/cpu.c b/cpu.c
index 5bd114e..e63760c 100644
--- a/cpu.c
+++ b/cpu.c
@@ -10,6 +10,11 @@
10#define STATUS_UPDATE_NEGATIVE(r) \ 10#define STATUS_UPDATE_NEGATIVE(r) \
11 (regs.status.negative = ((r & (1 << 7)) > 0)) 11 (regs.status.negative = ((r & (1 << 7)) > 0))
12 12
13#define PUSH(b) \
14 (memwrite(0x0100 + regs.sp--, b))
15#define PULL() \
16 (peek(0x0100 + regs.sp++))
17
13struct cpu_flags { 18struct cpu_flags {
14 uint8_t carry : 1; 19 uint8_t carry : 1;
15 uint8_t zero : 1; 20 uint8_t zero : 1;
@@ -467,51 +472,48 @@ ora(uint8_t arg)
467} 472}
468 473
469static void 474static void
470pha(uint8_t arg) 475pha(void)
471{ 476{
472/* TODO: complete this */ 477 PUSH(regs.a);
473} 478}
474 479
475static void 480static void
476php(uint8_t arg) 481php(void)
477{ 482{
478/* TODO: complete this */ 483 uint8_t status;
479}
480 484
481static void 485 status = (regs.status.carry << 7) | (regs.status.zero << 6)
482phx(uint8_t arg) 486 | (regs.status.interrupt_disable << 5) | (regs.status.decimal_mode << 4)
483{ 487 | (regs.status.brk << 3) | (regs.status.unused << 2)
484/* TODO: complete this */ 488 | (regs.status.overflow << 1) | regs.status.negative;
485}
486 489
487static void 490 PUSH(status);
488phy(uint8_t arg)
489{
490/* TODO: complete this */
491} 491}
492 492
493static void 493static void
494pla(uint8_t arg) 494pla(void)
495{ 495{
496/* TODO: complete this */ 496 regs.a = PULL();
497}
498 497
499static void 498 STATUS_UPDATE_ZERO(regs.a);
500plp(uint8_t arg) 499 STATUS_UPDATE_NEGATIVE(regs.a);
501{
502/* TODO: complete this */
503} 500}
504 501
505static void 502static void
506plx(uint8_t arg) 503plp(void)
507{ 504{
508/* TODO: complete this */ 505 uint8_t status;
509}
510 506
511static void 507 status = PULL();
512ply(uint8_t arg) 508
513{ 509 regs.status.carry = (status & (1 << 7)) > 0;
514/* TODO: complete this */ 510 regs.status.zero = (status & (1 << 6)) > 0;
511 regs.status.interrupt_disable = (status & (1 << 5)) > 0;
512 regs.status.decimal_mode = (status & (1 << 4)) > 0;
513 regs.status.brk = (status & (1 << 3)) > 0;
514 regs.status.unused = (status & (1 << 2)) > 0;
515 regs.status.overflow = (status & (1 << 1)) > 0;
516 regs.status.negative = (status & 1) > 0;
515} 517}
516 518
517static void 519static void
@@ -562,19 +564,19 @@ sbc(uint8_t arg)
562} 564}
563 565
564static void 566static void
565sec(uint8_t arg) 567sec(void)
566{ 568{
567 regs.status.carry = 1; 569 regs.status.carry = 1;
568} 570}
569 571
570static void 572static void
571sed(uint8_t arg) 573sed(void)
572{ 574{
573 regs.status.decimal_mode = 1; 575 regs.status.decimal_mode = 1;
574} 576}
575 577
576static void 578static void
577sei(uint8_t arg) 579sei(void)
578{ 580{
579 regs.status.interrupt_disable = 1; 581 regs.status.interrupt_disable = 1;
580} 582}
@@ -607,7 +609,7 @@ tax(void)
607} 609}
608 610
609static void 611static void
610tay(uint8_t arg) 612tay(void)
611{ 613{
612 regs.y = regs.a; 614 regs.y = regs.a;
613 615
@@ -616,13 +618,16 @@ tay(uint8_t arg)
616} 618}
617 619
618static void 620static void
619tsx(uint8_t arg) 621tsx(void)
620{ 622{
621/* TODO: complete this */ 623 regs.x = PULL();
624
625 STATUS_UPDATE_ZERO(regs.x);
626 STATUS_UPDATE_NEGATIVE(regs.x);
622} 627}
623 628
624static void 629static void
625txa(uint8_t arg) 630txa(void)
626{ 631{
627 regs.a = regs.x; 632 regs.a = regs.x;
628 633
@@ -631,13 +636,13 @@ txa(uint8_t arg)
631} 636}
632 637
633static void 638static void
634txs(uint8_t arg) 639txs(void)
635{ 640{
636/* TODO: complete this */ 641 PUSH(regs.x);
637} 642}
638 643
639static void 644static void
640tya(uint8_t arg) 645tya(void)
641{ 646{
642 regs.a = regs.y; 647 regs.a = regs.y;
643 648
@@ -1121,35 +1126,19 @@ interpret(void)
1121 cycles += 5; 1126 cycles += 5;
1122 break; 1127 break;
1123 case 0x48: 1128 case 0x48:
1124 pha(opcode_arg(AM_ACC)); 1129 pha();
1125 cycles += 3; 1130 cycles += 3;
1126 break; 1131 break;
1127 case 0x08: 1132 case 0x08:
1128 php(opcode_arg(AM_ACC)); 1133 php();
1129 cycles += 3;
1130 break;
1131 case 0xda:
1132 phx(opcode_arg(AM_ACC));
1133 cycles += 3;
1134 break;
1135 case 0x5a:
1136 phy(opcode_arg(AM_ACC));
1137 cycles += 3; 1134 cycles += 3;
1138 break; 1135 break;
1139 case 0x68: 1136 case 0x68:
1140 pla(opcode_arg(AM_ACC)); 1137 pla();
1141 cycles += 4; 1138 cycles += 4;
1142 break; 1139 break;
1143 case 0x28: 1140 case 0x28:
1144 plp(opcode_arg(AM_ACC)); 1141 plp();
1145 cycles += 4;
1146 break;
1147 case 0xfa:
1148 plx(opcode_arg(AM_ACC));
1149 cycles += 4;
1150 break;
1151 case 0x7a:
1152 ply(opcode_arg(AM_ACC));
1153 cycles += 4; 1142 cycles += 4;
1154 break; 1143 break;
1155 case 0x2a: 1144 case 0x2a:
@@ -1237,15 +1226,15 @@ interpret(void)
1237 cycles += 5; 1226 cycles += 5;
1238 break; 1227 break;
1239 case 0x38: 1228 case 0x38:
1240 sec(opcode_arg(AM_ACC)); 1229 sec();
1241 cycles += 2; 1230 cycles += 2;
1242 break; 1231 break;
1243 case 0xf8: 1232 case 0xf8:
1244 sed(opcode_arg(AM_ACC)); 1233 sed();
1245 cycles += 2; 1234 cycles += 2;
1246 break; 1235 break;
1247 case 0x78: 1236 case 0x78:
1248 sei(opcode_arg(AM_ACC)); 1237 sei();
1249 cycles += 2; 1238 cycles += 2;
1250 break; 1239 break;
1251 case 0x85: 1240 case 0x85:
@@ -1309,23 +1298,23 @@ interpret(void)
1309 cycles += 2; 1298 cycles += 2;
1310 break; 1299 break;
1311 case 0xa8: 1300 case 0xa8:
1312 tay(opcode_arg(AM_ACC)); 1301 tay();
1313 cycles += 2; 1302 cycles += 2;
1314 break; 1303 break;
1315 case 0xba: 1304 case 0xba:
1316 tsx(opcode_arg(AM_ACC)); 1305 tsx();
1317 cycles += 2; 1306 cycles += 2;
1318 break; 1307 break;
1319 case 0x8a: 1308 case 0x8a:
1320 txa(opcode_arg(AM_ACC)); 1309 txa();
1321 cycles += 2; 1310 cycles += 2;
1322 break; 1311 break;
1323 case 0x9a: 1312 case 0x9a:
1324 txs(opcode_arg(AM_ACC)); 1313 txs();
1325 cycles += 2; 1314 cycles += 2;
1326 break; 1315 break;
1327 case 0x98: 1316 case 0x98:
1328 tya(opcode_arg(AM_ACC)); 1317 tya();
1329 cycles += 2; 1318 cycles += 2;
1330 break; 1319 break;
1331 default: 1320 default:
@@ -1353,6 +1342,8 @@ cpu_init(void)
1353 1342
1354 memset(&regs.status, 0, sizeof(regs.status)); 1343 memset(&regs.status, 0, sizeof(regs.status));
1355 regs.status.unused = 1; 1344 regs.status.unused = 1;
1345
1346 cycles += 7;
1356} 1347}
1357 1348
1358int 1349int