From 1e90df7c3bbf1c8ad6be840645c7742c0e65ab93 Mon Sep 17 00:00:00 2001 From: lizzie Date: Tue, 22 Jul 2025 18:32:02 +0100 Subject: [PATCH] [dynarmic] better LRU prioritize empty regs --- .../src/dynarmic/backend/x64/reg_alloc.cpp | 22 ++++++++++++------- 1 file changed, 14 insertions(+), 8 deletions(-) diff --git a/externals/dynarmic/src/dynarmic/backend/x64/reg_alloc.cpp b/externals/dynarmic/src/dynarmic/backend/x64/reg_alloc.cpp index 2a30c52e01..db7c692f07 100644 --- a/externals/dynarmic/src/dynarmic/backend/x64/reg_alloc.cpp +++ b/externals/dynarmic/src/dynarmic/backend/x64/reg_alloc.cpp @@ -415,6 +415,10 @@ void RegAlloc::ReleaseStackSpace(const size_t stack_space) noexcept { } HostLoc RegAlloc::SelectARegister(const boost::container::static_vector& desired_locations) const noexcept { + // TODO(lizzie): Overspill causes issues (reads to 0 and such) on some games, I need to make a testbench + // to later track this down - however I just modified the LRU algo so it prefers empty registers first + // we need to test high register pressure (and spills, maybe 32 regs?) + // Selects the best location out of the available locations. // NOTE: Using last is BAD because new REX prefix for each insn using the last regs // TODO: Actually do LRU or something. Currently we just try to pick something without a value if possible. @@ -428,10 +432,9 @@ HostLoc RegAlloc::SelectARegister(const boost::container::static_vector= HostLoc::R8 && *it <= HostLoc::R15) { @@ -442,17 +445,20 @@ HostLoc RegAlloc::SelectARegister(const boost::container::static_vector Try normal candidate (no REX prefix) - // 2 => Try an empty candidate + // 1 => Try an empty candidate + // 2 => Try normal candidate (no REX prefix) // 3 => Try using a REX prefixed one // We avoid using REX-addressable registers because they add +1 REX prefix which // do we really need? The trade-off may not be worth it. - auto const it_final = it_candidate != desired_locations.cend() - ? it_candidate : it_empty_candidate != desired_locations.cend() - ? it_empty_candidate : it_rex_candidate; + auto const it_final = it_empty_candidate != desired_locations.cend() + ? it_empty_candidate : it_candidate != desired_locations.cend() + ? it_candidate : it_rex_candidate; ASSERT_MSG(it_final != desired_locations.cend(), "All candidate registers have already been allocated"); // Evil magic - increment LRU counter (will wrap at 256) const_cast(this)->LocInfo(*it_final).lru_counter++;