diff --git a/src/gba/gba-bios.c b/src/gba/gba-bios.c index df1de54ce..4cc1f562f 100644 --- a/src/gba/gba-bios.c +++ b/src/gba/gba-bios.c @@ -49,6 +49,9 @@ static void _CpuSet(struct GBA* gba) { void GBASwi16(struct ARMBoard* board, int immediate) { struct GBA* gba = ((struct GBABoard*) board)->p; switch (immediate) { + case 0x2: + GBAHalt(gba); + break; case 0xB: _CpuSet(gba); break; diff --git a/src/gba/gba-io.c b/src/gba/gba-io.c index e3739c3c5..d272bfb78 100644 --- a/src/gba/gba-io.c +++ b/src/gba/gba-io.c @@ -41,6 +41,14 @@ void GBAIOWrite(struct GBA* gba, uint32_t address, uint16_t value) { case REG_IME: GBAWriteIME(gba, value); break; + case REG_HALTCNT: + value &= 0x80; + if (!value) { + GBAHalt(gba); + } else { + GBALog(GBA_LOG_STUB, "Stop unimplemented"); + } + return; default: GBALog(GBA_LOG_STUB, "Stub I/O register write: %03x", address); break; diff --git a/src/gba/gba.c b/src/gba/gba.c index b2b18a63d..6d305bb9b 100644 --- a/src/gba/gba.c +++ b/src/gba/gba.c @@ -130,12 +130,6 @@ void GBARaiseIRQ(struct GBA* gba, enum GBAIRQ irq) { } } -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; @@ -146,24 +140,7 @@ int GBATestIRQ(struct GBA* gba) { } 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 { @@ -176,6 +153,10 @@ int GBAWaitForIRQ(struct GBA* gba) { } } +int GBAHalt(struct GBA* gba) { + return GBAWaitForIRQ(gba); +} + void GBALog(int level, const char* format, ...) { va_list args; va_start(args, format); diff --git a/src/gba/gba.h b/src/gba/gba.h index 9579c58a1..c1426b031 100644 --- a/src/gba/gba.h +++ b/src/gba/gba.h @@ -64,9 +64,9 @@ void GBABoardReset(struct ARMBoard* board); 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); +int GBAHalt(struct GBA* gba); void GBAAttachDebugger(struct GBA* gba, struct ARMDebugger* debugger);