all repos — mgba @ 2d0c3bf275a5ab4da7a240f5f4d744069ed73bc4

mGBA Game Boy Advance Emulator

Implement IRQs
Jeffrey Pfau jeffrey@endrift.com
Tue, 16 Apr 2013 07:50:34 -0700
commit

2d0c3bf275a5ab4da7a240f5f4d744069ed73bc4

parent

2da11dd523543964bf3b1bf378071a815a8bf575

3 files changed, 23 insertions(+), 3 deletions(-)

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

@@ -111,6 +111,25 @@

cpu->board->reset(cpu->board); } +void ARMRaiseIRQ(struct ARMCore* cpu) { + if (cpu->cpsr.i) { + return; + } + union PSR cpsr = cpu->cpsr; + int instructionWidth; + if (cpu->executionMode == MODE_THUMB) { + instructionWidth = WORD_SIZE_THUMB; + } else { + instructionWidth = WORD_SIZE_ARM; + } + ARMSetPrivilegeMode(cpu, MODE_IRQ); + cpu->spsr = cpsr; + cpu->gprs[ARM_LR] = cpu->gprs[ARM_PC] - instructionWidth + WORD_SIZE_ARM; + cpu->gprs[ARM_PC] = BASE_IRQ + WORD_SIZE_ARM; + _ARMSetMode(cpu, MODE_ARM); + cpu->cpsr.i = 1; +} + void ARMRun(struct ARMCore* cpu) { if (cpu->executionMode == MODE_THUMB) { ThumbStep(cpu);
M src/arm/arm.hsrc/arm/arm.h

@@ -121,6 +121,7 @@ void ARMAssociateBoard(struct ARMCore* cpu, struct ARMBoard* board);

void ARMReset(struct ARMCore* cpu); void ARMSetPrivilegeMode(struct ARMCore*, enum PrivilegeMode); +void ARMRaiseIRQ(struct ARMCore*); void ARMRun(struct ARMCore* cpu);
M src/gba/gba.csrc/gba/gba.c

@@ -109,13 +109,13 @@ GBALog(GBA_LOG_STUB, "Gamepak interrupts not implemented");

} if (gba->memory.io[REG_IME >> 1] && value & gba->memory.io[REG_IF >> 1]) { - //ARMRaiseIRQ(&gba.cpu); + ARMRaiseIRQ(&gba->cpu); } } void GBAWriteIME(struct GBA* gba, uint16_t value) { if (value && gba->memory.io[REG_IE >> 1] & gba->memory.io[REG_IF >> 1]) { - //ARMRaiseIRQ(&gba.cpu); + ARMRaiseIRQ(&gba->cpu); } }

@@ -123,7 +123,7 @@ void GBARaiseIRQ(struct GBA* gba, enum GBAIRQ irq) {

gba->memory.io[REG_IF >> 1] |= 1 << irq; if (gba->memory.io[REG_IME >> 1] && (gba->memory.io[REG_IE >> 1] & 1 << irq)) { - //ARMRaiseIRQ(); + ARMRaiseIRQ(&gba->cpu); } }