all repos — mgba @ 20622b6135056581a6fc8ed2d274eca8cf6daf84

mGBA Game Boy Advance Emulator

Copy some IRQ infrastructure from GBA.js
Jeffrey Pfau jeffrey@endrift.com
Tue, 16 Apr 2013 19:41:09 -0700
commit

20622b6135056581a6fc8ed2d274eca8cf6daf84

parent

bc9d0690bba1a01a612d7b2d25c24b10b077fab9

2 files changed, 53 insertions(+), 0 deletions(-)

jump to
M src/gba/gba.csrc/gba/gba.c

@@ -37,6 +37,8 @@

gba->video.p = gba; GBAVideoInit(&gba->video); + gba->springIRQ = 0; + ARMReset(&gba->cpu); }

@@ -124,6 +126,52 @@ gba->memory.io[REG_IF >> 1] |= 1 << irq;

if (gba->memory.io[REG_IME >> 1] && (gba->memory.io[REG_IE >> 1] & 1 << irq)) { ARMRaiseIRQ(&gba->cpu); + } +} + +void GBAPollNextEvent(struct GBA* gba) { + int32_t nextEvent = gba->video.nextEvent; + + gba->cpu.nextEvent = nextEvent; +} + +int GBATestIRQ(struct GBA* gba) { + if (gba->memory.io[REG_IME >> 1] && gba->memory.io[REG_IE >> 1] & gba->memory.io[REG_IF >> 1]) { + gba->springIRQ = 1; + gba->cpu.nextEvent = gba->cpu.cycles; + return 1; + } + return 0; +} + +int GBAWaitForIRQ(struct GBA* gba) { + int irqPending = GBATestIRQ(gba) || gba->video.hblankIRQ || gba->video.vblankIRQ || gba->video.vcounterIRQ; + /*if (this.timersEnabled) { + timer = this.timers[0]; + irqPending = irqPending || timer.doIrq; + timer = this.timers[1]; + irqPending = irqPending || timer.doIrq; + timer = this.timers[2]; + irqPending = irqPending || timer.doIrq; + timer = this.timers[3]; + irqPending = irqPending || timer.doIrq; + }*/ + if (!irqPending) { + return 0; + } + + while (1) { + GBAPollNextEvent(gba); + + if (gba->cpu.nextEvent == INT_MAX) { + return 0; + } else { + gba->cpu.cycles = gba->cpu.nextEvent; + GBAProcessEvents(&gba->board.d); + if (gba->memory.io[REG_IF >> 1]) { + return 1; + } + } } }
M src/gba/gba.hsrc/gba/gba.h

@@ -45,6 +45,8 @@ struct GBAVideo video;

struct ARMDebugger* debugger; + int springIRQ; + enum GBAError errno; const char* errstr; };

@@ -61,6 +63,9 @@

void GBAWriteIE(struct GBA* gba, uint16_t value); void GBAWriteIME(struct GBA* gba, uint16_t value); void GBARaiseIRQ(struct GBA* gba, enum GBAIRQ irq); +void GBAPollNextEvent(struct GBA* gba); +int GBATestIRQ(struct GBA* gba); +int GBAWaitForIRQ(struct GBA* gba); void GBAAttachDebugger(struct GBA* gba, struct ARMDebugger* debugger);