Added SHRD/SHLD x86 emitters, further optimized srawx
This commit is contained in:
parent
31ff1907a4
commit
79ca43226c
|
@ -867,6 +867,69 @@ void XEmitter::BTS(int bits, OpArg dest, OpArg index) {WriteBitTest(bits, dest,
|
||||||
void XEmitter::BTR(int bits, OpArg dest, OpArg index) {WriteBitTest(bits, dest, index, 6);}
|
void XEmitter::BTR(int bits, OpArg dest, OpArg index) {WriteBitTest(bits, dest, index, 6);}
|
||||||
void XEmitter::BTC(int bits, OpArg dest, OpArg index) {WriteBitTest(bits, dest, index, 7);}
|
void XEmitter::BTC(int bits, OpArg dest, OpArg index) {WriteBitTest(bits, dest, index, 7);}
|
||||||
|
|
||||||
|
//shift can be either imm8 or cl
|
||||||
|
void XEmitter::SHRD(int bits, OpArg dest, OpArg src, OpArg shift)
|
||||||
|
{
|
||||||
|
bool writeImm = false;
|
||||||
|
if (dest.IsImm())
|
||||||
|
{
|
||||||
|
_assert_msg_(DYNA_REC, 0, "SHRD - can't use imms as destination");
|
||||||
|
}
|
||||||
|
if (!src.IsSimpleReg())
|
||||||
|
{
|
||||||
|
_assert_msg_(DYNA_REC, 0, "SHRD - must use simple register as source");
|
||||||
|
}
|
||||||
|
if ((shift.IsSimpleReg() && shift.GetSimpleReg() != ECX) || (shift.IsImm() && shift.GetImmBits() != 8))
|
||||||
|
{
|
||||||
|
_assert_msg_(DYNA_REC, 0, "SHRD - illegal shift");
|
||||||
|
}
|
||||||
|
if (bits == 16) Write8(0x66);
|
||||||
|
X64Reg operand = src.GetSimpleReg();
|
||||||
|
dest.WriteRex(this, bits, bits, operand);
|
||||||
|
if (shift.GetImmBits() == 8)
|
||||||
|
{
|
||||||
|
Write8(0x0F); Write8(0xAC);
|
||||||
|
dest.WriteRest(this, 1, operand);
|
||||||
|
Write8((u8)shift.offset);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
Write8(0x0F); Write8(0xAD);
|
||||||
|
dest.WriteRest(this, 0, operand);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void XEmitter::SHLD(int bits, OpArg dest, OpArg src, OpArg shift)
|
||||||
|
{
|
||||||
|
bool writeImm = false;
|
||||||
|
if (dest.IsImm())
|
||||||
|
{
|
||||||
|
_assert_msg_(DYNA_REC, 0, "SHLD - can't use imms as destination");
|
||||||
|
}
|
||||||
|
if (!src.IsSimpleReg())
|
||||||
|
{
|
||||||
|
_assert_msg_(DYNA_REC, 0, "SHLD - must use simple register as source");
|
||||||
|
}
|
||||||
|
if ((shift.IsSimpleReg() && shift.GetSimpleReg() != ECX) || (shift.IsImm() && shift.GetImmBits() != 8))
|
||||||
|
{
|
||||||
|
_assert_msg_(DYNA_REC, 0, "SHLD - illegal shift");
|
||||||
|
}
|
||||||
|
if (bits == 16) Write8(0x66);
|
||||||
|
X64Reg operand = src.GetSimpleReg();
|
||||||
|
dest.WriteRex(this, bits, bits, operand);
|
||||||
|
if (shift.GetImmBits() == 8)
|
||||||
|
{
|
||||||
|
Write8(0x0F); Write8(0xA4);
|
||||||
|
dest.WriteRest(this, 1, operand);
|
||||||
|
Write8((u8)shift.offset);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
Write8(0x0F); Write8(0xA5);
|
||||||
|
dest.WriteRest(this, 0, operand);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void OpArg::WriteSingleByteOp(XEmitter *emit, u8 op, X64Reg _operandReg, int bits)
|
void OpArg::WriteSingleByteOp(XEmitter *emit, u8 op, X64Reg _operandReg, int bits)
|
||||||
{
|
{
|
||||||
if (bits == 16)
|
if (bits == 16)
|
||||||
|
|
|
@ -381,6 +381,10 @@ public:
|
||||||
void BTR(int bits, OpArg dest, OpArg index);
|
void BTR(int bits, OpArg dest, OpArg index);
|
||||||
void BTC(int bits, OpArg dest, OpArg index);
|
void BTC(int bits, OpArg dest, OpArg index);
|
||||||
|
|
||||||
|
// Double-Precision Shift
|
||||||
|
void SHRD(int bits, OpArg dest, OpArg src, OpArg shift);
|
||||||
|
void SHLD(int bits, OpArg dest, OpArg src, OpArg shift);
|
||||||
|
|
||||||
// Extend EAX into EDX in various ways
|
// Extend EAX into EDX in various ways
|
||||||
void CWD(int bits = 16);
|
void CWD(int bits = 16);
|
||||||
inline void CDQ() {CWD(32);}
|
inline void CDQ() {CWD(32);}
|
||||||
|
|
|
@ -1758,10 +1758,9 @@ void Jit64::srawx(UGeckoInstruction inst)
|
||||||
MOV(32, gpr.R(a), gpr.R(s));
|
MOV(32, gpr.R(a), gpr.R(s));
|
||||||
TEST(32, R(ECX), Imm32(32));
|
TEST(32, R(ECX), Imm32(32));
|
||||||
FixupBranch topBitSet = J_CC(CC_NZ);
|
FixupBranch topBitSet = J_CC(CC_NZ);
|
||||||
LEA(32, EAX, MComplex(gpr.RX(a), gpr.RX(a), 1, 0));
|
XOR(32, R(EAX), R(EAX));
|
||||||
|
SHRD(32, R(EAX), gpr.R(a), R(ECX));
|
||||||
SAR(32, gpr.R(a), R(ECX));
|
SAR(32, gpr.R(a), R(ECX));
|
||||||
NOT(32, R(ECX));
|
|
||||||
SHL(32, R(EAX), R(ECX));
|
|
||||||
TEST(32, R(EAX), gpr.R(a));
|
TEST(32, R(EAX), gpr.R(a));
|
||||||
FixupBranch nocarry1 = J_CC(CC_Z);
|
FixupBranch nocarry1 = J_CC(CC_Z);
|
||||||
JitSetCA();
|
JitSetCA();
|
||||||
|
|
Loading…
Reference in New Issue