A step closer to the .net implementation

This commit is contained in:
Adrian Conlon
2026-03-02 10:49:50 +00:00
parent 74c1bb431b
commit 3fc3b95bbd
4 changed files with 57 additions and 34 deletions

View File

@@ -76,7 +76,7 @@ namespace EightBit {
bool operator==(const Z80& rhs) const;
void execute() noexcept final;
int step() noexcept final;
void poweredStep() noexcept final;
[[nodiscard]] const register16_t& AF() const noexcept final;
[[nodiscard]] auto& AF() noexcept { return IntelProcessor::AF(); }
@@ -147,6 +147,10 @@ namespace EightBit {
int jrConditional(int condition) noexcept final;
private:
bool m_interruptPending = false;
bool m_nonMaskableInterruptPending = false;
bool m_resetPending = false;
InputOutput& m_ports;
enum { BC_IDX, DE_IDX, HL_IDX };
@@ -193,7 +197,7 @@ namespace EightBit {
}
void fetchDisplacement() noexcept;
[[nodiscard]] uint8_t fetchOpCode() noexcept;
[[nodiscard]] uint8_t fetchInstruction() noexcept;
uint8_t readBusDataM1() noexcept;

View File

@@ -26,13 +26,23 @@ EightBit::Z80::Z80(Bus& bus, InputOutput& ports)
IX() = IY() = Mask16;
resetWorkingRegisters();
resetPrefixes();
});
RaisedM1.connect([this](EventArgs) {
++REFRESH();
});
LoweredRESET.connect([this](EventArgs) {
m_resetPending = true;
});
LoweredNMI.connect([this](EventArgs) {
m_nonMaskableInterruptPending = true;
});
LoweredINT.connect([this](EventArgs) {
m_interruptPending = true;
});
}
EightBit::Z80::Z80(const Z80& rhs)
@@ -660,7 +670,7 @@ uint8_t EightBit::Z80::readBusDataM1() noexcept {
// received from the memory is ignored and an NOP instruction is forced internally to the
// CPU.The HALT acknowledge signal is active during this time indicating that the processor
// is in the HALT state
uint8_t EightBit::Z80::fetchOpCode() noexcept {
uint8_t EightBit::Z80::fetchInstruction() noexcept {
uint8_t returned;
{
_ActivateM1 m1(*this);
@@ -820,32 +830,30 @@ void EightBit::Z80::R2(const int r, const uint8_t value) noexcept {
}
}
int EightBit::Z80::step() noexcept {
resetCycles();
ExecutingInstruction.fire();
if (LIKELY(powered())) {
resetPrefixes();
bool handled = false;
if (lowered(RESET())) {
handleRESET();
handled = true;
} else if (lowered(NMI())) {
handleNMI();
handled = true;
} else if (lowered(INT())) {
raiseINT();
raiseHALT();
if (IFF1()) {
handleINT();
handled = true;
}
void EightBit::Z80::poweredStep() noexcept {
m_modifiedF = 0;
m_prefixCB = m_prefixDD = m_prefixED = m_prefixFD = false;
if (m_resetPending) {
m_resetPending = false;
handleRESET();
return;
} else if (m_nonMaskableInterruptPending) {
m_nonMaskableInterruptPending = false;
handleNMI();
return;
} else if (m_interruptPending) {
m_interruptPending = false;
if (IFF1()) {
handleINT();
return;
}
if (!handled)
IntelProcessor::execute(fetchOpCode());
}
ExecutedInstruction.fire();
ASSUME(cycles() > 0);
return cycles();
IntelProcessor::execute(fetchInstruction());
Q() = m_modifiedF;
}
void EightBit::Z80::execute() noexcept {
@@ -1419,7 +1427,7 @@ void EightBit::Z80::executeOther(const int x, const int y, const int z, const in
fetchDisplacement();
IntelProcessor::execute(fetchByte());
} else {
IntelProcessor::execute(fetchOpCode());
IntelProcessor::execute(fetchInstruction());
}
break;
case 2: // OUT (n),A
@@ -1460,15 +1468,15 @@ void EightBit::Z80::executeOther(const int x, const int y, const int z, const in
break;
case 1: // DD prefix
m_prefixDD = true;
IntelProcessor::execute(fetchOpCode());
IntelProcessor::execute(fetchInstruction());
break;
case 2: // ED prefix
m_prefixED = true;
IntelProcessor::execute(fetchOpCode());
IntelProcessor::execute(fetchInstruction());
break;
case 3: // FD prefix
m_prefixFD = true;
IntelProcessor::execute(fetchOpCode());
IntelProcessor::execute(fetchInstruction());
break;
default:
UNREACHABLE;

View File

@@ -40,7 +40,8 @@ namespace EightBit {
[[nodiscard]] constexpr const auto& intermediate() const noexcept { return m_intermediate; }
int run(int limit) noexcept;
virtual int step() noexcept = 0;
virtual int step() noexcept;
virtual void poweredStep() noexcept = 0;
virtual void execute() noexcept = 0;
void execute(uint8_t value) noexcept;

View File

@@ -94,6 +94,16 @@ void EightBit::Processor::setWord(const register16_t address, const register16_t
setWord(value);
}
int EightBit::Processor::step() noexcept {
resetCycles();
ExecutingInstruction.fire();
if (LIKELY(powered()))
poweredStep();
ExecutedInstruction.fire();
ASSUME(cycles() > 0);
return cycles();
}
int EightBit::Processor::run(const int limit) noexcept {
int current = 0;
while (LIKELY(powered() && (current < limit)))