From c034141ee5cab2a16c6c4bf4dbde7ab2fbb4ba34 Mon Sep 17 00:00:00 2001 From: jborza Date: Sun, 14 Apr 2019 23:05:37 +0200 Subject: [PATCH] STX, STY + tests --- cpu.c | 50 ++++++++++++---- emu6502.vcxproj | 8 +-- test6502.c | 151 +++++++++++++++++++++++++++++++++++++++++++++--- 3 files changed, 186 insertions(+), 23 deletions(-) diff --git a/cpu.c b/cpu.c index a8a3be2..52c295b 100644 --- a/cpu.c +++ b/cpu.c @@ -68,6 +68,14 @@ void LDY(State6502* state, byte operand) { set_NV_flags(state, state->y); } +void STX(State6502* state, word address) { + state->memory[address] = state->x; +} + +void STY(State6502* state, word address) { + state->memory[address] = state->y; +} + word pop_word(State6502* state) { byte low = pop_byte(state); byte high = pop_byte(state); @@ -79,27 +87,47 @@ word read_word(State6502 * state, word address) { return state->memory[address] | state->memory[address + 1] << 8; } +word get_address_zero_page(State6502* state) { + return pop_byte(state); +} + byte get_byte_zero_page(State6502 * state) { //8 bit addressing, only the first 256 bytes of the memory byte address = pop_byte(state); return state->memory[address]; } +word get_address_zero_page_x(State6502* state) { + //address is zero page, so wraparound byte + byte address = pop_byte(state) + state->x; + return address; +} + byte get_byte_zero_page_x(State6502 * state) { byte address = pop_byte(state) + state->x; return state->memory[address]; } -byte get_byte_zero_page_y(State6502 * state) { +word get_address_zero_page_y(State6502* state) { + //address is zero page, so wraparound byte byte address = pop_byte(state) + state->y; - return state->memory[address]; + return address; +} + +byte get_byte_zero_page_y(State6502 * state) { + return state->memory[get_address_zero_page_y(state)]; +} + +word get_address_absolute(State6502 * state) { + //absolute indexed, 16 bits + word address = pop_word(state); + return address; } byte get_byte_absolute(State6502 * state) { //absolute indexed, 16 bits - word address = pop_word(state); - return state->memory[address]; + return state->memory[get_address_absolute(state)]; } byte get_byte_absolute_x(State6502 * state) { @@ -284,14 +312,14 @@ int emulate_6502_op(State6502 * state) { case STA_ABS: unimplemented_instruction(state); break; case STA_ABSX: unimplemented_instruction(state); break; case STA_ABSY: unimplemented_instruction(state); break; - case STA_INDX: unimplemented_instruction(state); break; + case STA_INDX: unimplemented_instruction(state); break; case STA_INDY: unimplemented_instruction(state); break; - case STX_ZP: unimplemented_instruction(state); break; - case STX_ZPY: unimplemented_instruction(state); break; - case STX_ABS: unimplemented_instruction(state); break; - case STY_ZP: unimplemented_instruction(state); break; - case STY_ZPX: unimplemented_instruction(state); break; - case STY_ABS: unimplemented_instruction(state); break; + case STX_ZP: STX(state, get_address_zero_page(state)); break; + case STX_ZPY: STX(state, get_address_zero_page_y(state)); break; + case STX_ABS: STX(state, get_address_absolute(state)); break; + case STY_ZP: STY(state, get_address_zero_page(state)); break; + case STY_ZPX: STY(state, get_address_zero_page_x(state)); break; + case STY_ABS: STY(state, get_address_absolute(state)); break; default: unimplemented_instruction(state); break; diff --git a/emu6502.vcxproj b/emu6502.vcxproj index b7b79d1..a084356 100644 --- a/emu6502.vcxproj +++ b/emu6502.vcxproj @@ -89,7 +89,7 @@ Level3 Disabled true - WIN32;_CRT_SECURE_NO_WARNINGS;_DEBUG;_CONSOLE;%(PreprocessorDefinitions) + WIN32;_CRT_SECURE_NO_WARNINGS;_DEBUG;_CONSOLE;%(PreprocessorDefinitions);_CRT_SECURE_NO_WARNINGS true @@ -104,7 +104,7 @@ Level3 Disabled true - _DEBUG;_CONSOLE;%(PreprocessorDefinitions) + _DEBUG;_CONSOLE;%(PreprocessorDefinitions);_CRT_SECURE_NO_WARNINGS true @@ -121,7 +121,7 @@ true true true - WIN32;_CRT_SECURE_NO_WARNINGS;NDEBUG;_CONSOLE;%(PreprocessorDefinitions) + WIN32;_CRT_SECURE_NO_WARNINGS;NDEBUG;_CONSOLE;%(PreprocessorDefinitions);_CRT_SECURE_NO_WARNINGS true @@ -140,7 +140,7 @@ true true true - NDEBUG;_CONSOLE;%(PreprocessorDefinitions) + NDEBUG;_CONSOLE;%(PreprocessorDefinitions);_CRT_SECURE_NO_WARNINGS true diff --git a/test6502.c b/test6502.c index 6aaad01..fb8d0e9 100644 --- a/test6502.c +++ b/test6502.c @@ -75,6 +75,14 @@ void assertY(State6502* state, byte expected) { } } +//assert_memory(&state, 0xFF, 0x99) +void assert_memory(State6502* state, word address, byte expected) { + if (state->memory[address] != expected) { + printf("Unexpected value in $%04X, expected %02X, was %02X", address, expected, state->memory[address]); + exit(1); + } +} + //////////////////////////////////////// @@ -744,7 +752,7 @@ void test_LDY_ABS() { void test_LDY_ABSX() { //initialize State6502 state = create_blank_state(); - state.y = 0x02; + state.x = 0x02; //arrange char program[] = { LDY_ABSX, 0x01, 0x04 }; //LDY $0401,x @@ -761,6 +769,126 @@ void test_LDY_ABSX() { test_cleanup(&state); } +//// STX + +void test_STX_ZP() { + //initialize + State6502 state = create_blank_state(); + state.x = 0x99; + + //arrange + char program[] = { STX_ZP, 0xFF}; //STX $FF + memcpy(state.memory, program, sizeof(program)); + + //act + test_step(&state); + + //assert + assert_memory(&state, 0xFF, 0x99); + + //cleanup + test_cleanup(&state); +} + +void test_STX_ZPY() { + //initialize + State6502 state = create_blank_state(); + state.y = 0xA0; + state.x = 0x99; + + //arrange + char program[] = { STX_ZPY, 0x02}; //STX $02,Y + memcpy(state.memory, program, sizeof(program)); + + //act + test_step(&state); + + //assert + assert_memory(&state, 0xA2, 0x99); + + //cleanup + test_cleanup(&state); +} + +void test_STX_ABS() { + //initialize + State6502 state = create_blank_state(); + state.x = 0x99; + + //arrange + char program[] = { STX_ABS, 0x01, 0x04 }; //STX $0401 + memcpy(state.memory, program, sizeof(program)); + + //act + test_step(&state); + + //assert + assert_memory(&state, 0x401, 0x99); + + //cleanup + test_cleanup(&state); +} + +//// STY + +void test_STY_ZP() { + //initialize + State6502 state = create_blank_state(); + state.y = 0x99; + + //arrange + char program[] = { STY_ZP, 0xFF }; //STY $FF + memcpy(state.memory, program, sizeof(program)); + + //act + test_step(&state); + + //assert + assert_memory(&state, 0xFF, 0x99); + + //cleanup + test_cleanup(&state); +} + +void test_STY_ZPX() { + //initialize + State6502 state = create_blank_state(); + state.x = 0xA0; + state.y = 0x99; + + //arrange + char program[] = { STY_ZPX, 0x02 }; //STY $02,X + memcpy(state.memory, program, sizeof(program)); + + //act + test_step(&state); + + //assert + assert_memory(&state, 0xA2, 0x99); + + //cleanup + test_cleanup(&state); +} + +void test_STY_ABS() { + //initialize + State6502 state = create_blank_state(); + state.y = 0x99; + + //arrange + char program[] = { STY_ABS, 0x01, 0x04 }; //STY $0401 + memcpy(state.memory, program, sizeof(program)); + + //act + test_step(&state); + + //assert + assert_memory(&state, 0x401, 0x99); + + //cleanup + test_cleanup(&state); +} + ///////////////////// typedef void fp(); @@ -769,16 +897,23 @@ fp* tests_ora[] = { test_ORA_IMM, test_ORA_ZP, test_ORA_ZPX, test_ORA_ABS, test_ fp* tests_and[] = { test_AND_IMM, test_AND_ZP, test_AND_ZPX, test_AND_ABS, test_AND_ABSX, test_AND_ABSY, test_AND_INDX, test_AND_INDY }; fp* tests_ldx[] = { test_LDX_IMM, test_LDX_ZP, test_LDX_ZPY, test_LDX_ABS, test_LDX_ABSY }; fp* tests_ldy[] = { test_LDY_IMM, test_LDY_ZP, test_LDY_ZPX, test_LDY_ABS, test_LDY_ABSX }; +fp* tests_stx[] = { test_STX_ZP, test_STX_ZPY, test_STX_ABS}; +fp* tests_sty[] = { test_STY_ZP, test_STY_ZPX, test_STY_ABS }; -void run_suite(fp* suite[]) { - for (int i = 0; i < sizeof(suite) / sizeof(fp*); i++) +#define RUN(suite) run_suite(suite, sizeof(suite)/sizeof(fp*)) + +void run_suite(fp** suite, int size) { + for (int i = 0; i < size; i++) suite[i](); } void run_tests() { - run_suite(tests_lda); - run_suite(tests_ora); - run_suite(tests_and); - run_suite(tests_ldx); - run_suite(tests_ldy); + RUN(tests_lda); + RUN(tests_ora); + RUN(tests_and); + RUN(tests_ldx); + RUN(tests_lda); + RUN(tests_ldy); + RUN(tests_stx); + RUN(tests_sty); } \ No newline at end of file