Consolidate all jit integer compare ops into one function.
git-svn-id: https://dolphin-emu.googlecode.com/svn/trunk@1550 8ced0084-cf51-0410-be5f-012b33b47a6e
This commit is contained in:
parent
a44c421d01
commit
060523a805
|
@ -143,8 +143,7 @@ namespace Jit64
|
||||||
void fcmpx(UGeckoInstruction inst);
|
void fcmpx(UGeckoInstruction inst);
|
||||||
void fmrx(UGeckoInstruction inst);
|
void fmrx(UGeckoInstruction inst);
|
||||||
|
|
||||||
void cmpXi(UGeckoInstruction inst);
|
void cmpXX(UGeckoInstruction inst);
|
||||||
void cmpX(UGeckoInstruction inst);
|
|
||||||
|
|
||||||
void cntlzwx(UGeckoInstruction inst);
|
void cntlzwx(UGeckoInstruction inst);
|
||||||
|
|
||||||
|
|
|
@ -147,7 +147,7 @@ namespace Jit64
|
||||||
*/
|
*/
|
||||||
|
|
||||||
// unsigned
|
// unsigned
|
||||||
void cmpXi(UGeckoInstruction inst)
|
void cmpXX(UGeckoInstruction inst)
|
||||||
{
|
{
|
||||||
// USES_CR
|
// USES_CR
|
||||||
#ifdef JIT_OFF_OPTIONS
|
#ifdef JIT_OFF_OPTIONS
|
||||||
|
@ -159,21 +159,40 @@ namespace Jit64
|
||||||
// towards branches.
|
// towards branches.
|
||||||
INSTRUCTION_START;
|
INSTRUCTION_START;
|
||||||
int a = inst.RA;
|
int a = inst.RA;
|
||||||
|
int b = inst.RB;
|
||||||
int crf = inst.CRFD;
|
int crf = inst.CRFD;
|
||||||
int shift = crf * 4;
|
int shift = crf * 4;
|
||||||
Gen::CCFlags less_than, greater_than;
|
Gen::CCFlags less_than, greater_than;
|
||||||
OpArg comparand;
|
OpArg comparand;
|
||||||
if (inst.OPCD == 10) {
|
if (inst.OPCD == 31) {
|
||||||
less_than = CC_B;
|
gpr.Lock(a, b);
|
||||||
greater_than = CC_A;
|
gpr.LoadToX64(a, true, false);
|
||||||
comparand = Imm32(inst.UIMM);
|
comparand = gpr.R(b);
|
||||||
} else {
|
if (inst.SUBOP10 == 32) {
|
||||||
less_than = CC_L;
|
//cmpl
|
||||||
greater_than = CC_G;
|
less_than = CC_B;
|
||||||
comparand = Imm32((s32)(s16)inst.UIMM);
|
greater_than = CC_A;
|
||||||
|
} else {
|
||||||
|
//cmp
|
||||||
|
less_than = CC_L;
|
||||||
|
greater_than = CC_G;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
gpr.KillImmediate(a); // todo, optimize instead, but unlikely to make a difference
|
||||||
|
if (inst.OPCD == 10) {
|
||||||
|
//cmpli
|
||||||
|
less_than = CC_B;
|
||||||
|
greater_than = CC_A;
|
||||||
|
comparand = Imm32(inst.UIMM);
|
||||||
|
} else if (inst.OPCD == 11) {
|
||||||
|
//cmpi
|
||||||
|
less_than = CC_L;
|
||||||
|
greater_than = CC_G;
|
||||||
|
comparand = Imm32((s32)(s16)inst.UIMM);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
gpr.KillImmediate(a); // todo, optimize instead, but unlikely to make a difference
|
|
||||||
CMP(32, gpr.R(a), comparand);
|
CMP(32, gpr.R(a), comparand);
|
||||||
FixupBranch pLesser = J_CC(less_than);
|
FixupBranch pLesser = J_CC(less_than);
|
||||||
FixupBranch pGreater = J_CC(greater_than);
|
FixupBranch pGreater = J_CC(greater_than);
|
||||||
|
@ -190,53 +209,13 @@ namespace Jit64
|
||||||
SetJumpTarget(continue1);
|
SetJumpTarget(continue1);
|
||||||
SetJumpTarget(continue2);
|
SetJumpTarget(continue2);
|
||||||
|
|
||||||
|
gpr.UnlockAll();
|
||||||
|
|
||||||
// TODO: Add extra code at the end for the "taken" case. Jump to it from the matching branches.
|
// TODO: Add extra code at the end for the "taken" case. Jump to it from the matching branches.
|
||||||
// Since it's the last block, some liberties can be taken.
|
// Since it's the last block, some liberties can be taken.
|
||||||
// don't forget to flush registers AFTER the cmp BEFORE the jmp. Flushing doesn't affect flags.
|
// don't forget to flush registers AFTER the cmp BEFORE the jmp. Flushing doesn't affect flags.
|
||||||
}
|
}
|
||||||
|
|
||||||
// signed
|
|
||||||
void cmpX(UGeckoInstruction inst)
|
|
||||||
{
|
|
||||||
// USES_CR
|
|
||||||
#ifdef JIT_OFF_OPTIONS
|
|
||||||
if(Core::g_CoreStartupParameter.bJITOff || Core::g_CoreStartupParameter.bJITIntegerOff)
|
|
||||||
{Default(inst); return;} // turn off from debugger
|
|
||||||
#endif
|
|
||||||
INSTRUCTION_START;
|
|
||||||
int a = inst.RA;
|
|
||||||
int b = inst.RB;
|
|
||||||
int crf = inst.CRFD;
|
|
||||||
int shift = crf * 4;
|
|
||||||
Gen::CCFlags less_than, greater_than;
|
|
||||||
Gen::OpArg comparand = gpr.R(b);
|
|
||||||
if (inst.SUBOP10 == 32) {
|
|
||||||
less_than = CC_B;
|
|
||||||
greater_than = CC_A;
|
|
||||||
} else {
|
|
||||||
less_than = CC_L;
|
|
||||||
greater_than = CC_G;
|
|
||||||
}
|
|
||||||
gpr.Lock(a, b);
|
|
||||||
gpr.LoadToX64(a, true, false);
|
|
||||||
CMP(32, gpr.R(a), comparand);
|
|
||||||
FixupBranch pLesser = J_CC(less_than);
|
|
||||||
FixupBranch pGreater = J_CC(greater_than);
|
|
||||||
// _x86Reg == 0
|
|
||||||
MOV(8, M(&PowerPC::ppcState.cr_fast[crf]), Imm8(0x2)); // _x86Reg == 0
|
|
||||||
FixupBranch continue1 = J();
|
|
||||||
|
|
||||||
SetJumpTarget(pGreater);
|
|
||||||
MOV(8, M(&PowerPC::ppcState.cr_fast[crf]), Imm8(0x4)); // _x86Reg > 0
|
|
||||||
FixupBranch continue2 = J();
|
|
||||||
|
|
||||||
SetJumpTarget(pLesser);
|
|
||||||
MOV(8, M(&PowerPC::ppcState.cr_fast[crf]), Imm8(0x8)); // _x86Reg < 0
|
|
||||||
SetJumpTarget(continue1);
|
|
||||||
SetJumpTarget(continue2);
|
|
||||||
gpr.UnlockAll();
|
|
||||||
}
|
|
||||||
|
|
||||||
void orx(UGeckoInstruction inst)
|
void orx(UGeckoInstruction inst)
|
||||||
{
|
{
|
||||||
#ifdef JIT_OFF_OPTIONS
|
#ifdef JIT_OFF_OPTIONS
|
||||||
|
|
|
@ -141,8 +141,8 @@ GekkoOPTemplate primarytable[] =
|
||||||
|
|
||||||
{7, Interpreter::mulli, Jit64::mulli, {"mulli", OPTYPE_INTEGER, FL_OUT_D | FL_IN_A | FL_RC_BIT, 2}},
|
{7, Interpreter::mulli, Jit64::mulli, {"mulli", OPTYPE_INTEGER, FL_OUT_D | FL_IN_A | FL_RC_BIT, 2}},
|
||||||
{8, Interpreter::subfic, Jit64::subfic, {"subfic", OPTYPE_INTEGER, FL_OUT_D | FL_IN_A | FL_SET_CA}},
|
{8, Interpreter::subfic, Jit64::subfic, {"subfic", OPTYPE_INTEGER, FL_OUT_D | FL_IN_A | FL_SET_CA}},
|
||||||
{10, Interpreter::cmpli, Jit64::cmpXi, {"cmpli", OPTYPE_INTEGER, FL_IN_A | FL_SET_CRn}},
|
{10, Interpreter::cmpli, Jit64::cmpXX, {"cmpli", OPTYPE_INTEGER, FL_IN_A | FL_SET_CRn}},
|
||||||
{11, Interpreter::cmpi, Jit64::cmpXi, {"cmpi", OPTYPE_INTEGER, FL_IN_A | FL_SET_CRn}},
|
{11, Interpreter::cmpi, Jit64::cmpXX, {"cmpi", OPTYPE_INTEGER, FL_IN_A | FL_SET_CRn}},
|
||||||
{12, Interpreter::addic, Jit64::reg_imm, {"addic", OPTYPE_INTEGER, FL_OUT_D | FL_IN_A | FL_SET_CA}},
|
{12, Interpreter::addic, Jit64::reg_imm, {"addic", OPTYPE_INTEGER, FL_OUT_D | FL_IN_A | FL_SET_CA}},
|
||||||
{13, Interpreter::addic_rc, Jit64::reg_imm, {"addic_rc", OPTYPE_INTEGER, FL_OUT_D | FL_IN_A | FL_SET_CR0}},
|
{13, Interpreter::addic_rc, Jit64::reg_imm, {"addic_rc", OPTYPE_INTEGER, FL_OUT_D | FL_IN_A | FL_SET_CR0}},
|
||||||
{14, Interpreter::addi, Jit64::reg_imm, {"addi", OPTYPE_INTEGER, FL_OUT_D | FL_IN_A0}},
|
{14, Interpreter::addi, Jit64::reg_imm, {"addi", OPTYPE_INTEGER, FL_OUT_D | FL_IN_A0}},
|
||||||
|
@ -283,8 +283,8 @@ GekkoOPTemplate table31[] =
|
||||||
{412, Interpreter::orcx, Jit64::Default, {"orcx", OPTYPE_INTEGER, FL_OUT_A | FL_IN_SB | FL_RC_BIT}},
|
{412, Interpreter::orcx, Jit64::Default, {"orcx", OPTYPE_INTEGER, FL_OUT_A | FL_IN_SB | FL_RC_BIT}},
|
||||||
{476, Interpreter::nandx, Jit64::Default, {"nandx", OPTYPE_INTEGER, FL_OUT_A | FL_IN_SB | FL_RC_BIT}},
|
{476, Interpreter::nandx, Jit64::Default, {"nandx", OPTYPE_INTEGER, FL_OUT_A | FL_IN_SB | FL_RC_BIT}},
|
||||||
{284, Interpreter::eqvx, Jit64::Default, {"eqvx", OPTYPE_INTEGER, FL_OUT_A | FL_IN_SB | FL_RC_BIT}},
|
{284, Interpreter::eqvx, Jit64::Default, {"eqvx", OPTYPE_INTEGER, FL_OUT_A | FL_IN_SB | FL_RC_BIT}},
|
||||||
{0, Interpreter::cmp, Jit64::cmpX, {"cmp", OPTYPE_INTEGER, FL_IN_AB | FL_SET_CRn}},
|
{0, Interpreter::cmp, Jit64::cmpXX, {"cmp", OPTYPE_INTEGER, FL_IN_AB | FL_SET_CRn}},
|
||||||
{32, Interpreter::cmpl, Jit64::cmpX, {"cmpl", OPTYPE_INTEGER, FL_IN_AB | FL_SET_CRn}},
|
{32, Interpreter::cmpl, Jit64::cmpXX, {"cmpl", OPTYPE_INTEGER, FL_IN_AB | FL_SET_CRn}},
|
||||||
{26, Interpreter::cntlzwx, Jit64::cntlzwx, {"cntlzwx",OPTYPE_INTEGER, FL_OUT_A | FL_IN_S | FL_RC_BIT}},
|
{26, Interpreter::cntlzwx, Jit64::cntlzwx, {"cntlzwx",OPTYPE_INTEGER, FL_OUT_A | FL_IN_S | FL_RC_BIT}},
|
||||||
{922, Interpreter::extshx, Jit64::extshx, {"extshx", OPTYPE_INTEGER, FL_OUT_A | FL_IN_S | FL_RC_BIT}},
|
{922, Interpreter::extshx, Jit64::extshx, {"extshx", OPTYPE_INTEGER, FL_OUT_A | FL_IN_S | FL_RC_BIT}},
|
||||||
{954, Interpreter::extsbx, Jit64::extsbx, {"extsbx", OPTYPE_INTEGER, FL_OUT_A | FL_IN_S | FL_RC_BIT}},
|
{954, Interpreter::extsbx, Jit64::extsbx, {"extsbx", OPTYPE_INTEGER, FL_OUT_A | FL_IN_S | FL_RC_BIT}},
|
||||||
|
|
|
@ -143,7 +143,7 @@ inline u32 GetCRBit(int bit) {
|
||||||
return (PowerPC::ppcState.cr_fast[bit >> 2] >> (3 - (bit & 3))) & 1;
|
return (PowerPC::ppcState.cr_fast[bit >> 2] >> (3 - (bit & 3))) & 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
// SetCR and GetCR may become fairly slow soon. Should be avoided if possible.
|
// SetCR and GetCR are fairly slow. Should be avoided if possible.
|
||||||
inline void SetCR(u32 new_cr) {
|
inline void SetCR(u32 new_cr) {
|
||||||
PowerPC::ppcState.cr = new_cr;
|
PowerPC::ppcState.cr = new_cr;
|
||||||
PowerPC::ExpandCR();
|
PowerPC::ExpandCR();
|
||||||
|
|
Loading…
Reference in New Issue