all repos — mgba @ a969d70de3dd6bf814a4930525c79997e88dafc0

mGBA Game Boy Advance Emulator

Handle illegal and stub opcodes separately
Jeffrey Pfau jeffrey@endrift.com
Sat, 18 Jan 2014 00:39:51 -0800
commit

a969d70de3dd6bf814a4930525c79997e88dafc0

parent

ce4d0b5203f90f9e6dcf3d5212fc2a5559737e79

5 files changed, 29 insertions(+), 8 deletions(-)

jump to
M src/arm/arm.hsrc/arm/arm.h

@@ -117,6 +117,7 @@ void (*reset)(struct ARMBoard* board);

void (*processEvents)(struct ARMBoard* board); void (*swi16)(struct ARMBoard* board, int immediate); void (*swi32)(struct ARMBoard* board, int immediate); + void (*hitIllegal)(struct ARMBoard* board, uint32_t opcode); void (*readCPSR)(struct ARMBoard* board); void (*hitStub)(struct ARMBoard* board, uint32_t opcode);
M src/arm/isa-arm.csrc/arm/isa-arm.c

@@ -744,10 +744,18 @@ })

// End branch definitions +// Begin coprocessor definitions + +DEFINE_INSTRUCTION_ARM(CDP, ARM_STUB) +DEFINE_INSTRUCTION_ARM(LDC, ARM_STUB) +DEFINE_INSTRUCTION_ARM(STC, ARM_STUB) +DEFINE_INSTRUCTION_ARM(MCR, ARM_STUB) +DEFINE_INSTRUCTION_ARM(MRC, ARM_STUB) + // Begin miscellaneous definitions DEFINE_INSTRUCTION_ARM(BKPT, ARM_STUB) // Not strictly in ARMv4T, but here for convenience -DEFINE_INSTRUCTION_ARM(ILL, ARM_STUB) // Illegal opcode +DEFINE_INSTRUCTION_ARM(ILL, ARM_ILL) // Illegal opcode DEFINE_INSTRUCTION_ARM(MSR, int c = opcode & 0x00010000;

@@ -858,13 +866,12 @@ #define DECLARE_ARM_BRANCH_BLOCK(EMITTER, NAME) \

DO_256(DECLARE_INSTRUCTION_ARM(EMITTER, NAME)) // TODO: Support coprocessors -#define DECLARE_ARM_LOAD_STORE_COPROCESSOR_BLOCK(EMITTER, NAME, P, U, W, N) \ - DO_8(0), \ - DO_8(0) +#define DECLARE_ARM_LOAD_STORE_COPROCESSOR_BLOCK(EMITTER, NAME, P, U, N, W) \ + DO_8(DECLARE_INSTRUCTION_ARM(EMITTER, NAME)), \ + DO_8(DECLARE_INSTRUCTION_ARM(EMITTER, NAME)) #define DECLARE_ARM_COPROCESSOR_BLOCK(EMITTER, NAME1, NAME2) \ - DO_8(DO_8(DO_INTERLACE(0, 0))), \ - DO_8(DO_8(DO_INTERLACE(0, 0))) + DO_8(DO_8(DO_INTERLACE(DECLARE_INSTRUCTION_ARM(EMITTER, NAME1), DECLARE_INSTRUCTION_ARM(EMITTER, NAME2)))) #define DECLARE_ARM_SWI_BLOCK(EMITTER) \ DO_256(DECLARE_INSTRUCTION_ARM(EMITTER, SWI))

@@ -1125,6 +1132,7 @@ DECLARE_ARM_LOAD_STORE_COPROCESSOR_BLOCK(EMITTER, LDC, P, U, N, ), \

DECLARE_ARM_LOAD_STORE_COPROCESSOR_BLOCK(EMITTER, STC, P, U, N, W), \ DECLARE_ARM_LOAD_STORE_COPROCESSOR_BLOCK(EMITTER, LDC, P, U, N, W), \ DECLARE_ARM_COPROCESSOR_BLOCK(EMITTER, CDP, MCR), \ + DECLARE_ARM_COPROCESSOR_BLOCK(EMITTER, CDP, MRC), \ DECLARE_ARM_SWI_BLOCK(EMITTER) static const ARMInstruction _armTable[0x1000] = {
M src/arm/isa-inlines.hsrc/arm/isa-inlines.h

@@ -64,6 +64,7 @@ cpu->cycles += 4; \

} #define ARM_STUB cpu->board->hitStub(cpu->board, opcode) +#define ARM_ILL cpu->board->hitIllegal(cpu->board, opcode) #define ARM_WRITE_PC \ cpu->gprs[ARM_PC] = (cpu->gprs[ARM_PC] & -WORD_SIZE_ARM) + WORD_SIZE_ARM; \
M src/arm/isa-thumb.csrc/arm/isa-thumb.c

@@ -448,7 +448,7 @@ address -= 4;,

THUMB_STORE_POST_BODY, cpu->gprs[ARM_SP] = address + 4) -DEFINE_INSTRUCTION_THUMB(ILL, ARM_STUB) +DEFINE_INSTRUCTION_THUMB(ILL, ARM_ILL) DEFINE_INSTRUCTION_THUMB(BKPT, ARM_STUB) DEFINE_INSTRUCTION_THUMB(B, int16_t immediate = (opcode & 0x07FF) << 5;

@@ -589,7 +589,7 @@ DO_4(DECLARE_INSTRUCTION_THUMB(EMITTER, SWI)), \

DO_8(DO_4(DECLARE_INSTRUCTION_THUMB(EMITTER, B))), \ DO_8(DO_4(DECLARE_INSTRUCTION_THUMB(EMITTER, ILL))), \ DO_8(DO_4(DECLARE_INSTRUCTION_THUMB(EMITTER, BL1))), \ - DO_8(DO_4(DECLARE_INSTRUCTION_THUMB(EMITTER, BL2))) \ + DO_8(DO_4(DECLARE_INSTRUCTION_THUMB(EMITTER, BL2))) static const ThumbInstruction _thumbTable[0x400] = { DECLARE_THUMB_EMITTER_BLOCK(_ThumbInstruction)
M src/gba/gba.csrc/gba/gba.c

@@ -97,6 +97,7 @@

static void GBAProcessEvents(struct ARMBoard* board); static int32_t GBATimersProcessEvents(struct GBA* gba, int32_t cycles); static void GBAHitStub(struct ARMBoard* board, uint32_t opcode); +static void GBAIllegal(struct ARMBoard* board, uint32_t opcode); static void _checkOverrides(struct GBA* gba, uint32_t code);

@@ -146,6 +147,7 @@ board->d.reset = GBABoardReset;

board->d.processEvents = GBAProcessEvents; board->d.swi16 = GBASwi16; board->d.swi32 = GBASwi32; + board->d.hitIllegal = GBAIllegal; board->d.readCPSR = GBATestIRQ; board->d.hitStub = GBAHitStub; }

@@ -528,7 +530,16 @@ }

#else abort(); #endif +} +void GBAIllegal(struct ARMBoard* board, uint32_t opcode) { + struct GBABoard* gbaBoard = (struct GBABoard*) board; + GBALog(gbaBoard->p, GBA_LOG_WARN, "Illegal opcode: %08x", opcode); +#ifdef USE_DEBUGGER + if (gbaBoard->p->debugger) { + ARMDebuggerEnter(gbaBoard->p->debugger); + } +#endif } void _checkOverrides(struct GBA* gba, uint32_t id) {