DSP/Jit: Explicitly specify scratch register for Update_SR_Register

There were cases when the value register was RDX and thus was being
clobbered as RDX was implictly used as a scratch register.
This commit is contained in:
MerryMage 2017-03-14 19:09:18 +00:00
parent a3557ed199
commit 1020a3cb8e
4 changed files with 23 additions and 21 deletions

View File

@ -221,7 +221,7 @@ private:
void r_ifcc(UDSPInstruction opc);
void r_ret(UDSPInstruction opc);
void Update_SR_Register(Gen::X64Reg val = Gen::EAX);
void Update_SR_Register(Gen::X64Reg val = Gen::EAX, Gen::X64Reg scratch = Gen::EDX);
void get_long_prod(Gen::X64Reg long_prod = Gen::RAX);
void get_long_prod_round_prodl(Gen::X64Reg long_prod = Gen::RAX);
@ -243,7 +243,7 @@ private:
void HandleLoop();
// CC helpers
void Update_SR_Register64(Gen::X64Reg val = Gen::EAX);
void Update_SR_Register64(Gen::X64Reg val = Gen::EAX, Gen::X64Reg scratch = Gen::EDX);
void Update_SR_Register64_Carry(Gen::X64Reg val, Gen::X64Reg carry_ovfl, bool carry_eq = false);
void Update_SR_Register16(Gen::X64Reg val = Gen::EAX);
void Update_SR_Register16_OverS32(Gen::X64Reg val = Gen::EAX);

View File

@ -1382,7 +1382,7 @@ void DSPEmitter::lsrn(const UDSPInstruction opc)
// Update_SR_Register64(dsp_get_long_acc(0));
if (FlagsNeeded())
{
Update_SR_Register64(RDX);
Update_SR_Register64(RDX, RCX);
}
}
@ -1439,7 +1439,7 @@ void DSPEmitter::asrn(const UDSPInstruction opc)
SetJumpTarget(zero);
if (FlagsNeeded())
{
Update_SR_Register64(RDX);
Update_SR_Register64(RDX, RCX);
}
}
@ -1502,7 +1502,7 @@ void DSPEmitter::lsrnrx(const UDSPInstruction opc)
SetJumpTarget(zero);
if (FlagsNeeded())
{
Update_SR_Register64(RDX);
Update_SR_Register64(RDX, RCX);
}
}
@ -1559,7 +1559,7 @@ void DSPEmitter::asrnrx(const UDSPInstruction opc)
// Update_SR_Register64(dsp_get_long_acc(dreg));
if (FlagsNeeded())
{
Update_SR_Register64(RDX);
Update_SR_Register64(RDX, RCX);
}
}
@ -1617,7 +1617,7 @@ void DSPEmitter::lsrnr(const UDSPInstruction opc)
// Update_SR_Register64(dsp_get_long_acc(dreg));
if (FlagsNeeded())
{
Update_SR_Register64(RDX);
Update_SR_Register64(RDX, RCX);
}
}
@ -1672,7 +1672,7 @@ void DSPEmitter::asrnr(const UDSPInstruction opc)
// Update_SR_Register64(dsp_get_long_acc(dreg));
if (FlagsNeeded())
{
Update_SR_Register64(RDX);
Update_SR_Register64(RDX, RCX);
}
}

View File

@ -15,10 +15,12 @@ namespace JIT
{
namespace x86
{
// In: RAX: s64 _Value
// Clobbers RDX
void DSPEmitter::Update_SR_Register(Gen::X64Reg val)
// In: val: s64 _Value
// Clobbers scratch
void DSPEmitter::Update_SR_Register(Gen::X64Reg val, Gen::X64Reg scratch)
{
_assert_(val != scratch);
const OpArg sr_reg = m_gpr.GetReg(DSP_REG_SR);
// // 0x04
// if (_Value == 0) g_dsp.r[DSP_REG_SR] |= SR_ARITH_ZERO;
@ -36,18 +38,18 @@ void DSPEmitter::Update_SR_Register(Gen::X64Reg val)
// // 0x10
// if (_Value != (s32)_Value) g_dsp.r[DSP_REG_SR] |= SR_OVER_S32;
MOVSX(64, 32, RDX, R(val));
CMP(64, R(RDX), R(val));
MOVSX(64, 32, scratch, R(val));
CMP(64, R(scratch), R(val));
FixupBranch noOverS32 = J_CC(CC_E);
OR(16, sr_reg, Imm16(SR_OVER_S32));
SetJumpTarget(noOverS32);
// // 0x20 - Checks if top bits of m are equal
// if (((_Value & 0xc0000000) == 0) || ((_Value & 0xc0000000) == 0xc0000000))
MOV(32, R(RDX), Imm32(0xc0000000));
AND(32, R(val), R(RDX));
MOV(32, R(scratch), Imm32(0xc0000000));
AND(32, R(val), R(scratch));
FixupBranch zeroC = J_CC(CC_Z);
CMP(32, R(val), R(RDX));
CMP(32, R(val), R(scratch));
FixupBranch cC = J_CC(CC_NE);
SetJumpTarget(zeroC);
// g_dsp.r[DSP_REG_SR] |= SR_TOP2BITS;
@ -57,15 +59,15 @@ void DSPEmitter::Update_SR_Register(Gen::X64Reg val)
m_gpr.PutReg(DSP_REG_SR);
}
// In: RAX: s64 _Value
// Clobbers RDX
void DSPEmitter::Update_SR_Register64(Gen::X64Reg val)
// In: val: s64 _Value
// Clobbers scratch
void DSPEmitter::Update_SR_Register64(Gen::X64Reg val, Gen::X64Reg scratch)
{
// g_dsp.r[DSP_REG_SR] &= ~SR_CMP_MASK;
const OpArg sr_reg = m_gpr.GetReg(DSP_REG_SR);
AND(16, sr_reg, Imm16(~SR_CMP_MASK));
m_gpr.PutReg(DSP_REG_SR);
Update_SR_Register(val);
Update_SR_Register(val, scratch);
}
// In: (val): s64 _Value

View File

@ -393,7 +393,7 @@ void DSPEmitter::mulmvz(const UDSPInstruction opc)
// Update_SR_Register64(dsp_get_long_acc(rreg));
if (FlagsNeeded())
{
Update_SR_Register64(RDX);
Update_SR_Register64(RDX, RCX);
}
}