GB Serialize: Fix loading non-BIOS state from BIOS (fixes #1280)

This commit is contained in:
Vicki Pfau 2019-06-06 16:15:07 -07:00
parent 7b12516df4
commit 81476720e2
5 changed files with 31 additions and 8 deletions

View File

@ -30,6 +30,7 @@ Other fixes:
- Qt: Fix FPS target maxing out at 59.727 (fixes mgba.io/i/1421)
- Core: Fix crashes if core directories aren't set
- Qt: Cap audio buffer size to 8192 (fixes mgba.io/i/1433)
- GB Serialize: Fix loading non-BIOS state from BIOS (fixes mgba.io/i/1280)
Misc:
- GBA Savedata: EEPROM performance fixes
- GBA Savedata: Automatically map 1Mbit Flash files as 1Mbit Flash

View File

@ -150,6 +150,7 @@ void GBDestroy(struct GB* gb);
void GBReset(struct LR35902Core* cpu);
void GBSkipBIOS(struct GB* gb);
void GBMapBIOS(struct GB* gb);
void GBUnmapBIOS(struct GB* gb);
void GBDetectModel(struct GB* gb);

View File

@ -419,14 +419,7 @@ void GBReset(struct LR35902Core* cpu) {
gb->biosVf->close(gb->biosVf);
gb->biosVf = NULL;
} else {
gb->biosVf->seek(gb->biosVf, 0, SEEK_SET);
gb->memory.romBase = malloc(GB_SIZE_CART_BANK0);
ssize_t size = gb->biosVf->read(gb->biosVf, gb->memory.romBase, GB_SIZE_CART_BANK0);
memcpy(&gb->memory.romBase[size], &gb->memory.rom[size], GB_SIZE_CART_BANK0 - size);
if (size > 0x100) {
memcpy(&gb->memory.romBase[0x100], &gb->memory.rom[0x100], sizeof(struct GBCartridge));
}
GBMapBIOS(gb);
cpu->a = 0;
cpu->f.packed = 0;
cpu->c = 0;
@ -563,6 +556,16 @@ void GBSkipBIOS(struct GB* gb) {
}
}
void GBMapBIOS(struct GB* gb) {
gb->biosVf->seek(gb->biosVf, 0, SEEK_SET);
gb->memory.romBase = malloc(GB_SIZE_CART_BANK0);
ssize_t size = gb->biosVf->read(gb->biosVf, gb->memory.romBase, GB_SIZE_CART_BANK0);
memcpy(&gb->memory.romBase[size], &gb->memory.rom[size], GB_SIZE_CART_BANK0 - size);
if (size > 0x100) {
memcpy(&gb->memory.romBase[0x100], &gb->memory.rom[0x100], sizeof(struct GBCartridge));
}
}
void GBUnmapBIOS(struct GB* gb) {
if (gb->memory.romBase < gb->memory.rom || gb->memory.romBase > &gb->memory.rom[gb->memory.romSize - 1]) {
free(gb->memory.romBase);

View File

@ -185,8 +185,10 @@ void GBIOReset(struct GB* gb) {
GBIOWrite(gb, REG_NR51, 0xF3);
if (!gb->biosVf) {
GBIOWrite(gb, REG_LCDC, 0x91);
gb->memory.io[0x50] = 1;
} else {
GBIOWrite(gb, REG_LCDC, 0x00);
gb->memory.io[0x50] = 0xFF;
}
GBIOWrite(gb, REG_SCY, 0x00);
GBIOWrite(gb, REG_SCX, 0x00);

View File

@ -135,6 +135,16 @@ bool GBDeserialize(struct GB* gb, const struct GBSerializedState* state) {
if (ucheck16 >= 0x40) {
mLOG(GB_STATE, WARN, "Savestate is corrupted: OCPS is out of range");
}
bool differentBios = !gb->biosVf || gb->model != state->model;
if (state->io[0x50] == 0xFF) {
if (differentBios) {
mLOG(GB_STATE, WARN, "Incompatible savestate, please restart with correct BIOS in %s mode", GBModelToName(state->model));
error = true;
} else {
// TODO: Make it work correctly
mLOG(GB_STATE, WARN, "ILoading savestate in BIOS. This may not work correctly");
}
}
if (error) {
return false;
}
@ -187,6 +197,12 @@ bool GBDeserialize(struct GB* gb, const struct GBSerializedState* state) {
GBTimerDeserialize(&gb->timer, state);
GBAudioDeserialize(&gb->audio, state);
if (gb->memory.io[0x50] == 0xFF) {
GBMapBIOS(gb);
} else {
GBUnmapBIOS(gb);
}
if (gb->model & GB_MODEL_SGB && canSgb) {
GBSGBDeserialize(gb, state);
}