JitArm64: Fix single precision
This commit is contained in:
parent
cb5be45f72
commit
cfe65e0e91
|
@ -42,6 +42,7 @@ void JitArm64::faddsx(UGeckoInstruction inst)
|
|||
ARM64Reg VD = fpr.RW(d, REG_DUP);
|
||||
|
||||
m_float_emit.FADD(EncodeRegToDouble(VD), EncodeRegToDouble(VA), EncodeRegToDouble(VB));
|
||||
fpr.FixSinglePrecision(d);
|
||||
}
|
||||
|
||||
void JitArm64::faddx(UGeckoInstruction inst)
|
||||
|
@ -75,6 +76,7 @@ void JitArm64::fmaddsx(UGeckoInstruction inst)
|
|||
|
||||
m_float_emit.FMUL(EncodeRegToDouble(V0), EncodeRegToDouble(VA), EncodeRegToDouble(VC));
|
||||
m_float_emit.FADD(EncodeRegToDouble(VD), EncodeRegToDouble(V0), EncodeRegToDouble(VB));
|
||||
fpr.FixSinglePrecision(d);
|
||||
|
||||
fpr.Unlock(V0);
|
||||
}
|
||||
|
@ -125,6 +127,7 @@ void JitArm64::fmsubsx(UGeckoInstruction inst)
|
|||
|
||||
m_float_emit.FMUL(EncodeRegToDouble(V0), EncodeRegToDouble(VA), EncodeRegToDouble(VC));
|
||||
m_float_emit.FSUB(EncodeRegToDouble(VD), EncodeRegToDouble(V0), EncodeRegToDouble(VB));
|
||||
fpr.FixSinglePrecision(d);
|
||||
|
||||
fpr.Unlock(V0);
|
||||
}
|
||||
|
@ -158,6 +161,7 @@ void JitArm64::fmulsx(UGeckoInstruction inst)
|
|||
ARM64Reg VD = fpr.RW(d, REG_DUP);
|
||||
|
||||
m_float_emit.FMUL(EncodeRegToDouble(VD), EncodeRegToDouble(VA), EncodeRegToDouble(VC));
|
||||
fpr.FixSinglePrecision(d);
|
||||
}
|
||||
|
||||
void JitArm64::fmulx(UGeckoInstruction inst)
|
||||
|
@ -221,6 +225,7 @@ void JitArm64::fnmaddsx(UGeckoInstruction inst)
|
|||
m_float_emit.FMUL(EncodeRegToDouble(V0), EncodeRegToDouble(VA), EncodeRegToDouble(VC));
|
||||
m_float_emit.FADD(EncodeRegToDouble(VD), EncodeRegToDouble(V0), EncodeRegToDouble(VB));
|
||||
m_float_emit.FNEG(EncodeRegToDouble(VD), EncodeRegToDouble(VD));
|
||||
fpr.FixSinglePrecision(d);
|
||||
|
||||
fpr.Unlock(V0);
|
||||
}
|
||||
|
@ -258,6 +263,7 @@ void JitArm64::fnmsubsx(UGeckoInstruction inst)
|
|||
m_float_emit.FMUL(EncodeRegToDouble(V0), EncodeRegToDouble(VA), EncodeRegToDouble(VC));
|
||||
m_float_emit.FSUB(EncodeRegToDouble(VD), EncodeRegToDouble(V0), EncodeRegToDouble(VB));
|
||||
m_float_emit.FNEG(EncodeRegToDouble(VD), EncodeRegToDouble(VD));
|
||||
fpr.FixSinglePrecision(d);
|
||||
|
||||
fpr.Unlock(V0);
|
||||
}
|
||||
|
@ -308,6 +314,7 @@ void JitArm64::fsubsx(UGeckoInstruction inst)
|
|||
ARM64Reg VD = fpr.RW(d, REG_DUP);
|
||||
|
||||
m_float_emit.FSUB(EncodeRegToDouble(VD), EncodeRegToDouble(VA), EncodeRegToDouble(VB));
|
||||
fpr.FixSinglePrecision(d);
|
||||
}
|
||||
|
||||
void JitArm64::fsubx(UGeckoInstruction inst)
|
||||
|
@ -476,4 +483,5 @@ void JitArm64::fdivsx(UGeckoInstruction inst)
|
|||
ARM64Reg VD = fpr.RW(d, REG_DUP);
|
||||
|
||||
m_float_emit.FDIV(EncodeRegToDouble(VD), EncodeRegToDouble(VA), EncodeRegToDouble(VB));
|
||||
fpr.FixSinglePrecision(d);
|
||||
}
|
||||
|
|
|
@ -43,6 +43,7 @@ void JitArm64::ps_add(UGeckoInstruction inst)
|
|||
ARM64Reg VD = fpr.RW(d, REG_REG);
|
||||
|
||||
m_float_emit.FADD(64, VD, VA, VB);
|
||||
fpr.FixSinglePrecision(d);
|
||||
}
|
||||
|
||||
void JitArm64::ps_div(UGeckoInstruction inst)
|
||||
|
@ -58,6 +59,7 @@ void JitArm64::ps_div(UGeckoInstruction inst)
|
|||
ARM64Reg VD = fpr.RW(d, REG_REG);
|
||||
|
||||
m_float_emit.FDIV(64, VD, VA, VB);
|
||||
fpr.FixSinglePrecision(d);
|
||||
}
|
||||
|
||||
void JitArm64::ps_madd(UGeckoInstruction inst)
|
||||
|
@ -76,6 +78,7 @@ void JitArm64::ps_madd(UGeckoInstruction inst)
|
|||
|
||||
m_float_emit.FMUL(64, V0, VA, VC);
|
||||
m_float_emit.FADD(64, VD, V0, VB);
|
||||
fpr.FixSinglePrecision(d);
|
||||
|
||||
fpr.Unlock(V0);
|
||||
}
|
||||
|
@ -97,6 +100,7 @@ void JitArm64::ps_madds0(UGeckoInstruction inst)
|
|||
m_float_emit.DUP(64, V0, VC, 0);
|
||||
m_float_emit.FMUL(64, V0, V0, VA);
|
||||
m_float_emit.FADD(64, VD, V0, VB);
|
||||
fpr.FixSinglePrecision(d);
|
||||
|
||||
fpr.Unlock(V0);
|
||||
}
|
||||
|
@ -118,6 +122,7 @@ void JitArm64::ps_madds1(UGeckoInstruction inst)
|
|||
m_float_emit.DUP(64, V0, VC, 1);
|
||||
m_float_emit.FMUL(64, V0, V0, VA);
|
||||
m_float_emit.FADD(64, VD, V0, VB);
|
||||
fpr.FixSinglePrecision(d);
|
||||
|
||||
fpr.Unlock(V0);
|
||||
}
|
||||
|
@ -225,6 +230,7 @@ void JitArm64::ps_mul(UGeckoInstruction inst)
|
|||
ARM64Reg VD = fpr.RW(d, REG_REG);
|
||||
|
||||
m_float_emit.FMUL(64, VD, VA, VC);
|
||||
fpr.FixSinglePrecision(d);
|
||||
}
|
||||
|
||||
void JitArm64::ps_muls0(UGeckoInstruction inst)
|
||||
|
@ -242,6 +248,7 @@ void JitArm64::ps_muls0(UGeckoInstruction inst)
|
|||
|
||||
m_float_emit.DUP(64, V0, VC, 0);
|
||||
m_float_emit.FMUL(64, VD, VA, V0);
|
||||
fpr.FixSinglePrecision(d);
|
||||
fpr.Unlock(V0);
|
||||
}
|
||||
|
||||
|
@ -260,6 +267,7 @@ void JitArm64::ps_muls1(UGeckoInstruction inst)
|
|||
|
||||
m_float_emit.DUP(64, V0, VC, 1);
|
||||
m_float_emit.FMUL(64, VD, VA, V0);
|
||||
fpr.FixSinglePrecision(d);
|
||||
fpr.Unlock(V0);
|
||||
}
|
||||
|
||||
|
@ -279,6 +287,7 @@ void JitArm64::ps_msub(UGeckoInstruction inst)
|
|||
|
||||
m_float_emit.FMUL(64, V0, VA, VC);
|
||||
m_float_emit.FSUB(64, VD, V0, VB);
|
||||
fpr.FixSinglePrecision(d);
|
||||
|
||||
fpr.Unlock(V0);
|
||||
}
|
||||
|
@ -329,6 +338,7 @@ void JitArm64::ps_nmadd(UGeckoInstruction inst)
|
|||
m_float_emit.FMUL(64, V0, VA, VC);
|
||||
m_float_emit.FADD(64, VD, V0, VB);
|
||||
m_float_emit.FNEG(64, VD, VD);
|
||||
fpr.FixSinglePrecision(d);
|
||||
|
||||
fpr.Unlock(V0);
|
||||
}
|
||||
|
@ -350,6 +360,7 @@ void JitArm64::ps_nmsub(UGeckoInstruction inst)
|
|||
m_float_emit.FMUL(64, V0, VA, VC);
|
||||
m_float_emit.FSUB(64, VD, V0, VB);
|
||||
m_float_emit.FNEG(64, VD, VD);
|
||||
fpr.FixSinglePrecision(d);
|
||||
|
||||
fpr.Unlock(V0);
|
||||
}
|
||||
|
@ -366,6 +377,7 @@ void JitArm64::ps_res(UGeckoInstruction inst)
|
|||
ARM64Reg VD = fpr.RW(d, REG_REG);
|
||||
|
||||
m_float_emit.FRSQRTE(64, VD, VB);
|
||||
fpr.FixSinglePrecision(d);
|
||||
}
|
||||
|
||||
void JitArm64::ps_sel(UGeckoInstruction inst)
|
||||
|
@ -409,6 +421,7 @@ void JitArm64::ps_sub(UGeckoInstruction inst)
|
|||
ARM64Reg VD = fpr.RW(d, REG_REG);
|
||||
|
||||
m_float_emit.FSUB(64, VD, VA, VB);
|
||||
fpr.FixSinglePrecision(d);
|
||||
}
|
||||
|
||||
void JitArm64::ps_sum0(UGeckoInstruction inst)
|
||||
|
@ -436,6 +449,7 @@ void JitArm64::ps_sum0(UGeckoInstruction inst)
|
|||
m_float_emit.FADD(64, V0, V0, VA);
|
||||
m_float_emit.INS(64, VD, 0, V0, 0);
|
||||
}
|
||||
fpr.FixSinglePrecision(d);
|
||||
|
||||
fpr.Unlock(V0);
|
||||
}
|
||||
|
@ -465,6 +479,7 @@ void JitArm64::ps_sum1(UGeckoInstruction inst)
|
|||
m_float_emit.FADD(64, V0, V0, VB);
|
||||
m_float_emit.INS(64, VD, 1, V0, 1);
|
||||
}
|
||||
fpr.FixSinglePrecision(d);
|
||||
|
||||
fpr.Unlock(V0);
|
||||
}
|
||||
|
|
|
@ -559,3 +559,21 @@ BitSet32 Arm64FPRCache::GetCallerSavedUsed()
|
|||
registers[it.GetReg() - Q0] = 1;
|
||||
return registers;
|
||||
}
|
||||
|
||||
void Arm64FPRCache::FixSinglePrecision(u32 preg)
|
||||
{
|
||||
ARM64Reg host_reg = m_guest_registers[preg].GetReg();
|
||||
switch (m_guest_registers[preg].GetType())
|
||||
{
|
||||
case REG_DUP: // only PS0 needs to be converted
|
||||
m_float_emit->FCVT(32, 64, EncodeRegToDouble(host_reg), EncodeRegToDouble(host_reg));
|
||||
m_float_emit->FCVT(64, 32, EncodeRegToDouble(host_reg), EncodeRegToDouble(host_reg));
|
||||
break;
|
||||
case REG_REG: // PS0 and PS1 needs to be converted
|
||||
m_float_emit->FCVTN(32, EncodeRegToDouble(host_reg), EncodeRegToDouble(host_reg));
|
||||
m_float_emit->FCVTL(64, EncodeRegToDouble(host_reg), EncodeRegToDouble(host_reg));
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -277,6 +277,8 @@ public:
|
|||
|
||||
BitSet32 GetCallerSavedUsed() override;
|
||||
|
||||
void FixSinglePrecision(u32 preg);
|
||||
|
||||
protected:
|
||||
// Get the order of the host registers
|
||||
void GetAllocationOrder();
|
||||
|
|
Loading…
Reference in New Issue