mirror of
https://github.com/FEX-Emu/FEX.git
synced 2025-02-23 16:23:10 +00:00
OpcodeDispatcher: Use NZCVSelect for SelectCC
Massively better codegen. Signed-off-by: Alyssa Rosenzweig <alyssa@rosenzweig.io>
This commit is contained in:
parent
228c7d142e
commit
b187a853e7
@ -852,39 +852,34 @@ OrderedNode *OpDispatchBuilder::SelectMask(OrderedNode *Cmp, uint64_t Mask, bool
|
||||
TrueValue, FalseValue);
|
||||
}
|
||||
|
||||
OrderedNode *OpDispatchBuilder::SelectNZCV(unsigned BitOffset, bool TrueIsNonzero, IR::OpSize ResultSize, OrderedNode *TrueValue, OrderedNode *FalseValue) {
|
||||
return SelectMask(GetNZCV(), 1u << IndexNZCV(BitOffset), TrueIsNonzero, ResultSize, TrueValue, FalseValue);
|
||||
}
|
||||
|
||||
OrderedNode *OpDispatchBuilder::SelectCC(uint8_t OP, IR::OpSize ResultSize, OrderedNode *TrueValue, OrderedNode *FalseValue) {
|
||||
OrderedNode *SrcCond = nullptr;
|
||||
|
||||
auto ZeroConst = _Constant(0);
|
||||
auto OneConst = _Constant(1);
|
||||
|
||||
switch (OP) {
|
||||
case 0x0: { // JO - Jump if OF == 1
|
||||
SrcCond = SelectNZCV(FEXCore::X86State::RFLAG_OF_RAW_LOC, true, ResultSize, TrueValue, FalseValue);
|
||||
SrcCond = _NZCVSelect(ResultSize, CondClassType{COND_FU}, TrueValue, FalseValue);
|
||||
break;
|
||||
}
|
||||
case 0x1:{ // JNO - Jump if OF == 0
|
||||
SrcCond = SelectNZCV(FEXCore::X86State::RFLAG_OF_RAW_LOC, false, ResultSize, TrueValue, FalseValue);
|
||||
SrcCond = _NZCVSelect(ResultSize, CondClassType{COND_FNU}, TrueValue, FalseValue);
|
||||
break;
|
||||
}
|
||||
case 0x2: { // JC - Jump if CF == 1
|
||||
SrcCond = SelectNZCV(FEXCore::X86State::RFLAG_CF_RAW_LOC, true, ResultSize, TrueValue, FalseValue);
|
||||
SrcCond = _NZCVSelect(ResultSize, CondClassType{COND_UGE}, TrueValue, FalseValue);
|
||||
break;
|
||||
}
|
||||
case 0x3: { // JNC - Jump if CF == 0
|
||||
SrcCond = SelectNZCV(FEXCore::X86State::RFLAG_CF_RAW_LOC, false, ResultSize, TrueValue, FalseValue);
|
||||
SrcCond = _NZCVSelect(ResultSize, CondClassType{COND_ULT}, TrueValue, FalseValue);
|
||||
break;
|
||||
}
|
||||
case 0x4: { // JE - Jump if ZF == 1
|
||||
SrcCond = SelectNZCV(FEXCore::X86State::RFLAG_ZF_RAW_LOC, true, ResultSize, TrueValue, FalseValue);
|
||||
SrcCond = _NZCVSelect(ResultSize, CondClassType{COND_EQ}, TrueValue, FalseValue);
|
||||
break;
|
||||
}
|
||||
case 0x5: { // JNE - Jump if ZF == 0
|
||||
SrcCond = SelectNZCV(FEXCore::X86State::RFLAG_ZF_RAW_LOC, false, ResultSize, TrueValue, FalseValue);
|
||||
SrcCond = _NZCVSelect(ResultSize, CondClassType{COND_NEQ}, TrueValue, FalseValue);
|
||||
break;
|
||||
}
|
||||
case 0x6: { // JNA - Jump if CF == 1 || ZC == 1
|
||||
@ -900,11 +895,11 @@ OrderedNode *OpDispatchBuilder::SelectCC(uint8_t OP, IR::OpSize ResultSize, Orde
|
||||
break;
|
||||
}
|
||||
case 0x8: { // JS - Jump if SF == 1
|
||||
SrcCond = SelectNZCV(FEXCore::X86State::RFLAG_SF_RAW_LOC, true, ResultSize, TrueValue, FalseValue);
|
||||
SrcCond = _NZCVSelect(ResultSize, CondClassType{COND_MI}, TrueValue, FalseValue);
|
||||
break;
|
||||
}
|
||||
case 0x9: { // JNS - Jump if SF == 0
|
||||
SrcCond = SelectNZCV(FEXCore::X86State::RFLAG_SF_RAW_LOC, false, ResultSize, TrueValue, FalseValue);
|
||||
SrcCond = _NZCVSelect(ResultSize, CondClassType{COND_PL}, TrueValue, FalseValue);
|
||||
break;
|
||||
}
|
||||
case 0xA: { // JP - Jump if PF == 1
|
||||
@ -917,45 +912,19 @@ OrderedNode *OpDispatchBuilder::SelectCC(uint8_t OP, IR::OpSize ResultSize, Orde
|
||||
break;
|
||||
}
|
||||
case 0xC: { // SF <> OF
|
||||
auto Flag1 = GetRFLAG(FEXCore::X86State::RFLAG_SF_RAW_LOC);
|
||||
auto Flag2 = GetRFLAG(FEXCore::X86State::RFLAG_OF_RAW_LOC);
|
||||
SrcCond = _Select(ResultSize, OpSize::i32Bit, CondClassType{COND_NEQ},
|
||||
Flag1, Flag2, TrueValue, FalseValue);
|
||||
SrcCond = _NZCVSelect(ResultSize, CondClassType{COND_SLT}, TrueValue, FalseValue);
|
||||
break;
|
||||
}
|
||||
case 0xD: { // SF = OF
|
||||
auto Flag1 = GetRFLAG(FEXCore::X86State::RFLAG_SF_RAW_LOC);
|
||||
auto Flag2 = GetRFLAG(FEXCore::X86State::RFLAG_OF_RAW_LOC);
|
||||
SrcCond = _Select(ResultSize, OpSize::i32Bit, CondClassType{COND_EQ},
|
||||
Flag1, Flag2, TrueValue, FalseValue);
|
||||
SrcCond = _NZCVSelect(ResultSize, CondClassType{COND_SGE}, TrueValue, FalseValue);
|
||||
break;
|
||||
}
|
||||
case 0xE: {// ZF = 1 || SF <> OF
|
||||
auto Select1 = SelectNZCV(FEXCore::X86State::RFLAG_ZF_RAW_LOC, true, OpSize::i32Bit,
|
||||
OneConst, ZeroConst);
|
||||
|
||||
auto Flag2 = GetRFLAG(FEXCore::X86State::RFLAG_SF_RAW_LOC);
|
||||
auto Flag3 = GetRFLAG(FEXCore::X86State::RFLAG_OF_RAW_LOC);
|
||||
auto Select2 = _Select(OpSize::i32Bit, OpSize::i32Bit, CondClassType{COND_NEQ},
|
||||
Flag2, Flag3, OneConst, ZeroConst);
|
||||
|
||||
auto Check = _Or(OpSize::i32Bit, Select1, Select2);
|
||||
SrcCond = _Select(ResultSize, OpSize::i32Bit, CondClassType{COND_EQ},
|
||||
Check, OneConst, TrueValue, FalseValue);
|
||||
SrcCond = _NZCVSelect(ResultSize, CondClassType{COND_SLE}, TrueValue, FalseValue);
|
||||
break;
|
||||
}
|
||||
case 0xF: {// ZF = 0 && SF = OF
|
||||
auto Select1 = SelectNZCV(FEXCore::X86State::RFLAG_ZF_RAW_LOC, false, OpSize::i32Bit,
|
||||
OneConst, ZeroConst);
|
||||
|
||||
auto Flag2 = GetRFLAG(FEXCore::X86State::RFLAG_SF_RAW_LOC);
|
||||
auto Flag3 = GetRFLAG(FEXCore::X86State::RFLAG_OF_RAW_LOC);
|
||||
auto Select2 = _Select(OpSize::i32Bit, OpSize::i32Bit, CondClassType{COND_EQ},
|
||||
Flag2, Flag3, OneConst, ZeroConst);
|
||||
|
||||
auto Check = _And(OpSize::i32Bit, Select1, Select2);
|
||||
SrcCond = _Select(ResultSize, OpSize::i32Bit, CondClassType{COND_EQ},
|
||||
Check, OneConst, TrueValue, FalseValue);
|
||||
SrcCond = _NZCVSelect(ResultSize, CondClassType{COND_SGT}, TrueValue, FalseValue);
|
||||
break;
|
||||
}
|
||||
default:
|
||||
|
@ -1449,7 +1449,6 @@ private:
|
||||
}
|
||||
|
||||
OrderedNode *SelectMask(OrderedNode *Cmp, uint64_t Mask, bool Invert, IR::OpSize ResultSize, OrderedNode *TrueValue, OrderedNode *FalseValue);
|
||||
OrderedNode *SelectNZCV(unsigned BitOffset, bool Invert, IR::OpSize ResultSize, OrderedNode *TrueValue, OrderedNode *FalseValue);
|
||||
OrderedNode *SelectCC(uint8_t OP, IR::OpSize ResultSize, OrderedNode *TrueValue, OrderedNode *FalseValue);
|
||||
|
||||
/**
|
||||
|
Loading…
x
Reference in New Issue
Block a user