mirror of
https://github.com/FEX-Emu/FEX.git
synced 2026-10-23 07:00:45 +02:00
Merge pull request #550 from FEX-Emu/skmp/improve-dead-flags
DFSE: Fix dead clag calculation, Extend InvalidateFlags
This commit is contained in:
3 files changed
+36
-10
No files matched your search
+24
-2
@@ -146,7 +146,7 @@ void OpDispatchBuilder::RETOp(OpcodeArgs) {
|
||||
|
||||
// ABI Optimization: Flags don't survive calls or rets
|
||||
if (CTX->Config.ABILocalFlags) {
|
||||
_InvalidateFlags();
|
||||
_InvalidateFlags(~0UL); // all flags
|
||||
}
|
||||
|
||||
auto Constant = _Constant(GPRSize);
|
||||
@@ -630,7 +630,7 @@ void OpDispatchBuilder::CALLOp(OpcodeArgs) {
|
||||
|
||||
// ABI Optimization: Flags don't survive calls or rets
|
||||
if (CTX->Config.ABILocalFlags) {
|
||||
_InvalidateFlags();
|
||||
_InvalidateFlags(~0UL); // all flags
|
||||
}
|
||||
|
||||
auto ConstantPC = _Constant(Op->PC + Op->InstSize);
|
||||
@@ -4857,6 +4857,8 @@ void OpDispatchBuilder::GenerateFlags_ADC(FEXCore::X86Tables::DecodedOp Op, Orde
|
||||
|
||||
auto XorOp = _Xor(PopCountOp, _Constant(1));
|
||||
SetRFLAG<FEXCore::X86State::RFLAG_PF_LOC>(XorOp);
|
||||
} else {
|
||||
_InvalidateFlags(1UL << FEXCore::X86State::RFLAG_PF_LOC);
|
||||
}
|
||||
|
||||
// ZF
|
||||
@@ -4924,6 +4926,8 @@ void OpDispatchBuilder::GenerateFlags_SBB(FEXCore::X86Tables::DecodedOp Op, Orde
|
||||
|
||||
auto XorOp = _Xor(PopCountOp, _Constant(1));
|
||||
SetRFLAG<FEXCore::X86State::RFLAG_PF_LOC>(XorOp);
|
||||
} else {
|
||||
_InvalidateFlags(1UL << FEXCore::X86State::RFLAG_PF_LOC);
|
||||
}
|
||||
|
||||
// ZF
|
||||
@@ -4990,6 +4994,8 @@ void OpDispatchBuilder::GenerateFlags_SUB(FEXCore::X86Tables::DecodedOp Op, Orde
|
||||
auto PopCountOp = _Popcount(_And(Res, EightBitMask));
|
||||
auto XorOp = _Xor(PopCountOp, _Constant(1));
|
||||
SetRFLAG<FEXCore::X86State::RFLAG_PF_LOC>(XorOp);
|
||||
} else {
|
||||
_InvalidateFlags(1UL << FEXCore::X86State::RFLAG_PF_LOC);
|
||||
}
|
||||
|
||||
// ZF
|
||||
@@ -5045,6 +5051,8 @@ void OpDispatchBuilder::GenerateFlags_ADD(FEXCore::X86Tables::DecodedOp Op, Orde
|
||||
auto PopCountOp = _Popcount(_And(Res, EightBitMask));
|
||||
auto XorOp = _Xor(PopCountOp, _Constant(1));
|
||||
SetRFLAG<FEXCore::X86State::RFLAG_PF_LOC>(XorOp);
|
||||
} else {
|
||||
_InvalidateFlags(1UL << FEXCore::X86State::RFLAG_PF_LOC);
|
||||
}
|
||||
|
||||
// ZF
|
||||
@@ -5155,6 +5163,8 @@ void OpDispatchBuilder::GenerateFlags_Logical(FEXCore::X86Tables::DecodedOp Op,
|
||||
auto PopCountOp = _Popcount(_And(Res, EightBitMask));
|
||||
auto XorOp = _Xor(PopCountOp, _Constant(1));
|
||||
SetRFLAG<FEXCore::X86State::RFLAG_PF_LOC>(XorOp);
|
||||
} else {
|
||||
_InvalidateFlags(1UL << FEXCore::X86State::RFLAG_PF_LOC);
|
||||
}
|
||||
|
||||
// ZF
|
||||
@@ -5192,6 +5202,8 @@ void OpDispatchBuilder::GenerateFlags_ShiftLeft(FEXCore::X86Tables::DecodedOp Op
|
||||
auto PopCountOp = _Popcount(_And(Res, EightBitMask));
|
||||
auto XorOp = _Xor(PopCountOp, _Constant(1));
|
||||
COND_FLAG_SET(Src2, RFLAG_PF_LOC, XorOp);
|
||||
} else {
|
||||
_InvalidateFlags(1UL << FEXCore::X86State::RFLAG_PF_LOC);
|
||||
}
|
||||
|
||||
// AF
|
||||
@@ -5238,6 +5250,8 @@ void OpDispatchBuilder::GenerateFlags_ShiftRight(FEXCore::X86Tables::DecodedOp O
|
||||
auto PopCountOp = _Popcount(_And(Res, EightBitMask));
|
||||
auto XorOp = _Xor(PopCountOp, _Constant(1));
|
||||
COND_FLAG_SET(Src2, RFLAG_PF_LOC, XorOp);
|
||||
} else {
|
||||
_InvalidateFlags(1UL << FEXCore::X86State::RFLAG_PF_LOC);
|
||||
}
|
||||
|
||||
// AF
|
||||
@@ -5284,6 +5298,8 @@ void OpDispatchBuilder::GenerateFlags_SignShiftRight(FEXCore::X86Tables::Decoded
|
||||
auto PopCountOp = _Popcount(_And(Res, EightBitMask));
|
||||
auto XorOp = _Xor(PopCountOp, _Constant(1));
|
||||
COND_FLAG_SET(Src2, RFLAG_PF_LOC, XorOp);
|
||||
} else {
|
||||
_InvalidateFlags(1UL << FEXCore::X86State::RFLAG_PF_LOC);
|
||||
}
|
||||
|
||||
// AF
|
||||
@@ -5330,6 +5346,8 @@ void OpDispatchBuilder::GenerateFlags_ShiftLeftImmediate(FEXCore::X86Tables::Dec
|
||||
auto PopCountOp = _Popcount(_And(Res, EightBitMask));
|
||||
auto XorOp = _Xor(PopCountOp, _Constant(1));
|
||||
SetRFLAG<FEXCore::X86State::RFLAG_PF_LOC>(XorOp);
|
||||
} else {
|
||||
_InvalidateFlags(1UL << FEXCore::X86State::RFLAG_PF_LOC);
|
||||
}
|
||||
|
||||
// AF
|
||||
@@ -5377,6 +5395,8 @@ void OpDispatchBuilder::GenerateFlags_SignShiftRightImmediate(FEXCore::X86Tables
|
||||
auto PopCountOp = _Popcount(_And(Res, EightBitMask));
|
||||
auto XorOp = _Xor(PopCountOp, _Constant(1));
|
||||
SetRFLAG<FEXCore::X86State::RFLAG_PF_LOC>(XorOp);
|
||||
} else {
|
||||
_InvalidateFlags(1UL << FEXCore::X86State::RFLAG_PF_LOC);
|
||||
}
|
||||
|
||||
// AF
|
||||
@@ -5426,6 +5446,8 @@ void OpDispatchBuilder::GenerateFlags_ShiftRightImmediate(FEXCore::X86Tables::De
|
||||
auto PopCountOp = _Popcount(_And(Res, EightBitMask));
|
||||
auto XorOp = _Xor(PopCountOp, _Constant(1));
|
||||
SetRFLAG<FEXCore::X86State::RFLAG_PF_LOC>(XorOp);
|
||||
} else {
|
||||
_InvalidateFlags(1UL << FEXCore::X86State::RFLAG_PF_LOC);
|
||||
}
|
||||
|
||||
// AF
|
||||
|
||||
+4
-1
@@ -95,7 +95,10 @@
|
||||
|
||||
"InvalidateFlags": {
|
||||
"OpClass": "Misc",
|
||||
"HasSideEffects": true
|
||||
"HasSideEffects": true,
|
||||
"Args": [
|
||||
"uint64_t", "Flags"
|
||||
]
|
||||
},
|
||||
|
||||
"EndBlock": {
|
||||
|
||||
@@ -9,9 +9,9 @@ public:
|
||||
};
|
||||
|
||||
struct FlagInfo {
|
||||
uint32_t reads { 0 };
|
||||
uint32_t writes { 0 };
|
||||
uint32_t kill { 0 };
|
||||
uint64_t reads { 0 };
|
||||
uint64_t writes { 0 };
|
||||
uint64_t kill { 0 };
|
||||
};
|
||||
|
||||
/**
|
||||
@@ -40,14 +40,15 @@ bool DeadFlagStoreElimination::Run(IREmitter *IREmit) {
|
||||
|
||||
if (IROp->Op == OP_STOREFLAG) {
|
||||
auto Op = IROp->CW<IR::IROp_StoreFlag>();
|
||||
FlagMap[BlockNode].writes |= 1 << Op->Flag;
|
||||
FlagMap[BlockNode].writes |= 1UL << Op->Flag;
|
||||
}
|
||||
else if (IROp->Op == OP_INVALIDATEFLAGS) {
|
||||
FlagMap[BlockNode].writes = -1;
|
||||
auto Op = IROp->CW<IR::IROp_InvalidateFlags>();
|
||||
FlagMap[BlockNode].writes |= Op->Flags;
|
||||
}
|
||||
else if (IROp->Op == OP_LOADFLAG) {
|
||||
auto Op = IROp->CW<IR::IROp_LoadFlag>();
|
||||
FlagMap[BlockNode].reads |= 1 << Op->Flag;
|
||||
FlagMap[BlockNode].reads |= 1UL << Op->Flag;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -98,7 +99,7 @@ bool DeadFlagStoreElimination::Run(IREmitter *IREmit) {
|
||||
if (IROp->Op == OP_STOREFLAG) {
|
||||
auto Op = IROp->CW<IR::IROp_StoreFlag>();
|
||||
// If this StoreFlag is never read, remove it
|
||||
if (FlagMap[BlockNode].kill & (1 << Op->Flag)) {
|
||||
if (FlagMap[BlockNode].kill & (1UL << Op->Flag)) {
|
||||
IREmit->Remove(CodeNode);
|
||||
Changed = true;
|
||||
}
|
||||
|
||||
Reference in new issue
Block a user