mirror of
https://github.com/dolphin-emu/dolphin.git
synced 2025-07-22 22:00:39 -06:00
Add MOV optimization and MOV_sum
Replaces incarnations of the A=B+C pattern throughout the code so we can apply optimizations consistently.
This commit is contained in:
@ -1540,6 +1540,13 @@ void XEmitter::XOR(int bits, const OpArg& a1, const OpArg& a2)
|
||||
}
|
||||
void XEmitter::MOV(int bits, const OpArg& a1, const OpArg& a2)
|
||||
{
|
||||
// Shortcut to zero a register
|
||||
if (a2.IsZero() && a1.IsSimpleReg() && !flags_locked)
|
||||
{
|
||||
XOR(bits, a1, a1);
|
||||
return;
|
||||
}
|
||||
|
||||
if (a1.IsSimpleReg() && a2.IsSimpleReg() && a1.GetSimpleReg() == a2.GetSimpleReg())
|
||||
ERROR_LOG(DYNA_REC, "Redundant MOV @ %p - bug in JIT?", code);
|
||||
WriteNormalOp(bits, nrmMOV, a1, a2);
|
||||
@ -1572,6 +1579,76 @@ void XEmitter::CMP_or_TEST(int bits, const OpArg& a1, const OpArg& a2)
|
||||
}
|
||||
}
|
||||
|
||||
void XEmitter::MOV_sum(int bits, X64Reg dest, const OpArg& a1, const OpArg& a2)
|
||||
{
|
||||
// This stomps on flags, so ensure they aren't locked
|
||||
_dbg_assert_(DYNA_REC, !flags_locked);
|
||||
|
||||
// Zero shortcuts (note that this can generate no code in the case where a1 == dest && a2 == zero
|
||||
// or a2 == dest && a1 == zero)
|
||||
if (a1.IsZero())
|
||||
{
|
||||
if (!a2.IsSimpleReg() || a2.GetSimpleReg() != dest)
|
||||
{
|
||||
MOV(bits, R(dest), a2);
|
||||
}
|
||||
return;
|
||||
}
|
||||
if (a2.IsZero())
|
||||
{
|
||||
if (!a1.IsSimpleReg() || a1.GetSimpleReg() != dest)
|
||||
{
|
||||
MOV(bits, R(dest), a1);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
// If dest == a1 or dest == a2 we can simplify this
|
||||
if (a1.IsSimpleReg() && a1.GetSimpleReg() == dest)
|
||||
{
|
||||
ADD(bits, R(dest), a2);
|
||||
return;
|
||||
}
|
||||
|
||||
if (a2.IsSimpleReg() && a2.GetSimpleReg() == dest)
|
||||
{
|
||||
ADD(bits, R(dest), a1);
|
||||
return;
|
||||
}
|
||||
|
||||
// TODO: 32-bit optimizations may apply to other bit sizes (confirm)
|
||||
if (bits == 32)
|
||||
{
|
||||
if (a1.IsImm() && a2.IsImm())
|
||||
{
|
||||
MOV(32, R(dest), Imm32(a1.Imm32() + a2.Imm32()));
|
||||
return;
|
||||
}
|
||||
|
||||
if (a1.IsSimpleReg() && a2.IsSimpleReg())
|
||||
{
|
||||
LEA(32, dest, MRegSum(a1.GetSimpleReg(), a2.GetSimpleReg()));
|
||||
return;
|
||||
}
|
||||
|
||||
if (a1.IsSimpleReg() && a2.IsImm())
|
||||
{
|
||||
LEA(32, dest, MDisp(a1.GetSimpleReg(), a2.Imm32()));
|
||||
return;
|
||||
}
|
||||
|
||||
if (a1.IsImm() && a2.IsSimpleReg())
|
||||
{
|
||||
LEA(32, dest, MDisp(a2.GetSimpleReg(), a1.Imm32()));
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
// Fallback
|
||||
MOV(bits, R(dest), a1);
|
||||
ADD(bits, R(dest), a2);
|
||||
}
|
||||
|
||||
void XEmitter::IMUL(int bits, X64Reg regOp, const OpArg& a1, const OpArg& a2)
|
||||
{
|
||||
CheckFlags();
|
||||
|
Reference in New Issue
Block a user