diff --git a/Intel8080/inc/Intel8080.h b/Intel8080/inc/Intel8080.h index 989e418..14ca744 100644 --- a/Intel8080/inc/Intel8080.h +++ b/Intel8080/inc/Intel8080.h @@ -107,9 +107,8 @@ namespace EightBit { // - void compare(uint8_t value) { - auto check = A(); - sub(check, value); + void compare(uint8_t& f, uint8_t check, uint8_t value) { + subtract(f, check, value); } void anda(uint8_t value) { @@ -154,22 +153,21 @@ namespace EightBit { HL().word = sum; } - void sub(uint8_t& operand, uint8_t value, int carry = 0) { - auto& f = F(); - register16_t difference; - difference.word = operand - value - carry; - adjustAuxiliaryCarrySub(f, operand, value, difference.word); - operand = difference.low; - setFlag(f, CF, difference.word & Bit8); + void subtract(uint8_t& f, uint8_t& operand, uint8_t value, int carry = 0) { + + register16_t result; + result.word = operand - value - carry; + + adjustAuxiliaryCarrySub(f, operand, value, result.word); + + operand = result.low; + + setFlag(f, CF, result.word & Bit8); adjustSZP(f, operand); } - void sub(uint8_t value, int carry = 0) { - sub(A(), value, carry); - } - void sbb(uint8_t value) { - sub(value, F() & CF); + subtract(F(), A(), value, F() & CF); } void mov_m_r(uint8_t value) { @@ -499,17 +497,17 @@ namespace EightBit { // subtract - void sub_a() { sub(A()); } - void sub_b() { sub(B()); } - void sub_c() { sub(C()); } - void sub_d() { sub(D()); } - void sub_e() { sub(E()); } - void sub_h() { sub(H()); } - void sub_l() { sub(L()); } + void sub_a() { subtract(F(), A(), A()); } + void sub_b() { subtract(F(), A(), B()); } + void sub_c() { subtract(F(), A(), C()); } + void sub_d() { subtract(F(), A(), D()); } + void sub_e() { subtract(F(), A(), E()); } + void sub_h() { subtract(F(), A(), H()); } + void sub_l() { subtract(F(), A(), L()); } void sub_m() { m_memory.ADDRESS() = HL(); - sub(m_memory.reference()); + subtract(F(), A(), m_memory.reference()); } void sbb_a() { sbb(A()); } @@ -530,7 +528,7 @@ namespace EightBit { } void sui() { - sub(fetchByte()); + subtract(F(), A(), fetchByte()); } // logical @@ -580,20 +578,20 @@ namespace EightBit { void ori() { ora(fetchByte()); } - void cmp_a() { compare(A()); } - void cmp_b() { compare(B()); } - void cmp_c() { compare(C()); } - void cmp_d() { compare(D()); } - void cmp_e() { compare(E()); } - void cmp_h() { compare(H()); } - void cmp_l() { compare(L()); } + void cmp_a() { compare(F(), A(), A()); } + void cmp_b() { compare(F(), A(), B()); } + void cmp_c() { compare(F(), A(), C()); } + void cmp_d() { compare(F(), A(), D()); } + void cmp_e() { compare(F(), A(), E()); } + void cmp_h() { compare(F(), A(), H()); } + void cmp_l() { compare(F(), A(), L()); } void cmp_m() { m_memory.ADDRESS() = HL(); - compare(m_memory.reference()); + compare(F(), A(), m_memory.reference()); } - void cpi() { compare(fetchByte()); } + void cpi() { compare(F(), A(), fetchByte()); } // rotate diff --git a/LR35902/inc/LR35902.h b/LR35902/inc/LR35902.h index e379a86..0bc2ada 100644 --- a/LR35902/inc/LR35902.h +++ b/LR35902/inc/LR35902.h @@ -108,7 +108,7 @@ namespace EightBit { return execute(fetchByte()); } - uint8_t& R(int r) { + uint8_t& R(int r, uint8_t& a) { switch (r) { case 0: return B(); @@ -126,7 +126,7 @@ namespace EightBit { m_memory.ADDRESS() = HL(); return m_memory.reference(); case 7: - return A(); + return a; } throw std::logic_error("Unhandled registry mechanism"); } @@ -157,6 +157,8 @@ namespace EightBit { setFlag(f, HC, calculateHalfCarrySub(before, value, calculation)); } + static void subtract(uint8_t& f, uint8_t& operand, uint8_t value, int carry = 0); + void executeCB(int x, int y, int z, int p, int q); void executeOther(int x, int y, int z, int p, int q); @@ -165,43 +167,41 @@ namespace EightBit { void reti(); - bool jrConditionalFlag(int flag); - bool returnConditionalFlag(int flag); - bool jumpConditionalFlag(int flag); - bool callConditionalFlag(int flag); + bool jrConditionalFlag(uint8_t& f, int flag); + bool returnConditionalFlag(uint8_t& f, int flag); + bool jumpConditionalFlag(uint8_t& f, int flag); + bool callConditionalFlag(uint8_t& f, int flag); - void sbc(register16_t& operand, register16_t value); - void adc(register16_t& operand, register16_t value); + void sbc(uint8_t& f, register16_t& operand, register16_t value); + void adc(uint8_t& f, register16_t& operand, register16_t value); + void add(uint8_t& f, register16_t& operand, register16_t value); - void add(register16_t& operand, register16_t value); + static void add(uint8_t& f, uint8_t& operand, uint8_t value, int carry = 0); + static void adc(uint8_t& f, uint8_t& operand, uint8_t value); + static void sbc(uint8_t& f, uint8_t& operand, uint8_t value); + static void andr(uint8_t& f, uint8_t& operand, uint8_t value); + static void xorr(uint8_t& f, uint8_t& operand, uint8_t value); + static void orr(uint8_t& f, uint8_t& operand, uint8_t value); + static void compare(uint8_t& f, uint8_t check, uint8_t value); - void add(uint8_t& operand, uint8_t value, int carry = 0); - void adc(uint8_t& operand, uint8_t value); - void sub(uint8_t& operand, uint8_t value, int carry = 0); - void sbc(uint8_t& operand, uint8_t value); - void andr(uint8_t& operand, uint8_t value); - void xorr(uint8_t& operand, uint8_t value); - void orr(uint8_t& operand, uint8_t value); - void compare(uint8_t value); + static void rlc(uint8_t& f, uint8_t& operand); + static void rrc(uint8_t& f, uint8_t& operand); + static void rl(uint8_t& f, uint8_t& operand); + static void rr(uint8_t& f, uint8_t& operand); + static void sla(uint8_t& f, uint8_t& operand); + static void sra(uint8_t& f, uint8_t& operand); + static void srl(uint8_t& f, uint8_t& operand); - void rlc(uint8_t& operand); - void rrc(uint8_t& operand); - void rl(uint8_t& operand); - void rr(uint8_t& operand); - void sla(uint8_t& operand); - void sra(uint8_t& operand); - void srl(uint8_t& operand); + static void bit(uint8_t& f, int n, uint8_t& operand); + static void res(int n, uint8_t& operand); + static void set(int n, uint8_t& operand); - void bit(int n, uint8_t& operand); - void res(int n, uint8_t& operand); - void set(int nit, uint8_t& operand); + static void daa(uint8_t& a, uint8_t& f); - void daa(); + static void scf(uint8_t& a, uint8_t& f); + static void ccf(uint8_t& a, uint8_t& f); + static void cpl(uint8_t& a, uint8_t& f); - void scf(); - void ccf(); - void cpl(); - - void swap(uint8_t& operand); + void swap(uint8_t& f, uint8_t& operand); }; } \ No newline at end of file diff --git a/LR35902/src/LR35902.cpp b/LR35902/src/LR35902.cpp index 0b4cf1b..621e674 100644 --- a/LR35902/src/LR35902.cpp +++ b/LR35902/src/LR35902.cpp @@ -67,30 +67,30 @@ void EightBit::LR35902::postDecrement(uint8_t& f, uint8_t value) { #pragma region PC manipulation: call/ret/jp/jr -bool EightBit::LR35902::jrConditionalFlag(int flag) { +bool EightBit::LR35902::jrConditionalFlag(uint8_t& f, int flag) { switch (flag) { case 0: // NZ - return jrConditional(!(F() & ZF)); + return jrConditional(!(f & ZF)); case 1: // Z - return jrConditional(F() & ZF); + return jrConditional(f & ZF); case 2: // NC - return jrConditional(!(F() & CF)); + return jrConditional(!(f & CF)); case 3: // C - return jrConditional(F() & CF); + return jrConditional(f & CF); } throw std::logic_error("Unhandled JR conditional"); } -bool EightBit::LR35902::jumpConditionalFlag(int flag) { +bool EightBit::LR35902::jumpConditionalFlag(uint8_t& f, int flag) { switch (flag) { case 0: // NZ - return jumpConditional(!(F() & ZF)); + return jumpConditional(!(f & ZF)); case 1: // Z - return jumpConditional(F() & ZF); + return jumpConditional(f & ZF); case 2: // NC - return jumpConditional(!(F() & CF)); + return jumpConditional(!(f & CF)); case 3: // C - return jumpConditional(F() & CF); + return jumpConditional(f & CF); } throw std::logic_error("Unhandled JP conditional"); } @@ -100,30 +100,30 @@ void EightBit::LR35902::reti() { ei(); } -bool EightBit::LR35902::returnConditionalFlag(int flag) { +bool EightBit::LR35902::returnConditionalFlag(uint8_t& f, int flag) { switch (flag) { case 0: // NZ - return returnConditional(!(F() & ZF)); + return returnConditional(!(f & ZF)); case 1: // Z - return returnConditional(F() & ZF); + return returnConditional(f & ZF); case 2: // NC - return returnConditional(!(F() & CF)); + return returnConditional(!(f & CF)); case 3: // C - return returnConditional(F() & CF); + return returnConditional(f & CF); } throw std::logic_error("Unhandled RET conditional"); } -bool EightBit::LR35902::callConditionalFlag(int flag) { +bool EightBit::LR35902::callConditionalFlag(uint8_t& f, int flag) { switch (flag) { case 0: // NZ - return callConditional(!(F() & ZF)); + return callConditional(!(f & ZF)); case 1: // Z - return callConditional(F() & ZF); + return callConditional(f & ZF); case 2: // NC - return callConditional(!(F() & CF)); + return callConditional(!(f & CF)); case 3: // C - return callConditional(F() & CF); + return callConditional(f & CF); } throw std::logic_error("Unhandled CALL conditional"); } @@ -132,35 +132,33 @@ bool EightBit::LR35902::callConditionalFlag(int flag) { #pragma region 16-bit arithmetic -void EightBit::LR35902::sbc(register16_t& operand, register16_t value) { +void EightBit::LR35902::sbc(uint8_t& f, register16_t& operand, register16_t value) { auto before = operand; - auto result = before.word - value.word - (F() & CF); + auto result = before.word - value.word - (f & CF); operand.word = result; - auto& f = F(); clearFlag(f, ZF, operand.word); adjustHalfCarrySub(f, before.high, value.high, operand.high); setFlag(f, NF); setFlag(f, CF, result & Bit16); } -void EightBit::LR35902::adc(register16_t& operand, register16_t value) { +void EightBit::LR35902::adc(uint8_t& f, register16_t& operand, register16_t value) { auto before = operand; - auto result = before.word + value.word + (F() & CF); + auto result = before.word + value.word + (f & CF); operand.word = result; - auto& f = F(); clearFlag(f, ZF, result); adjustHalfCarryAdd(f, before.high, value.high, operand.high); clearFlag(f, NF); setFlag(f, CF, result & Bit16); } -void EightBit::LR35902::add(register16_t& operand, register16_t value) { +void EightBit::LR35902::add(uint8_t& f, register16_t& operand, register16_t value) { auto before = operand; @@ -168,7 +166,6 @@ void EightBit::LR35902::add(register16_t& operand, register16_t value) { operand.word = result; - auto& f = F(); clearFlag(f, NF); setFlag(f, CF, result & Bit16); adjustHalfCarryAdd(f, before.high, value.high, operand.high); @@ -178,9 +175,7 @@ void EightBit::LR35902::add(register16_t& operand, register16_t value) { #pragma region ALU -void EightBit::LR35902::add(uint8_t& operand, uint8_t value, int carry) { - - auto& f = F(); +void EightBit::LR35902::add(uint8_t& f, uint8_t& operand, uint8_t value, int carry) { register16_t result; result.word = operand + value + carry; @@ -194,13 +189,11 @@ void EightBit::LR35902::add(uint8_t& operand, uint8_t value, int carry) { adjustZero(f, operand); } -void EightBit::LR35902::adc(uint8_t& operand, uint8_t value) { - add(operand, value, F() & CF); +void EightBit::LR35902::adc(uint8_t& f, uint8_t& operand, uint8_t value) { + add(operand, value, f & CF); } -void EightBit::LR35902::sub(uint8_t& operand, uint8_t value, int carry) { - - auto& f = F(); +void EightBit::LR35902::subtract(uint8_t& f, uint8_t& operand, uint8_t value, int carry) { register16_t result; result.word = operand - value - carry; @@ -214,112 +207,87 @@ void EightBit::LR35902::sub(uint8_t& operand, uint8_t value, int carry) { adjustZero(f, operand); } -void EightBit::LR35902::sbc(uint8_t& operand, uint8_t value) { - sub(operand, value, F() & CF); +void EightBit::LR35902::sbc(uint8_t& f, uint8_t& operand, uint8_t value) { + subtract(operand, value, f & CF); } -void EightBit::LR35902::andr(uint8_t& operand, uint8_t value) { - auto& f = F(); +void EightBit::LR35902::andr(uint8_t& f, uint8_t& operand, uint8_t value) { operand &= value; setFlag(f, HC); clearFlag(f, CF | NF); adjustZero(f, operand); } -void EightBit::LR35902::xorr(uint8_t& operand, uint8_t value) { - auto& f = F(); +void EightBit::LR35902::xorr(uint8_t& f, uint8_t& operand, uint8_t value) { operand ^= value; clearFlag(f, HC | CF | NF); adjustZero(f, operand); } -void EightBit::LR35902::orr(uint8_t& operand, uint8_t value) { - auto& f = F(); +void EightBit::LR35902::orr(uint8_t& f, uint8_t& operand, uint8_t value) { operand |= value; clearFlag(f, HC | CF | NF); adjustZero(f, operand); } -void EightBit::LR35902::compare(uint8_t value) { - auto check = A(); - sub(check, value); +void EightBit::LR35902::compare(uint8_t& f, uint8_t check, uint8_t value) { + subtract(f, check, value); } #pragma endregion ALU #pragma region Shift and rotate -void EightBit::LR35902::rlc(uint8_t& operand) { - auto& f = F(); - auto carry = operand & Bit7; - operand <<= 1; - setFlag(f, CF, carry); - carry ? operand |= Bit0 : operand &= ~Bit0; +void EightBit::LR35902::rlc(uint8_t& f, uint8_t& operand) { clearFlag(f, NF | HC); + setFlag(f, CF, operand & Bit7); + operand = _rotl8(operand, 1); adjustZero(f, operand); } -void EightBit::LR35902::rrc(uint8_t& operand) { - auto& f = F(); - auto carry = operand & Bit0; - operand >>= 1; - carry ? operand |= Bit7 : operand &= ~Bit7; - setFlag(f, CF, carry); +void EightBit::LR35902::rrc(uint8_t& f, uint8_t& operand) { clearFlag(f, NF | HC); + setFlag(f, CF, operand & Bit0); + operand = _rotr8(operand, 1); adjustZero(f, operand); } -void EightBit::LR35902::rl(uint8_t& operand) { - auto& f = F(); - auto oldCarry = f & CF; - auto newCarry = operand & Bit7; - operand <<= 1; - oldCarry ? operand |= Bit0 : operand &= ~Bit0; - setFlag(f, CF, newCarry); +void EightBit::LR35902::rl(uint8_t& f, uint8_t& operand) { clearFlag(f, NF | HC); + const auto carry = f & CF; + setFlag(f, CF, operand & Bit7); + operand = (operand << 1) | carry; adjustZero(f, operand); } -void EightBit::LR35902::rr(uint8_t& operand) { - auto& f = F(); - auto oldCarry = f & CF; - auto newCarry = operand & Bit0; - operand >>= 1; - operand |= oldCarry << 7; - setFlag(f, CF, newCarry); +void EightBit::LR35902::rr(uint8_t& f, uint8_t& operand) { clearFlag(f, NF | HC); + const auto carry = f & CF; + setFlag(f, CF, operand & Bit0); + operand = (operand >> 1) | (carry << 7); adjustZero(f, operand); } // -void EightBit::LR35902::sla(uint8_t& operand) { - auto& f = F(); - auto newCarry = operand & Bit7; +void EightBit::LR35902::sla(uint8_t& f, uint8_t& operand) { + clearFlag(f, NF | HC); + setFlag(f, CF, operand & Bit7); operand <<= 1; - setFlag(f, CF, newCarry); - clearFlag(f, NF | HC); adjustZero(f, operand); } -void EightBit::LR35902::sra(uint8_t& operand) { - auto& f = F(); - auto new7 = operand & Bit7; - auto newCarry = operand & Bit0; - operand >>= 1; - operand |= new7; - setFlag(f, CF, newCarry); +void EightBit::LR35902::sra(uint8_t& f, uint8_t& operand) { clearFlag(f, NF | HC); + setFlag(f, CF, operand & Bit0); + operand = (operand >> 1) | operand & Bit7; adjustZero(f, operand); } -void EightBit::LR35902::srl(uint8_t& operand) { - auto& f = F(); - auto newCarry = operand & Bit0; - operand >>= 1; - operand &= ~Bit7; // clear bit 7 - setFlag(f, CF, newCarry); +void EightBit::LR35902::srl(uint8_t& f, uint8_t& operand) { clearFlag(f, NF | HC); + setFlag(f, CF, operand & Bit0); + operand = (operand >> 1) & ~Bit7; adjustZero(f, operand); } @@ -327,11 +295,10 @@ void EightBit::LR35902::srl(uint8_t& operand) { #pragma region BIT/SET/RES -void EightBit::LR35902::bit(int n, uint8_t& operand) { - auto& f = F(); +void EightBit::LR35902::bit(uint8_t& f, int n, uint8_t& operand) { auto carry = f & CF; uint8_t discarded = operand; - andr(discarded, 1 << n); + andr(f, discarded, 1 << n); setFlag(f, CF, carry); } @@ -349,55 +316,48 @@ void EightBit::LR35902::set(int n, uint8_t& operand) { #pragma region Miscellaneous instructions -void EightBit::LR35902::daa() { +void EightBit::LR35902::daa(uint8_t& a, uint8_t& f) { - auto& f = F(); + auto updated = a; - uint8_t a = A(); + auto lowAdjust = (f & HC) | (lowNibble(a) > 9); + auto highAdjust = (f & CF) | (a > 0x99); - auto lowAdjust = (f & HC) | ((A() & Mask4) > 9); - auto highAdjust = (f & CF) | (A() > 0x99); - - if (F() & NF) { + if (f & NF) { if (lowAdjust) - a -= 6; + updated -= 6; if (highAdjust) - a -= 0x60; + updated -= 0x60; } else { if (lowAdjust) - a += 6; + updated += 6; if (highAdjust) - a += 0x60; + updated += 0x60; } - f = (f & (CF | NF)) | (A() > 0x99) | ((A() ^ a) & HC); + f = (f & (CF | NF)) | (a > 0x99) | ((a ^ updated) & HC); + a = updated; adjustZero(f, a); - - A() = a; } -void EightBit::LR35902::cpl() { - A() = ~A(); - auto& f = F(); +void EightBit::LR35902::cpl(uint8_t& a, uint8_t& f) { + a = ~a; setFlag(f, HC | NF); } -void EightBit::LR35902::scf() { - auto& f = F(); +void EightBit::LR35902::scf(uint8_t& a, uint8_t& f) { setFlag(f, CF); clearFlag(f, HC | NF); } -void EightBit::LR35902::ccf() { - auto& f = F(); +void EightBit::LR35902::ccf(uint8_t& a, uint8_t& f) { auto carry = f & CF; clearFlag(f, CF, carry); clearFlag(f, NF | HC); } -void EightBit::LR35902::swap(uint8_t& operand) { - auto& f = F(); +void EightBit::LR35902::swap(uint8_t& f, uint8_t& operand) { auto low = lowNibble(operand); auto high = highNibble(operand); operand = promoteNibble(low) | demoteNibble(high); @@ -435,35 +395,37 @@ int EightBit::LR35902::execute(uint8_t opcode) { } void EightBit::LR35902::executeCB(int x, int y, int z, int p, int q) { + auto& a = A(); + auto& f = F(); switch (x) { case 0: // rot[y] r[z] switch (y) { case 0: - rlc(R(z)); + rlc(f, R(z, a)); break; case 1: - rrc(R(z)); + rrc(f, R(z, a)); break; case 2: - rl(R(z)); + rl(f, R(z, a)); break; case 3: - rr(R(z)); + rr(f, R(z, a)); break; case 4: - sla(R(z)); + sla(f, R(z, a)); break; case 5: - sra(R(z)); + sra(f, R(z, a)); break; case 6: - swap(R(z)); + swap(f, R(z, a)); break; case 7: - srl(R(z)); + srl(f, R(z, a)); break; } - adjustZero(F(), R(z)); + adjustZero(f, R(z, a)); cycles += 2; if (z == 6) { m_bus.fireWriteBusEvent(); @@ -471,7 +433,7 @@ void EightBit::LR35902::executeCB(int x, int y, int z, int p, int q) { } break; case 1: // BIT y, r[z] - bit(y, R(z)); + bit(f, y, R(z, a)); cycles += 2; if (z == 6) { m_bus.fireReadBusEvent(); @@ -479,7 +441,7 @@ void EightBit::LR35902::executeCB(int x, int y, int z, int p, int q) { } break; case 2: // RES y, r[z] - res(y, R(z)); + res(y, R(z, a)); cycles += 2; if (z == 6) { m_bus.fireWriteBusEvent(); @@ -487,7 +449,7 @@ void EightBit::LR35902::executeCB(int x, int y, int z, int p, int q) { } break; case 3: // SET y, r[z] - set(y, R(z)); + set(y, R(z, a)); cycles += 2; if (z == 6) { m_bus.fireWriteBusEvent(); @@ -498,6 +460,8 @@ void EightBit::LR35902::executeCB(int x, int y, int z, int p, int q) { } void EightBit::LR35902::executeOther(int x, int y, int z, int p, int q) { + auto& a = A(); + auto& f = F(); switch (x) { case 0: switch (z) { @@ -519,14 +483,13 @@ void EightBit::LR35902::executeOther(int x, int y, int z, int p, int q) { jr(fetchByte()); cycles += 4; break; - default: { // JR cc,d - auto condition = y - 4; - if (condition < 4) { - if (jrConditionalFlag(condition)) - cycles++; - cycles += 2; - } - } + case 4: // JR cc,d + case 5: + case 6: + case 7: + if (jrConditionalFlag(f, y - 4)) + cycles++; + cycles += 2; break; } break; @@ -537,7 +500,7 @@ void EightBit::LR35902::executeOther(int x, int y, int z, int p, int q) { cycles += 3; break; case 1: // ADD HL,rp - add(HL(), RP(p)); + add(f, HL(), RP(p)); cycles += 2; break; } @@ -547,19 +510,19 @@ void EightBit::LR35902::executeOther(int x, int y, int z, int p, int q) { case 0: switch (p) { case 0: // LD (BC),A - m_memory.write(BC().word, A()); + m_memory.write(BC().word, a); cycles += 2; break; case 1: // LD (DE),A - m_memory.write(DE().word, A()); + m_memory.write(DE().word, a); cycles += 2; break; case 2: // GB: LDI (HL),A - m_memory.write(HL().word++, A()); + m_memory.write(HL().word++, a); cycles += 2; break; case 3: // GB: LDD (HL),A - m_memory.write(HL().word--, A()); + m_memory.write(HL().word--, a); cycles += 2; break; } @@ -567,19 +530,19 @@ void EightBit::LR35902::executeOther(int x, int y, int z, int p, int q) { case 1: switch (p) { case 0: // LD A,(BC) - A() = m_memory.read(BC().word); + a = m_memory.read(BC().word); cycles += 2; break; case 1: // LD A,(DE) - A() = m_memory.read(DE().word); + a = m_memory.read(DE().word); cycles += 2; break; case 2: // GB: LDI A,(HL) - A() = m_memory.read(HL().word++); + a = m_memory.read(HL().word++); cycles += 2; break; case 3: // GB: LDD A,(HL) - A() = m_memory.read(HL().word--); + a = m_memory.read(HL().word--); cycles += 2; break; } @@ -598,7 +561,7 @@ void EightBit::LR35902::executeOther(int x, int y, int z, int p, int q) { cycles += 2; break; case 4: // 8-bit INC - postIncrement(F(), ++R(y)); // INC r + postIncrement(f, ++R(y, a)); // INC r cycles++; if (y == 6) { m_bus.fireWriteBusEvent(); @@ -606,7 +569,7 @@ void EightBit::LR35902::executeOther(int x, int y, int z, int p, int q) { } break; case 5: // 8-bit DEC - postDecrement(F(), --R(y)); // DEC r + postDecrement(f, --R(y, a)); // DEC r cycles++; if (y == 6) { m_bus.fireWriteBusEvent(); @@ -614,7 +577,7 @@ void EightBit::LR35902::executeOther(int x, int y, int z, int p, int q) { } break; case 6: // 8-bit load immediate - R(y) = fetchByte(); + R(y, a) = fetchByte(); if (y == 6) m_bus.fireWriteBusEvent(); cycles += 2; @@ -622,32 +585,28 @@ void EightBit::LR35902::executeOther(int x, int y, int z, int p, int q) { case 7: // Assorted operations on accumulator/flags switch (y) { case 0: - rlc(A()); - clearFlag(F(), ZF); + rlc(f, a); break; case 1: - rrc(A()); - clearFlag(F(), ZF); + rrc(f, a); break; case 2: - rl(A()); - clearFlag(F(), ZF); + rl(f, a); break; case 3: - rr(A()); - clearFlag(F(), ZF); + rr(f, a); break; case 4: - daa(); + daa(a, f); break; case 5: - cpl(); + cpl(a, f); break; case 6: - scf(); + scf(a, f); break; case 7: - ccf(); + ccf(a, f); break; } cycles++; @@ -658,7 +617,7 @@ void EightBit::LR35902::executeOther(int x, int y, int z, int p, int q) { if (z == 6 && y == 6) { // Exception (replaces LD (HL), (HL)) halt(); } else { - R(y) = R(z); + R(y, a) = R(z, a); if ((y == 6) || (z == 6)) { // M operations if (y == 6) m_bus.fireWriteBusEvent(); @@ -672,28 +631,28 @@ void EightBit::LR35902::executeOther(int x, int y, int z, int p, int q) { case 2: // Operate on accumulator and register/memory location switch (y) { case 0: // ADD A,r - add(A(), R(z)); + add(f, a, R(z, a)); break; case 1: // ADC A,r - adc(A(), R(z)); + adc(f, a, R(z, a)); break; case 2: // SUB r - sub(A(), R(z)); + subtract(f, a, R(z, a)); break; case 3: // SBC A,r - sbc(A(), R(z)); + sbc(f, a, R(z, a)); break; case 4: // AND r - andr(A(), R(z)); + andr(f, a, R(z, a)); break; case 5: // XOR r - xorr(A(), R(z)); + xorr(f, a, R(z, a)); break; case 6: // OR r - orr(A(), R(z)); + orr(f, a, R(z, a)); break; case 7: // CP r - compare(R(z)); + compare(f, a, R(z, a)); break; } cycles++; @@ -705,45 +664,45 @@ void EightBit::LR35902::executeOther(int x, int y, int z, int p, int q) { case 3: switch (z) { case 0: // Conditional return - if (y < 4) { - if (returnConditionalFlag(y)) + switch (y) { + case 0: + case 1: + case 2: + case 3: + if (returnConditionalFlag(f, y)) cycles += 3; cycles += 2; - } else { - switch (y) { - case 4: // GB: LD (FF00 + n),A - m_bus.writeRegister(fetchByte(), A()); - cycles += 3; - break; - case 5: { // GB: ADD SP,dd - auto& f = F(); - auto before = SP(); - auto value = fetchByte(); - auto result = SP().word + (int8_t)value; - SP().word = result; - clearFlag(f, ZF | NF); - setFlag(f, CF, result & Bit16); - adjustHalfCarryAdd(f, before.high, value, SP().high); - } - cycles += 4; - break; - case 6: // GB: LD A,(FF00 + n) - A() = m_bus.readRegister(fetchByte()); - cycles += 3; - break; - case 7: { // GB: LD HL,SP + dd - auto& f = F(); - auto before = HL(); - auto value = fetchByte(); - auto result = SP().word + (int8_t)value; - HL().word = result; - clearFlag(f, ZF | NF); - setFlag(f, CF, result & Bit16); - adjustHalfCarryAdd(f, before.high, value, HL().high); - } - cycles += 3; - break; + break; + case 4: // GB: LD (FF00 + n),A + m_bus.writeRegister(fetchByte(), a); + cycles += 3; + break; + case 5: { // GB: ADD SP,dd + auto before = SP(); + auto value = fetchByte(); + auto result = SP().word + (int8_t)value; + SP().word = result; + clearFlag(f, ZF | NF); + setFlag(f, CF, result & Bit16); + adjustHalfCarryAdd(f, before.high, value, SP().high); } + cycles += 4; + break; + case 6: // GB: LD A,(FF00 + n) + a = m_bus.readRegister(fetchByte()); + cycles += 3; + break; + case 7: { // GB: LD HL,SP + dd + auto before = HL(); + auto value = fetchByte(); + auto result = SP().word + (int8_t)value; + HL().word = result; + clearFlag(f, ZF | NF); + setFlag(f, CF, result & Bit16); + adjustHalfCarryAdd(f, before.high, value, HL().high); + } + cycles += 3; + break; } break; case 1: // POP & various ops @@ -774,30 +733,32 @@ void EightBit::LR35902::executeOther(int x, int y, int z, int p, int q) { } break; case 2: // Conditional jump - if (y < 4) { - jumpConditionalFlag(y); + switch (y) { + case 0: + case 1: + case 2: + case 3: + jumpConditionalFlag(f, y); cycles += 3; - } else { - switch (y) { - case 4: // GB: LD (FF00 + C),A - m_bus.writeRegister(C(), A()); - cycles += 2; - break; - case 5: // GB: LD (nn),A - fetchWord(); - m_bus.write(MEMPTR().word, A()); - cycles += 4; - break; - case 6: // GB: LD A,(FF00 + C) - A() = m_bus.readRegister(C()); - cycles += 2; - break; - case 7: // GB: LD A,(nn) - fetchWord(); - A() = m_bus.read(MEMPTR().word); - cycles += 4; - break; - } + break; + case 4: // GB: LD (FF00 + C),A + m_bus.writeRegister(C(), a); + cycles += 2; + break; + case 5: // GB: LD (nn),A + fetchWord(); + m_bus.write(MEMPTR().word, a); + cycles += 4; + break; + case 6: // GB: LD A,(FF00 + C) + a = m_bus.readRegister(C()); + cycles += 2; + break; + case 7: // GB: LD A,(nn) + fetchWord(); + a = m_bus.read(MEMPTR().word); + cycles += 4; + break; } break; case 3: // Assorted operations @@ -822,7 +783,7 @@ void EightBit::LR35902::executeOther(int x, int y, int z, int p, int q) { } break; case 4: // Conditional call: CALL cc[y], nn - if (callConditionalFlag(y)) + if (callConditionalFlag(f, y)) cycles += 3; cycles += 3; break; @@ -845,28 +806,28 @@ void EightBit::LR35902::executeOther(int x, int y, int z, int p, int q) { case 6: // Operate on accumulator and immediate operand: alu[y] n switch (y) { case 0: // ADD A,n - add(A(), fetchByte()); + add(f, a, fetchByte()); break; case 1: // ADC A,n - adc(A(), fetchByte()); + adc(f, a, fetchByte()); break; case 2: // SUB n - sub(A(), fetchByte()); + subtract(f, a, fetchByte()); break; case 3: // SBC A,n - sbc(A(), fetchByte()); + sbc(f, a, fetchByte()); break; case 4: // AND n - andr(A(), fetchByte()); + andr(f, a, fetchByte()); break; case 5: // XOR n - xorr(A(), fetchByte()); + xorr(f, a, fetchByte()); break; case 6: // OR n - orr(A(), fetchByte()); + orr(f, a, fetchByte()); break; case 7: // CP n - compare(fetchByte()); + compare(f, a, fetchByte()); break; } cycles += 2; diff --git a/Z80/inc/Z80.h b/Z80/inc/Z80.h index f0fcd52..b27b73d 100644 --- a/Z80/inc/Z80.h +++ b/Z80/inc/Z80.h @@ -322,7 +322,7 @@ namespace EightBit { static uint8_t& bit(uint8_t& f, int n, uint8_t& operand); static uint8_t& res(int n, uint8_t& operand); - static uint8_t& set(int nit, uint8_t& operand); + static uint8_t& set(int n, uint8_t& operand); static void daa(uint8_t& a, uint8_t& f); diff --git a/Z80/src/Z80.cpp b/Z80/src/Z80.cpp index 5d037cd..bef3299 100644 --- a/Z80/src/Z80.cpp +++ b/Z80/src/Z80.cpp @@ -140,14 +140,6 @@ bool EightBit::Z80::jrConditionalFlag(uint8_t& f, int flag) { return jrConditional(!(f & CF)); case 3: // C return jrConditional(f & CF); - case 4: // PO - return jrConditional(!(f & PF)); - case 5: // PE - return jrConditional(f & PF); - case 6: // P - return jrConditional(!(f & SF)); - case 7: // M - return jrConditional(f & SF); default: __assume(0); } @@ -1149,11 +1141,16 @@ void EightBit::Z80::executeOther(int x, int y, int z, int p, int q) { jr(fetchByte()); cycles += 12; break; - default: // JR cc,d + case 4: // JR cc,d + case 5: + case 6: + case 7: if (jrConditionalFlag(f, y - 4)) cycles += 5; cycles += 5; break; + default: + __assume(0); } break; case 1: // 16-bit load immediate/add