diff --git a/GXRuntime/include/core/cpu.h b/GXRuntime/include/core/cpu.h index 65f316fc2d..e242b00259 100644 --- a/GXRuntime/include/core/cpu.h +++ b/GXRuntime/include/core/cpu.h @@ -30,7 +30,11 @@ extern "C" { // consumes and resets it (Dolphin chassis: per-dispatch flush into // ppc_state.downcount). Hosts that do not meter guest time may ignore it // (s64: it cannot wrap in any realistic session). -#define GXRUNTIME_CPU_ABI_VERSION 3u +// - ABI v4 adds `cycle_budget` directly after `downcount`, mirroring the +// field DolRecomp added to its generated-code CPUState in f0a86be. The +// prefix is shared with generated code, so the field must sit at the same +// offset on both sides; hosts that do not meter guest time may ignore it. +#define GXRUNTIME_CPU_ABI_VERSION 4u #define GXRUNTIME_CPU_ABI_DOLRECOMP_PREFIX 1u #define GXRUNTIME_CPU_ABI_EXTERNAL_POINTER_EXTENSION 1u @@ -153,6 +157,7 @@ struct CPUState { u32 ram_size; PPCExternalPointer external_pointer; s64 downcount; + s64 cycle_budget; u8* exram; u32 exram_size; PPCSPRRead spr_read; diff --git a/GXRuntime/tests/runtime_tests.c b/GXRuntime/tests/runtime_tests.c index de7d77dcb1..b974ad1444 100644 --- a/GXRuntime/tests/runtime_tests.c +++ b/GXRuntime/tests/runtime_tests.c @@ -27,7 +27,7 @@ #include #include -_Static_assert(GXRUNTIME_CPU_ABI_VERSION == 3u, +_Static_assert(GXRUNTIME_CPU_ABI_VERSION == 4u, "update runtime ABI tests when the CPU ABI changes"); _Static_assert(GXRUNTIME_CPU_ABI_DOLRECOMP_PREFIX == 1u, "GXRuntime generated-code prefix must stay explicit"); @@ -49,6 +49,10 @@ _Static_assert(offsetof(CPUState, downcount) > offsetof(CPUState, external_point "ABI v2 downcount must remain the tail field"); _Static_assert(sizeof(((CPUState*)0)->downcount) == 8u, "downcount is s64 so unconsumed charges cannot wrap"); +_Static_assert(offsetof(CPUState, cycle_budget) > offsetof(CPUState, downcount), + "ABI v4 cycle_budget must follow downcount"); +_Static_assert(sizeof(((CPUState*)0)->cycle_budget) == 8u, + "cycle_budget is s64 to match DolRecomp's generated-code prefix"); _Static_assert(offsetof(CPUState, spr_read) > offsetof(CPUState, exram_size), "ABI v3 callbacks must remain tail fields"); _Static_assert(offsetof(CPUState, cache_control) > offsetof(CPUState, spr_write),