diff --git a/Source/Core/Core/PowerPC/JitArm64/JitArm64_RegCache.cpp b/Source/Core/Core/PowerPC/JitArm64/JitArm64_RegCache.cpp index fdd47908079f..6f86c69aabb4 100644 --- a/Source/Core/Core/PowerPC/JitArm64/JitArm64_RegCache.cpp +++ b/Source/Core/Core/PowerPC/JitArm64/JitArm64_RegCache.cpp @@ -742,6 +742,17 @@ bool Arm64FPRCache::IsCalleeSaved(ARM64Reg reg) const return std::find(callee_regs.begin(), callee_regs.end(), reg) != callee_regs.end(); } +bool Arm64FPRCache::IsTopHalfUsed(ARM64Reg reg) const +{ + for (const OpArg& r : m_guest_registers) + { + if (r.GetReg() != ARM64Reg::INVALID_REG && DecodeReg(r.GetReg()) == DecodeReg(reg)) + return r.GetType() == RegType::Register; + } + + return false; +} + void Arm64FPRCache::FlushRegister(size_t preg, bool maintain_state, ARM64Reg tmp_reg) { OpArg& reg = m_guest_registers[preg]; @@ -846,7 +857,7 @@ BitSet32 Arm64FPRCache::GetCallerSavedUsed() const BitSet32 registers(0); for (const auto& it : m_host_registers) { - if (it.IsLocked()) + if (it.IsLocked() && (!IsCalleeSaved(it.GetReg()) || IsTopHalfUsed(it.GetReg()))) registers[DecodeReg(it.GetReg())] = true; } return registers; diff --git a/Source/Core/Core/PowerPC/JitArm64/JitArm64_RegCache.h b/Source/Core/Core/PowerPC/JitArm64/JitArm64_RegCache.h index a8a110b1e121..9be43a3a6e3f 100644 --- a/Source/Core/Core/PowerPC/JitArm64/JitArm64_RegCache.h +++ b/Source/Core/Core/PowerPC/JitArm64/JitArm64_RegCache.h @@ -351,6 +351,7 @@ class Arm64FPRCache : public Arm64RegCache private: bool IsCalleeSaved(Arm64Gen::ARM64Reg reg) const; + bool IsTopHalfUsed(Arm64Gen::ARM64Reg reg) const; void FlushRegisters(BitSet32 regs, bool maintain_state, Arm64Gen::ARM64Reg tmp_reg); };