Core: Begin modernizing game override API (fixes #2963)

This commit is contained in:
Vicki Pfau 2023-06-26 04:43:23 -07:00
parent 4d94ab7a38
commit 200e846b81
10 changed files with 50 additions and 33 deletions

View File

@ -16,6 +16,7 @@ Emulation fixes:
- GBA BIOS: Fix clobbering registers with word-sized CpuSet - GBA BIOS: Fix clobbering registers with word-sized CpuSet
- GBA Video: Disable BG target 1 blending when OBJ blending (fixes mgba.io/i/2722) - GBA Video: Disable BG target 1 blending when OBJ blending (fixes mgba.io/i/2722)
Other fixes: Other fixes:
- Core: Fix inconsistencies with setting game-specific overrides (fixes mgba.io/i/2963)
- Debugger: Fix writing to specific segment in command-line debugger - Debugger: Fix writing to specific segment in command-line debugger
- mGUI: Fix cases where an older save state screenshot would be shown. (fixes mgba.io/i/2183) - mGUI: Fix cases where an older save state screenshot would be shown. (fixes mgba.io/i/2183)
- Qt: Fix savestate preview sizes with different scales (fixes mgba.io/i/2560) - Qt: Fix savestate preview sizes with different scales (fixes mgba.io/i/2560)

View File

@ -65,6 +65,7 @@ struct mCore {
void (*setSync)(struct mCore*, struct mCoreSync*); void (*setSync)(struct mCore*, struct mCoreSync*);
void (*loadConfig)(struct mCore*, const struct mCoreConfig*); void (*loadConfig)(struct mCore*, const struct mCoreConfig*);
void (*reloadConfigOption)(struct mCore*, const char* option, const struct mCoreConfig*); void (*reloadConfigOption)(struct mCore*, const char* option, const struct mCoreConfig*);
void (*setOverride)(struct mCore*, const void* override);
void (*baseVideoSize)(const struct mCore*, unsigned* width, unsigned* height); void (*baseVideoSize)(const struct mCore*, unsigned* width, unsigned* height);
void (*currentVideoSize)(const struct mCore*, unsigned* width, unsigned* height); void (*currentVideoSize)(const struct mCore*, unsigned* width, unsigned* height);

View File

@ -99,6 +99,8 @@ struct GBCore {
uint8_t keys; uint8_t keys;
struct mCPUComponent* components[CPU_COMPONENT_MAX]; struct mCPUComponent* components[CPU_COMPONENT_MAX];
const struct Configuration* overrides; const struct Configuration* overrides;
struct GBCartridgeOverride override;
bool hasOverride;
struct mDebuggerPlatform* debuggerPlatform; struct mDebuggerPlatform* debuggerPlatform;
struct mCheatDevice* cheatDevice; struct mCheatDevice* cheatDevice;
struct mCoreMemoryBlock memoryBlocks[8]; struct mCoreMemoryBlock memoryBlocks[8];
@ -124,6 +126,8 @@ static bool _GBCoreInit(struct mCore* core) {
gbcore->logContext = NULL; gbcore->logContext = NULL;
#endif #endif
memcpy(gbcore->memoryBlocks, _GBMemoryBlocks, sizeof(_GBMemoryBlocks)); memcpy(gbcore->memoryBlocks, _GBMemoryBlocks, sizeof(_GBMemoryBlocks));
memset(&gbcore->override, 0, sizeof(gbcore->override));
gbcore->hasOverride = false;
GBCreate(gb); GBCreate(gb);
memset(gbcore->components, 0, sizeof(gbcore->components)); memset(gbcore->components, 0, sizeof(gbcore->components));
@ -364,6 +368,12 @@ static void _GBCoreReloadConfigOption(struct mCore* core, const char* option, co
} }
} }
static void _GBCoreSetOverride(struct mCore* core, const void* override) {
struct GBCore* gbcore = (struct GBCore*) core;
memcpy(&gbcore->override, override, sizeof(gbcore->override));
gbcore->hasOverride = true;
}
static void _GBCoreBaseVideoSize(const struct mCore* core, unsigned* width, unsigned* height) { static void _GBCoreBaseVideoSize(const struct mCore* core, unsigned* width, unsigned* height) {
UNUSED(core); UNUSED(core);
*width = SGB_VIDEO_HORIZONTAL_PIXELS; *width = SGB_VIDEO_HORIZONTAL_PIXELS;
@ -541,14 +551,15 @@ static void _GBCoreReset(struct mCore* core) {
mCoreConfigGetIntValue(&core->config, "useCgbColors", &doColorOverride); mCoreConfigGetIntValue(&core->config, "useCgbColors", &doColorOverride);
} }
struct GBCartridgeOverride override;
const struct GBCartridge* cart = (const struct GBCartridge*) &gb->memory.rom[0x100]; const struct GBCartridge* cart = (const struct GBCartridge*) &gb->memory.rom[0x100];
override.headerCrc32 = doCrc32(cart, sizeof(*cart)); if (!gbcore->hasOverride) {
bool modelOverride = GBOverrideFind(gbcore->overrides, &override) || (doColorOverride && GBOverrideColorFind(&override, doColorOverride)); gbcore->override.headerCrc32 = doCrc32(cart, sizeof(*cart));
if (modelOverride) { gbcore->hasOverride = GBOverrideFind(gbcore->overrides, &gbcore->override) || (doColorOverride && GBOverrideColorFind(&gbcore->override, doColorOverride));
GBOverrideApply(gb, &override);
} }
if (!modelOverride || override.model == GB_MODEL_AUTODETECT) { if (gbcore->hasOverride) {
GBOverrideApply(gb, &gbcore->override);
}
if (!gbcore->hasOverride || gbcore->override.model == GB_MODEL_AUTODETECT) {
const char* modelGB = mCoreConfigGetValue(&core->config, "gb.model"); const char* modelGB = mCoreConfigGetValue(&core->config, "gb.model");
const char* modelSGB = mCoreConfigGetValue(&core->config, "sgb.model"); const char* modelSGB = mCoreConfigGetValue(&core->config, "sgb.model");
const char* modelCGB = mCoreConfigGetValue(&core->config, "cgb.model"); const char* modelCGB = mCoreConfigGetValue(&core->config, "cgb.model");
@ -1280,6 +1291,7 @@ struct mCore* GBCoreCreate(void) {
core->setSync = _GBCoreSetSync; core->setSync = _GBCoreSetSync;
core->loadConfig = _GBCoreLoadConfig; core->loadConfig = _GBCoreLoadConfig;
core->reloadConfigOption = _GBCoreReloadConfigOption; core->reloadConfigOption = _GBCoreReloadConfigOption;
core->setOverride = _GBCoreSetOverride;
core->baseVideoSize = _GBCoreBaseVideoSize; core->baseVideoSize = _GBCoreBaseVideoSize;
core->currentVideoSize = _GBCoreCurrentVideoSize; core->currentVideoSize = _GBCoreCurrentVideoSize;
core->videoScale = _GBCoreVideoScale; core->videoScale = _GBCoreVideoScale;

View File

@ -182,6 +182,8 @@ struct GBACore {
#endif #endif
struct mCPUComponent* components[CPU_COMPONENT_MAX]; struct mCPUComponent* components[CPU_COMPONENT_MAX];
const struct Configuration* overrides; const struct Configuration* overrides;
struct GBACartridgeOverride override;
bool hasOverride;
struct mDebuggerPlatform* debuggerPlatform; struct mDebuggerPlatform* debuggerPlatform;
struct mCheatDevice* cheatDevice; struct mCheatDevice* cheatDevice;
struct GBAAudioMixer* audioMixer; struct GBAAudioMixer* audioMixer;
@ -426,6 +428,12 @@ static void _GBACoreReloadConfigOption(struct mCore* core, const char* option, c
} }
} }
static void _GBACoreSetOverride(struct mCore* core, const void* override) {
struct GBACore* gbacore = (struct GBACore*) core;
memcpy(&gbacore->override, override, sizeof(gbacore->override));
gbacore->hasOverride = true;
}
static void _GBACoreBaseVideoSize(const struct mCore* core, unsigned* width, unsigned* height) { static void _GBACoreBaseVideoSize(const struct mCore* core, unsigned* width, unsigned* height) {
UNUSED(core); UNUSED(core);
*width = GBA_VIDEO_HORIZONTAL_PIXELS; *width = GBA_VIDEO_HORIZONTAL_PIXELS;
@ -678,7 +686,11 @@ static void _GBACoreReset(struct mCore* core) {
if (!forceGbp) { if (!forceGbp) {
gba->memory.hw.devices &= ~HW_GB_PLAYER_DETECTION; gba->memory.hw.devices &= ~HW_GB_PLAYER_DETECTION;
} }
GBAOverrideApplyDefaults(gba, gbacore->overrides); if (gbacore->hasOverride) {
GBAOverrideApply(gba, &gbacore->override);
} else {
GBAOverrideApplyDefaults(gba, gbacore->overrides);
}
if (forceGbp) { if (forceGbp) {
gba->memory.hw.devices |= HW_GB_PLAYER_DETECTION; gba->memory.hw.devices |= HW_GB_PLAYER_DETECTION;
} }
@ -1405,6 +1417,7 @@ struct mCore* GBACoreCreate(void) {
core->setSync = _GBACoreSetSync; core->setSync = _GBACoreSetSync;
core->loadConfig = _GBACoreLoadConfig; core->loadConfig = _GBACoreLoadConfig;
core->reloadConfigOption = _GBACoreReloadConfigOption; core->reloadConfigOption = _GBACoreReloadConfigOption;
core->setOverride = _GBACoreSetOverride;
core->baseVideoSize = _GBACoreBaseVideoSize; core->baseVideoSize = _GBACoreBaseVideoSize;
core->currentVideoSize = _GBACoreCurrentVideoSize; core->currentVideoSize = _GBACoreCurrentVideoSize;
core->videoScale = _GBACoreVideoScale; core->videoScale = _GBACoreVideoScale;

View File

@ -79,6 +79,11 @@ CoreController::CoreController(mCore* core, QObject* parent)
controller->updatePlayerSave(); controller->updatePlayerSave();
} }
if (controller->m_override) {
controller->m_override->identify(context->core);
context->core->setOverride(context->core, controller->m_override->raw());
}
QMetaObject::invokeMethod(controller, "started"); QMetaObject::invokeMethod(controller, "started");
}; };
@ -88,11 +93,6 @@ CoreController::CoreController(mCore* core, QObject* parent)
action(); action();
} }
if (controller->m_override) {
controller->m_override->identify(context->core);
controller->m_override->apply(context->core);
}
controller->m_resetActions.clear(); controller->m_resetActions.clear();
controller->m_frameCounter = -1; controller->m_frameCounter = -1;

View File

@ -10,17 +10,6 @@
using namespace QGBA; using namespace QGBA;
void GBAOverride::apply(struct mCore* core) {
if (core->platform(core) != mPLATFORM_GBA) {
return;
}
GBA* gba = static_cast<GBA*>(core->board);
if (!vbaBugCompatSet) {
override.vbaBugCompat = gba->vbaBugCompat;
}
GBAOverrideApply(gba, &override);
}
void GBAOverride::identify(const struct mCore* core) { void GBAOverride::identify(const struct mCore* core) {
if (core->platform(core) != mPLATFORM_GBA) { if (core->platform(core) != mPLATFORM_GBA) {
return; return;
@ -33,3 +22,7 @@ void GBAOverride::identify(const struct mCore* core) {
void GBAOverride::save(struct Configuration* config) const { void GBAOverride::save(struct Configuration* config) const {
GBAOverrideSave(config, &override); GBAOverrideSave(config, &override);
} }
const void* GBAOverride::raw() const {
return &override;
}

View File

@ -13,9 +13,9 @@ namespace QGBA {
class GBAOverride : public Override { class GBAOverride : public Override {
public: public:
void apply(struct mCore*) override;
void identify(const struct mCore*) override; void identify(const struct mCore*) override;
void save(struct Configuration*) const override; void save(struct Configuration*) const override;
const void* raw() const override;
struct GBACartridgeOverride override; struct GBACartridgeOverride override;
bool vbaBugCompatSet; bool vbaBugCompatSet;

View File

@ -11,13 +11,6 @@
using namespace QGBA; using namespace QGBA;
void GBOverride::apply(struct mCore* core) {
if (core->platform(core) != mPLATFORM_GB) {
return;
}
GBOverrideApply(static_cast<GB*>(core->board), &override);
}
void GBOverride::identify(const struct mCore* core) { void GBOverride::identify(const struct mCore* core) {
if (core->platform(core) != mPLATFORM_GB) { if (core->platform(core) != mPLATFORM_GB) {
return; return;
@ -32,3 +25,7 @@ void GBOverride::identify(const struct mCore* core) {
void GBOverride::save(struct Configuration* config) const { void GBOverride::save(struct Configuration* config) const {
GBOverrideSave(config, &override); GBOverrideSave(config, &override);
} }
const void* GBOverride::raw() const {
return &override;
}

View File

@ -13,9 +13,9 @@ namespace QGBA {
class GBOverride : public Override { class GBOverride : public Override {
public: public:
void apply(struct mCore*) override;
void identify(const struct mCore*) override; void identify(const struct mCore*) override;
void save(struct Configuration*) const override; void save(struct Configuration*) const override;
const void* raw() const override;
struct GBCartridgeOverride override; struct GBCartridgeOverride override;
}; };

View File

@ -14,9 +14,9 @@ class Override {
public: public:
virtual ~Override() {} virtual ~Override() {}
virtual void apply(struct mCore*) = 0;
virtual void identify(const struct mCore*) = 0; virtual void identify(const struct mCore*) = 0;
virtual void save(struct Configuration*) const = 0; virtual void save(struct Configuration*) const = 0;
virtual const void* raw() const = 0;
}; };
} }