libgambatte: fix interrupt execution anatomy
This commit is contained in:
parent
7e851b19f3
commit
1547d324e7
|
@ -277,8 +277,8 @@ void CPU::loadState(SaveState const &state) {
|
|||
// push rr (16 cycles):
|
||||
// Push value of register pair onto stack:
|
||||
#define push_rr(r1, r2) do { \
|
||||
PUSH(r1, r2); \
|
||||
cycleCounter += 4; \
|
||||
PUSH(r1, r2); \
|
||||
} while (0)
|
||||
|
||||
// pop rr (12 cycles):
|
||||
|
@ -461,8 +461,9 @@ void CPU::loadState(SaveState const &state) {
|
|||
// rst n (16 Cycles):
|
||||
// Push present address onto stack, jump to address n (one of 00h,08h,10h,18h,20h,28h,30h,38h):
|
||||
#define rst_n(n) do { \
|
||||
cycleCounter += 4; \
|
||||
PUSH(pc >> 8, pc & 0xFF); \
|
||||
PC_MOD(n); \
|
||||
pc = n; \
|
||||
} while (0)
|
||||
|
||||
// ret (16 cycles):
|
||||
|
@ -475,9 +476,10 @@ void CPU::loadState(SaveState const &state) {
|
|||
|
||||
void CPU::process(unsigned long const cycles) {
|
||||
mem_.setEndtime(cycleCounter_, cycles);
|
||||
hitInterruptAddress = 0;
|
||||
mem_.updateInput();
|
||||
|
||||
hitInterruptAddress = -1;
|
||||
|
||||
//unsigned char a = a_;
|
||||
unsigned long cycleCounter = cycleCounter_;
|
||||
|
||||
|
@ -490,50 +492,51 @@ void CPU::process(unsigned long const cycles) {
|
|||
cycleCounter += cycles + (-cycles & 3);
|
||||
}
|
||||
} else while (cycleCounter < mem_.nextEventTime()) {
|
||||
unsigned char opcode = 0x00;
|
||||
unsigned char opcode;
|
||||
|
||||
int FullPC = pc;
|
||||
#ifdef DLLABLES
|
||||
for (int i = 0; i < numInterruptAddresses; ++i) {
|
||||
if (pc == (interruptAddresses[i] & 0xFFFF)) {
|
||||
unsigned bank = interruptAddresses[i] >> 16;
|
||||
|
||||
if (pc >= 0x4000 && pc <= 0x7FFF)
|
||||
FullPC |= mem_.curRomBank() << 16;
|
||||
|
||||
for (int i = 0; i < numInterruptAddresses; i++) {
|
||||
if (FullPC == interruptAddresses[i]) {
|
||||
hitInterruptAddress = interruptAddresses[i];
|
||||
mem_.setEndtime(cycleCounter, 0);
|
||||
break;
|
||||
if (!bank || bank == mem_.curRomBank()) {
|
||||
hitInterruptAddress = interruptAddresses[i];
|
||||
mem_.setEndtime(cycleCounter, 0);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!hitInterruptAddress)
|
||||
{
|
||||
if (tracecallback) {
|
||||
int result[14];
|
||||
result[0] = cycleCounter;
|
||||
result[1] = pc;
|
||||
result[2] = sp;
|
||||
result[3] = a;
|
||||
result[4] = b;
|
||||
result[5] = c;
|
||||
result[6] = d;
|
||||
result[7] = e;
|
||||
result[8] = toF(hf2, cf, zf);
|
||||
result[9] = h;
|
||||
result[10] = l;
|
||||
result[11] = skip_;
|
||||
PC_READ_FIRST(opcode);
|
||||
result[12] = opcode;
|
||||
result[13] = mem_.debugGetLY();
|
||||
tracecallback((void *)result);
|
||||
}
|
||||
else {
|
||||
PC_READ_FIRST(opcode);
|
||||
}
|
||||
if (hitInterruptAddress != -1)
|
||||
break;
|
||||
#endif
|
||||
|
||||
if (skip_) {
|
||||
pc = (pc - 1) & 0xFFFF;
|
||||
skip_ = false;
|
||||
}
|
||||
if (tracecallback) {
|
||||
int result[14];
|
||||
result[0] = cycleCounter;
|
||||
result[1] = pc;
|
||||
result[2] = sp;
|
||||
result[3] = a;
|
||||
result[4] = b;
|
||||
result[5] = c;
|
||||
result[6] = d;
|
||||
result[7] = e;
|
||||
result[8] = toF(hf2, cf, zf);
|
||||
result[9] = h;
|
||||
result[10] = l;
|
||||
result[11] = skip_;
|
||||
PC_READ_FIRST(opcode);
|
||||
result[12] = opcode;
|
||||
result[13] = mem_.debugGetLY();
|
||||
tracecallback((void *)result);
|
||||
}
|
||||
else {
|
||||
PC_READ_FIRST(opcode);
|
||||
}
|
||||
|
||||
if (skip_) {
|
||||
pc = (pc - 1) & 0xFFFF;
|
||||
skip_ = false;
|
||||
}
|
||||
|
||||
switch (opcode) {
|
||||
|
|
|
@ -48,6 +48,7 @@ Memory::Memory(unsigned short &sp, unsigned short &pc)
|
|||
intreq_.setEventTime<intevent_blit>(144 * 456ul);
|
||||
intreq_.setEventTime<intevent_end>(0);
|
||||
}
|
||||
|
||||
Memory::~Memory() {
|
||||
delete []bios_;
|
||||
}
|
||||
|
@ -166,11 +167,11 @@ unsigned long Memory::event(unsigned long cc) {
|
|||
|
||||
switch (intreq_.minEventId()) {
|
||||
case intevent_unhalt:
|
||||
intreq_.unhalt();
|
||||
intreq_.setEventTime<intevent_unhalt>(disabled_time);
|
||||
nontrivial_ff_write(0xFF04, 0, cc);
|
||||
pc_ = (pc_ + 1) & 0xFFFF;
|
||||
cc += 4;
|
||||
intreq_.unhalt();
|
||||
intreq_.setEventTime<intevent_unhalt>(disabled_time);
|
||||
break;
|
||||
case intevent_end:
|
||||
intreq_.setEventTime<intevent_end>(disabled_time - 1);
|
||||
|
@ -324,6 +325,7 @@ unsigned long Memory::event(unsigned long cc) {
|
|||
} else
|
||||
address = 0x50 + n;
|
||||
|
||||
updateIrqs(cc);
|
||||
intreq_.ackIrq(n);
|
||||
|
||||
cc += 2;
|
||||
|
@ -980,7 +982,6 @@ void Memory::nontrivial_ff_write(unsigned const p, unsigned data, unsigned long
|
|||
if(cgbSwitching_) {
|
||||
lcd_.copyCgbPalettesToDmg();
|
||||
lcd_.setCgb(false);
|
||||
cgbSwitching_ = false;
|
||||
}
|
||||
return;
|
||||
case 0x51:
|
||||
|
@ -1050,8 +1051,10 @@ void Memory::nontrivial_ff_write(unsigned const p, unsigned data, unsigned long
|
|||
|
||||
return;
|
||||
case 0x6C:
|
||||
ioamhram_[0x16C] = data | 0xFE;
|
||||
cgbSwitching_ = true;
|
||||
if (isCgb()) {
|
||||
ioamhram_[0x16C] = data | 0xFE;
|
||||
cgbSwitching_ = true;
|
||||
}
|
||||
|
||||
return;
|
||||
case 0x70:
|
||||
|
|
|
@ -139,7 +139,7 @@ void LCD::loadState(SaveState const &state, unsigned char const *const oamram) {
|
|||
SpriteMapper::schedule(ppu_.lyCounter(), ppu_.now()));
|
||||
eventTimes_.setm<memevent_lycirq>(lycIrq_.time());
|
||||
eventTimes_.setm<memevent_m1irq>(
|
||||
ppu_.lyCounter().nextFrameCycle(144 * 456, ppu_.now()));
|
||||
ppu_.lyCounter().nextFrameCycle(144 * 456, ppu_.now()) - 2);
|
||||
eventTimes_.setm<memevent_m2irq>(
|
||||
mode2IrqSchedule(statReg_, ppu_.lyCounter(), ppu_.now()));
|
||||
eventTimes_.setm<memevent_m0irq>(statReg_ & lcdstat_m0irqen
|
||||
|
@ -230,7 +230,7 @@ void LCD::speedChange(unsigned long const cc) {
|
|||
eventTimes_.set<event_ly>(ppu_.lyCounter().time());
|
||||
eventTimes_.setm<memevent_spritemap>(SpriteMapper::schedule(ppu_.lyCounter(), cc));
|
||||
eventTimes_.setm<memevent_lycirq>(lycIrq_.time());
|
||||
eventTimes_.setm<memevent_m1irq>(ppu_.lyCounter().nextFrameCycle(144 * 456, cc));
|
||||
eventTimes_.setm<memevent_m1irq>(ppu_.lyCounter().nextFrameCycle(144 * 456, cc) - 2);
|
||||
eventTimes_.setm<memevent_m2irq>(mode2IrqSchedule(statReg_, ppu_.lyCounter(), cc));
|
||||
|
||||
if (eventTimes_(memevent_m0irq) != disabled_time
|
||||
|
@ -458,7 +458,7 @@ void LCD::lcdcChange(unsigned const data, unsigned long const cc) {
|
|||
SpriteMapper::schedule(ppu_.lyCounter(), cc));
|
||||
eventTimes_.setm<memevent_lycirq>(lycIrq_.time());
|
||||
eventTimes_.setm<memevent_m1irq>(
|
||||
ppu_.lyCounter().nextFrameCycle(144 * 456, cc));
|
||||
ppu_.lyCounter().nextFrameCycle(144 * 456, cc) - 2);
|
||||
eventTimes_.setm<memevent_m2irq>(
|
||||
mode2IrqSchedule(statReg_, ppu_.lyCounter(), cc));
|
||||
if (statReg_ & lcdstat_m0irqen) {
|
||||
|
|
Binary file not shown.
Loading…
Reference in New Issue