GBA: Improve multiboot image detection

This commit is contained in:
Vicki Pfau 2017-11-01 16:57:09 -07:00
parent 1a71b8b11a
commit a2e1641d4e
2 changed files with 44 additions and 9 deletions

View File

@ -5,6 +5,8 @@ Bugfixes:
- GB Video: Only trigger STAT write IRQs when screen is on (fixes mgba.io/i/912)
- GBA Cheats: Fix PARv3 slide codes (fixes mgba.io/i/919)
- GBA Video: OBJWIN can change blend params after OBJ is drawn (fixes mgba.io/i/921)
Misc:
- GBA: Improve multiboot image detection
0.6.1: (2017-10-01)
Bugfixes:

View File

@ -509,16 +509,49 @@ bool GBAIsMB(struct VFile* vf) {
LOAD_32(opcode, 0, &signature);
struct ARMInstructionInfo info;
ARMDecodeARM(opcode, &info);
if (info.branchType != ARM_BRANCH) {
return false;
if (info.branchType == ARM_BRANCH) {
if (info.op1.immediate <= 0) {
return false;
} else if (info.op1.immediate == 28) {
// Ancient toolchain that is known to throw MB detection for a loop
return false;
} else if (info.op1.immediate != 24) {
return true;
}
}
if (info.op1.immediate <= 0) {
return false;
} else if (info.op1.immediate == 28) {
// Ancient toolchain that is known to throw MB detection for a loop
return false;
} else if (info.op1.immediate != 24) {
return true;
uint32_t pc = GBA_MB_MAGIC_OFFSET;
int i;
for (i = 0; i < 80; ++i) {
if (vf->read(vf, &signature, sizeof(signature)) != sizeof(signature)) {
break;
}
pc += 4;
LOAD_32(opcode, 0, &signature);
ARMDecodeARM(opcode, &info);
if (info.mnemonic != ARM_MN_LDR) {
continue;
}
if ((info.operandFormat & ARM_OPERAND_MEMORY) && info.memory.baseReg == ARM_PC && info.memory.format & ARM_MEMORY_IMMEDIATE_OFFSET) {
uint32_t immediate = info.memory.offset.immediate;
if (info.memory.format & ARM_MEMORY_OFFSET_SUBTRACT) {
immediate = -immediate;
}
immediate += pc + 8;
if (vf->seek(vf, immediate, SEEK_SET) < 0) {
break;
}
if (vf->read(vf, &signature, sizeof(signature)) != sizeof(signature)) {
break;
}
LOAD_32(immediate, 0, &signature);
if (vf->seek(vf, pc, SEEK_SET) < 0) {
break;
}
if ((immediate & ~0x7FF) == BASE_WORKING_RAM) {
return true;
}
}
}
// Found a libgba-linked cart...these are a bit harder to detect.
return false;