aboutsummaryrefslogtreecommitdiff
path: root/llvm/lib/CodeGen/SelectionDAG/TargetLowering.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'llvm/lib/CodeGen/SelectionDAG/TargetLowering.cpp')
-rw-r--r--llvm/lib/CodeGen/SelectionDAG/TargetLowering.cpp21
1 files changed, 18 insertions, 3 deletions
diff --git a/llvm/lib/CodeGen/SelectionDAG/TargetLowering.cpp b/llvm/lib/CodeGen/SelectionDAG/TargetLowering.cpp
index 48d6b99..b3f131d 100644
--- a/llvm/lib/CodeGen/SelectionDAG/TargetLowering.cpp
+++ b/llvm/lib/CodeGen/SelectionDAG/TargetLowering.cpp
@@ -5363,10 +5363,25 @@ SDValue TargetLowering::SimplifySetCC(EVT VT, SDValue N0, SDValue N1,
if (AndRHSC.isNegatedPowerOf2() && C1.isSubsetOf(AndRHSC)) {
unsigned ShiftBits = AndRHSC.countr_zero();
if (!shouldAvoidTransformToShift(ShValTy, ShiftBits)) {
+ // If using an unsigned shift doesn't yield a legal compare
+ // immediate, try using sra instead.
+ APInt NewC = C1.lshr(ShiftBits);
+ if (NewC.getSignificantBits() <= 64 &&
+ !isLegalICmpImmediate(NewC.getSExtValue())) {
+ APInt SignedC = C1.ashr(ShiftBits);
+ if (SignedC.getSignificantBits() <= 64 &&
+ isLegalICmpImmediate(SignedC.getSExtValue())) {
+ SDValue Shift = DAG.getNode(
+ ISD::SRA, dl, ShValTy, N0.getOperand(0),
+ DAG.getShiftAmountConstant(ShiftBits, ShValTy, dl));
+ SDValue CmpRHS = DAG.getConstant(SignedC, dl, ShValTy);
+ return DAG.getSetCC(dl, VT, Shift, CmpRHS, Cond);
+ }
+ }
SDValue Shift = DAG.getNode(
ISD::SRL, dl, ShValTy, N0.getOperand(0),
DAG.getShiftAmountConstant(ShiftBits, ShValTy, dl));
- SDValue CmpRHS = DAG.getConstant(C1.lshr(ShiftBits), dl, ShValTy);
+ SDValue CmpRHS = DAG.getConstant(NewC, dl, ShValTy);
return DAG.getSetCC(dl, VT, Shift, CmpRHS, Cond);
}
}
@@ -6482,8 +6497,8 @@ SDValue TargetLowering::buildSDIVPow2WithCMov(
Created.push_back(CMov.getNode());
// Divide by pow2.
- SDValue SRA =
- DAG.getNode(ISD::SRA, DL, VT, CMov, DAG.getConstant(Lg2, DL, VT));
+ SDValue SRA = DAG.getNode(ISD::SRA, DL, VT, CMov,
+ DAG.getShiftAmountConstant(Lg2, VT, DL));
// If we're dividing by a positive value, we're done. Otherwise, we must
// negate the result.