mirror of
https://github.com/RetroPortingToolKit/psxrecomp
synced 2026-10-25 18:05:12 -04:00
fix(interp): scope load-delay values to BIOS-owned code
This commit is contained in:
@@ -1339,7 +1339,18 @@ static int exec_one_fetched(CPUState *cpu, uint32_t pc, uint32_t insn,
|
||||
* register, not a GPR, so it needs no deferral here. */
|
||||
const uint32_t ld_op = op_field(insn);
|
||||
const uint32_t ld_rt = rt_field(insn);
|
||||
const int is_ld = (ld_op >= 0x20u && ld_op <= 0x26u) && (ld_rt != 0u);
|
||||
const uint32_t pc_phys = pc & 0x1FFFFFFFu;
|
||||
/* OpenBIOS executes cardfasttrack both from ROM and from its low-RAM
|
||||
* kernel copy (for example 0x3554..0x36D4). Its hand-written dependent
|
||||
* load requires the real R3000A value delay. Game-owned dirty RAM crosses
|
||||
* mixed compiled/interpreted boundaries that do not carry this pending
|
||||
* writeback yet, so preserve the historical eager-value contract there. */
|
||||
const int in_bios_rom =
|
||||
pc_phys >= 0x1FC00000u && pc_phys < 0x1FC80000u;
|
||||
const int in_bios_kernel_ram = pc_phys < 0x00010000u;
|
||||
const int is_ld = (in_bios_rom || in_bios_kernel_ram) &&
|
||||
(ld_op >= 0x20u && ld_op <= 0x26u) &&
|
||||
(ld_rt != 0u);
|
||||
const uint32_t ld_before = is_ld ? cpu->gpr[ld_rt] : 0u;
|
||||
|
||||
const int rv = exec_one_fetched_inner(cpu, pc, insn, next_pc_out);
|
||||
|
||||
@@ -97,6 +97,14 @@ def main():
|
||||
dispatch_inner = body(interp, "dirty_ram_dispatch_inner")
|
||||
if "(!current_page_dirty || next_page != current_page)" not in dispatch_inner:
|
||||
raise AssertionError("page fast path does not preserve clean-miss behavior")
|
||||
exec_one = body(interp, "exec_one_fetched")
|
||||
for scope_guard in (
|
||||
"pc_phys >= 0x1FC00000u && pc_phys < 0x1FC80000u",
|
||||
"pc_phys < 0x00010000u",
|
||||
"(in_bios_rom || in_bios_kernel_ram)"):
|
||||
if scope_guard not in exec_one:
|
||||
raise AssertionError(
|
||||
f"load-delay value semantics lost BIOS ownership guard: {scope_guard}")
|
||||
# RFE backend-contract parity: the recompiled rfe and every overlay shard
|
||||
# (ABI v12) call psx_rfe_mark_escape after popping SR, and the generated
|
||||
# trampoline runs psx_rfe_escape_check after each return. The interpreter
|
||||
|
||||
Reference in New Issue
Block a user