From 35d6bdb84decefb2da9434cd6cf34a6e86469c47 Mon Sep 17 00:00:00 2001 From: Melefo <42809472+Melefo@users.noreply.github.com> Date: Fri, 21 Feb 2020 11:03:47 +0100 Subject: [PATCH] Adding Stack operations --- CMakeLists.txt | 2 ++ sources/APU/APU.cpp | 16 ++++++++++++++++ sources/APU/APU.hpp | 5 +++++ sources/APU/Instructions/Stack.cpp | 20 ++++++++++++++++++++ tests/APU/testAPUInstructions.cpp | 30 ++++++++++++++++++++++++++++++ 5 files changed, 73 insertions(+) create mode 100644 sources/APU/Instructions/Stack.cpp diff --git a/CMakeLists.txt b/CMakeLists.txt index 1b5558d..f6d5374 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -71,6 +71,7 @@ add_executable(unit_tests sources/Ram/ExtendedRam.hpp sources/Utility/Utility.hpp sources/Utility/Utility.cpp sources/APU/Instructions/Bit.cpp + sources/APU/Instructions/Stack.cpp ) # include criterion & coverage @@ -154,6 +155,7 @@ add_executable(ComSquare sources/Debugger/HeaderViewer.hpp sources/Debugger/APUDebug.hpp sources/Debugger/APUDebug.cpp + sources/APU/Instructions/Stack.cpp ) target_compile_definitions(ComSquare PUBLIC DEBUGGER_ENABLED) diff --git a/sources/APU/APU.cpp b/sources/APU/APU.cpp index 6dec86b..5894c38 100644 --- a/sources/APU/APU.cpp +++ b/sources/APU/APU.cpp @@ -166,6 +166,8 @@ namespace ComSquare::APU return this->SET1(this->_getDirectAddr(), 0); case 0x0A: return this->OR1(this->_getAbsoluteBit()); + case 0x0D: + return this->PUSH(this->_internalRegisters.psw); case 0x0E: return this->TSET1(this->_getAbsoluteAddr()); case 0x12: @@ -176,6 +178,8 @@ namespace ComSquare::APU return this->SET1(this->_getDirectAddr(), 1); case 0x2A: return this->OR1(this->_getAbsoluteBit(), true); + case 0x2D: + return this->PUSH(this->_internalRegisters.a); case 0x32: return this->CLR1(this->_getDirectAddr(), 1); case 0x40: @@ -184,6 +188,8 @@ namespace ComSquare::APU return this->SET1(this->_getDirectAddr(), 2); case 0x4A: return this->AND1(this->_getAbsoluteBit()); + case 0x4D: + return this->PUSH(this->_internalRegisters.x); case 0x4E: return this->TCLR1(this->_getAbsoluteAddr()); case 0x52: @@ -194,6 +200,8 @@ namespace ComSquare::APU return this->SET1(this->_getDirectAddr(), 3); case 0x6A: return this->AND1(this->_getAbsoluteBit(), true); + case 0x6D: + return this->PUSH(this->_internalRegisters.y); case 0x72: return this->CLR1(this->_getDirectAddr(), 3); case 0x80: @@ -202,6 +210,8 @@ namespace ComSquare::APU return this->SET1(this->_getDirectAddr(), 4); case 0x8A: return this->EOR1(this->_getAbsoluteBit()); + case 0x8E: + return this->POP(this->_internalRegisters.psw); case 0x92: return this->CLR1(this->_getDirectAddr(), 4); case 0xA0: @@ -210,6 +220,8 @@ namespace ComSquare::APU return this->SET1(this->_getDirectAddr(), 5); case 0xAA: return this->MOV1(this->_getAbsoluteBit(), true); + case 0xAE: + return this->POP(this->_internalRegisters.a); case 0xB2: return this->CLR1(this->_getDirectAddr(), 5); case 0xC0: @@ -218,10 +230,14 @@ namespace ComSquare::APU return this->SET1(this->_getDirectAddr(), 6); case 0xC1: return this->MOV1(this->_getAbsoluteBit()); + case 0xCE: + return this->POP(this->_internalRegisters.x); case 0xD2: return this->CLR1(this->_getDirectAddr(), 6); case 0xE2: return this->SET1(this->_getDirectAddr(), 7); + case 0xEE: + return this->POP(this->_internalRegisters.y); case 0xF2: return this->CLR1(this->_getDirectAddr(), 7); case 0xEA: diff --git a/sources/APU/APU.hpp b/sources/APU/APU.hpp index 05ffc13..a7cf1a9 100644 --- a/sources/APU/APU.hpp +++ b/sources/APU/APU.hpp @@ -214,6 +214,11 @@ namespace ComSquare::APU int NOT1(std::pair operand); //! @brief Either moves the specified bit into carry or moves carry into the specified bit. int MOV1(std::pair operand, bool to_carry = false); + + //! @brief Push a value onto the stack and decrement SP Register. + int PUSH(uint8_t value); + //! @brief Increment SP Register and pop a single value from the stack. + int POP(uint8_t &destination); public: explicit APU(std::shared_ptr &map); APU(const APU &) = default; diff --git a/sources/APU/Instructions/Stack.cpp b/sources/APU/Instructions/Stack.cpp new file mode 100644 index 0000000..bd9d5d3 --- /dev/null +++ b/sources/APU/Instructions/Stack.cpp @@ -0,0 +1,20 @@ +// +// Created by Melefo on 21/02/2020. +// + +#include "../APU.hpp" + +namespace ComSquare::APU +{ + int APU::PUSH(uint8_t value) + { + this->_internalWrite(this->_internalRegisters.sp-- | 0x0100u, value); + return 4; + } + + int APU::POP(uint8_t &destination) + { + destination = this->_internalRead(++this->_internalRegisters.sp | 0x100u); + return 4; + } +} \ No newline at end of file diff --git a/tests/APU/testAPUInstructions.cpp b/tests/APU/testAPUInstructions.cpp index b3a762f..66533d7 100644 --- a/tests/APU/testAPUInstructions.cpp +++ b/tests/APU/testAPUInstructions.cpp @@ -339,4 +339,34 @@ Test(Bit, MOV1_carry) apu->_internalRegisters.pc -= 2; cr_assert_eq(apu->_internalRegisters.c, false); cr_assert_eq(result, 4); +} + +///////////////// +// // +// Stack tests // +// // +///////////////// + +Test(Stack, push) +{ + auto apu = Init().second.apu; + int result = 0; + + apu->_internalRegisters.a = 56; + result = apu->PUSH(apu->_internalRegisters.a); + apu->_internalRegisters.sp++; + cr_assert_eq(result, 4); + cr_assert_eq(apu->_internalRead(apu->_internalRegisters.sp | 0x100u), 56); +} + +Test(Stack, pop) +{ + auto apu = Init().second.apu; + int result = 0; + + apu->_internalWrite(++apu->_internalRegisters.sp | 0x100u, 82); + apu->_internalRegisters.sp--; + result = apu->POP(apu->_internalRegisters.y); + cr_assert_eq(result, 4); + cr_assert_eq(apu->_internalRegisters.y, 82); } \ No newline at end of file