Index: src/IceTargetLoweringX86BaseImpl.h |
diff --git a/src/IceTargetLoweringX86BaseImpl.h b/src/IceTargetLoweringX86BaseImpl.h |
index ebdfb1e86b7e94dc86c2ad4f413da5dc754a41a0..477c9f66e931329dfb24c4ea5551ebbf3dbde9ce 100644 |
--- a/src/IceTargetLoweringX86BaseImpl.h |
+++ b/src/IceTargetLoweringX86BaseImpl.h |
@@ -525,20 +525,19 @@ template <class Machine> void TargetX86Base<Machine>::findRMW() { |
// x = FakeDef |
// RMW <op>, addr, other, x |
// b = Store b, addr, x |
- // Note that inferTwoAddress() makes sure setDestNonKillable() gets |
- // called on the updated Store instruction, to avoid liveness problems |
- // later. |
+ // Note that inferTwoAddress() makes sure setDestRedefined() gets called |
+ // on the updated Store instruction, to avoid liveness problems later. |
// |
// With this transformation, the Store instruction acquires a Dest |
// variable and is now subject to dead code elimination if there are no |
- // more uses of "b". Variable "x" is a beacon for determining whether |
- // the Store instruction gets dead-code eliminated. If the Store |
- // instruction is eliminated, then it must be the case that the RMW |
- // instruction ends x's live range, and therefore the RMW instruction |
- // will be retained and later lowered. On the other hand, if the RMW |
- // instruction does not end x's live range, then the Store instruction |
- // must still be present, and therefore the RMW instruction is ignored |
- // during lowering because it is redundant with the Store instruction. |
+ // more uses of "b". Variable "x" is a beacon for determining whether the |
+ // Store instruction gets dead-code eliminated. If the Store instruction |
+ // is eliminated, then it must be the case that the RMW instruction ends |
+ // x's live range, and therefore the RMW instruction will be retained and |
+ // later lowered. On the other hand, if the RMW instruction does not end |
+ // x's live range, then the Store instruction must still be present, and |
+ // therefore the RMW instruction is ignored during lowering because it is |
+ // redundant with the Store instruction. |
// |
// Note that if "a" has further uses, the RMW transformation may still |
// trigger, resulting in two loads and one store, which is worse than the |
@@ -1034,19 +1033,16 @@ bool TargetX86Base<Machine>::optimizeScalarMul(Variable *Dest, Operand *Src0, |
const uint16_t Shift = 3; // log2(9-1) |
_lea(T, |
Traits::X86OperandMem::create(Func, IceType_void, T, Zero, T, Shift)); |
- _set_dest_nonkillable(); |
} |
for (uint32_t i = 0; i < Count5; ++i) { |
const uint16_t Shift = 2; // log2(5-1) |
_lea(T, |
Traits::X86OperandMem::create(Func, IceType_void, T, Zero, T, Shift)); |
- _set_dest_nonkillable(); |
} |
for (uint32_t i = 0; i < Count3; ++i) { |
const uint16_t Shift = 1; // log2(3-1) |
_lea(T, |
Traits::X86OperandMem::create(Func, IceType_void, T, Zero, T, Shift)); |
- _set_dest_nonkillable(); |
} |
if (Count2) { |
_shl(T, Ctx->getConstantInt(Ty, Count2)); |
@@ -1216,11 +1212,10 @@ void TargetX86Base<Machine>::lowerShift64(InstArithmetic::OpKind Op, |
_shl(T_2, T_1); |
_test(T_1, BitTest); |
_br(Traits::Cond::Br_e, Label); |
- // T_2 and T_3 are being assigned again because of the intra-block |
- // control flow, so we need the _mov_nonkillable variant to avoid |
- // liveness problems. |
- _mov_nonkillable(T_3, T_2); |
- _mov_nonkillable(T_2, Zero); |
+ // T_2 and T_3 are being assigned again because of the intra-block control |
+ // flow, so we need the _mov_redefined variant to avoid liveness problems. |
+ _mov_redefined(T_3, T_2); |
+ _mov_redefined(T_2, Zero); |
} break; |
case InstArithmetic::Lshr: { |
// a=b>>c (unsigned) ==> |
@@ -1235,11 +1230,10 @@ void TargetX86Base<Machine>::lowerShift64(InstArithmetic::OpKind Op, |
_shr(T_3, T_1); |
_test(T_1, BitTest); |
_br(Traits::Cond::Br_e, Label); |
- // T_2 and T_3 are being assigned again because of the intra-block |
- // control flow, so we need the _mov_nonkillable variant to avoid |
- // liveness problems. |
- _mov_nonkillable(T_2, T_3); |
- _mov_nonkillable(T_3, Zero); |
+ // T_2 and T_3 are being assigned again because of the intra-block control |
+ // flow, so we need the _mov_redefined variant to avoid liveness problems. |
+ _mov_redefined(T_2, T_3); |
+ _mov_redefined(T_3, Zero); |
} break; |
case InstArithmetic::Ashr: { |
// a=b>>c (signed) ==> |
@@ -1255,11 +1249,11 @@ void TargetX86Base<Machine>::lowerShift64(InstArithmetic::OpKind Op, |
_sar(T_3, T_1); |
_test(T_1, BitTest); |
_br(Traits::Cond::Br_e, Label); |
- // T_2 and T_3 are being assigned again because of the intra-block |
- // control flow, so T_2 needs the _mov_nonkillable variant to avoid |
- // liveness problems. T_3 doesn't need special treatment because it is |
- // reassigned via _sar instead of _mov. |
- _mov_nonkillable(T_2, T_3); |
+ // T_2 and T_3 are being assigned again because of the intra-block control |
+ // flow, so T_2 needs the _mov_redefined variant to avoid liveness |
+ // problems. T_3 doesn't need special treatment because it is reassigned |
+ // via _sar instead of _mov. |
+ _mov_redefined(T_2, T_3); |
_sar(T_3, SignExtend); |
} break; |
} |
@@ -2615,7 +2609,7 @@ void TargetX86Base<Machine>::lowerFcmp(const InstFcmp *Inst) { |
} |
Constant *NonDefault = |
Ctx->getConstantInt32(!Traits::TableFcmp[Index].Default); |
- _mov_nonkillable(Dest, NonDefault); |
+ _mov_redefined(Dest, NonDefault); |
Context.insert(Label); |
} |
} |
@@ -2776,7 +2770,7 @@ TargetX86Base<Machine>::lowerIcmp64(const InstIcmp *Inst) { |
_cmp(Src0LoRM, Src1LoRI); |
_br(Traits::TableIcmp64[Index].C3, LabelTrue); |
Context.insert(LabelFalse); |
- _mov_nonkillable(Dest, Zero); |
+ _mov_redefined(Dest, Zero); |
Context.insert(LabelTrue); |
} |
@@ -3249,7 +3243,7 @@ void TargetX86Base<Machine>::lowerIntrinsicCall( |
case Intrinsics::Stackrestore: { |
Variable *esp = |
Func->getTarget()->getPhysicalRegister(Traits::RegisterSet::Reg_esp); |
- _mov_nonkillable(esp, Instr->getArg(0)); |
+ _mov_redefined(esp, Instr->getArg(0)); |
return; |
} |
case Intrinsics::Trap: |
@@ -4388,7 +4382,7 @@ void TargetX86Base<Machine>::lowerSelect(const InstSelect *Inst) { |
_mov(Dest, SrcT); |
_br(Cond, Label); |
SrcF = legalize(SrcF, Legal_Reg | Legal_Imm); |
- _mov_nonkillable(Dest, SrcF); |
+ _mov_redefined(Dest, SrcF); |
Context.insert(Label); |
return; |
} |
@@ -5224,7 +5218,7 @@ Type TargetX86Base<Machine>::firstTypeThatFitsSize(uint32_t Size, |
template <class Machine> void TargetX86Base<Machine>::postLower() { |
if (Ctx->getFlags().getOptLevel() == Opt_m1) |
return; |
- inferTwoAddress(); |
+ markRedefinitions(); |
} |
template <class Machine> |
@@ -5311,9 +5305,6 @@ Operand *TargetX86Base<Machine>::randomizeOrPoolImmediate(Constant *Immediate, |
Constant *Offset = Ctx->getConstantInt(IceType_i32, 0 - Cookie); |
_lea(Reg, Traits::X86OperandMem::create(Func, IceType_i32, Reg, Offset, |
nullptr, 0)); |
- // make sure liveness analysis won't kill this variable, otherwise a |
- // liveness assertion will be triggered. |
- _set_dest_nonkillable(); |
if (Immediate->getType() != IceType_i32) { |
Variable *TruncReg = makeReg(Immediate->getType(), RegNum); |
_mov(TruncReg, Reg); |
@@ -5400,11 +5391,6 @@ TargetX86Base<Machine>::randomizeOrPoolImmediate( |
// use-def chain. So we add RegNum argument here. |
Variable *RegTemp = makeReg(MemOperand->getOffset()->getType(), RegNum); |
_lea(RegTemp, TempMemOperand); |
- // As source operand doesn't use the dstreg, we don't need to add |
- // _set_dest_nonkillable(). But if we use the same Dest Reg, that is, |
- // with RegNum assigned, we should add this _set_dest_nonkillable() |
- if (RegNum != Variable::NoRegister) |
- _set_dest_nonkillable(); |
typename Traits::X86OperandMem *NewMemOperand = |
Traits::X86OperandMem::create(Func, MemOperand->getType(), RegTemp, |
@@ -5457,7 +5443,6 @@ TargetX86Base<Machine>::randomizeOrPoolImmediate( |
Func, MemOperand->getType(), MemOperand->getBase(), nullptr, |
RegTemp, 0, MemOperand->getSegmentRegister()); |
_lea(RegTemp, CalculateOperand); |
- _set_dest_nonkillable(); |
} |
typename Traits::X86OperandMem *NewMemOperand = |
Traits::X86OperandMem::create(Func, MemOperand->getType(), RegTemp, |