mirror of
https://github.com/RPCSX/llvm.git
synced 2025-02-03 19:15:30 +00:00
[InstCombine][InstSimplify] Use APInt::isNullValue/isOneValue to reduce compiled code for comparing APInts with 0 and 1. NFC
These methods are specifically optimized to only counting leading zeros without an additional uint64_t compare. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@304876 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
parent
e57d4f53f8
commit
eb370b4757
@ -262,7 +262,7 @@ template <typename Predicate> struct api_pred_ty : public Predicate {
|
|||||||
};
|
};
|
||||||
|
|
||||||
struct is_one {
|
struct is_one {
|
||||||
bool isValue(const APInt &C) { return C == 1; }
|
bool isValue(const APInt &C) { return C.isOneValue(); }
|
||||||
};
|
};
|
||||||
|
|
||||||
/// \brief Match an integer 1 or a vector with all elements equal to 1.
|
/// \brief Match an integer 1 or a vector with all elements equal to 1.
|
||||||
|
@ -2391,7 +2391,7 @@ static void setLimitsForBinOp(BinaryOperator &BO, APInt &Lower, APInt &Upper) {
|
|||||||
const APInt *C;
|
const APInt *C;
|
||||||
switch (BO.getOpcode()) {
|
switch (BO.getOpcode()) {
|
||||||
case Instruction::Add:
|
case Instruction::Add:
|
||||||
if (match(BO.getOperand(1), m_APInt(C)) && *C != 0) {
|
if (match(BO.getOperand(1), m_APInt(C)) && !C->isNullValue()) {
|
||||||
// FIXME: If we have both nuw and nsw, we should reduce the range further.
|
// FIXME: If we have both nuw and nsw, we should reduce the range further.
|
||||||
if (BO.hasNoUnsignedWrap()) {
|
if (BO.hasNoUnsignedWrap()) {
|
||||||
// 'add nuw x, C' produces [C, UINT_MAX].
|
// 'add nuw x, C' produces [C, UINT_MAX].
|
||||||
@ -2429,7 +2429,7 @@ static void setLimitsForBinOp(BinaryOperator &BO, APInt &Lower, APInt &Upper) {
|
|||||||
Upper = APInt::getSignedMaxValue(Width).ashr(*C) + 1;
|
Upper = APInt::getSignedMaxValue(Width).ashr(*C) + 1;
|
||||||
} else if (match(BO.getOperand(0), m_APInt(C))) {
|
} else if (match(BO.getOperand(0), m_APInt(C))) {
|
||||||
unsigned ShiftAmount = Width - 1;
|
unsigned ShiftAmount = Width - 1;
|
||||||
if (*C != 0 && BO.isExact())
|
if (!C->isNullValue() && BO.isExact())
|
||||||
ShiftAmount = C->countTrailingZeros();
|
ShiftAmount = C->countTrailingZeros();
|
||||||
if (C->isNegative()) {
|
if (C->isNegative()) {
|
||||||
// 'ashr C, x' produces [C, C >> (Width-1)]
|
// 'ashr C, x' produces [C, C >> (Width-1)]
|
||||||
@ -2450,7 +2450,7 @@ static void setLimitsForBinOp(BinaryOperator &BO, APInt &Lower, APInt &Upper) {
|
|||||||
} else if (match(BO.getOperand(0), m_APInt(C))) {
|
} else if (match(BO.getOperand(0), m_APInt(C))) {
|
||||||
// 'lshr C, x' produces [C >> (Width-1), C].
|
// 'lshr C, x' produces [C >> (Width-1), C].
|
||||||
unsigned ShiftAmount = Width - 1;
|
unsigned ShiftAmount = Width - 1;
|
||||||
if (*C != 0 && BO.isExact())
|
if (!C->isNullValue() && BO.isExact())
|
||||||
ShiftAmount = C->countTrailingZeros();
|
ShiftAmount = C->countTrailingZeros();
|
||||||
Lower = C->lshr(ShiftAmount);
|
Lower = C->lshr(ShiftAmount);
|
||||||
Upper = *C + 1;
|
Upper = *C + 1;
|
||||||
@ -2512,7 +2512,7 @@ static void setLimitsForBinOp(BinaryOperator &BO, APInt &Lower, APInt &Upper) {
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case Instruction::UDiv:
|
case Instruction::UDiv:
|
||||||
if (match(BO.getOperand(1), m_APInt(C)) && *C != 0) {
|
if (match(BO.getOperand(1), m_APInt(C)) && !C->isNullValue()) {
|
||||||
// 'udiv x, C' produces [0, UINT_MAX / C].
|
// 'udiv x, C' produces [0, UINT_MAX / C].
|
||||||
Upper = APInt::getMaxValue(Width).udiv(*C) + 1;
|
Upper = APInt::getMaxValue(Width).udiv(*C) + 1;
|
||||||
} else if (match(BO.getOperand(0), m_APInt(C))) {
|
} else if (match(BO.getOperand(0), m_APInt(C))) {
|
||||||
@ -2827,14 +2827,14 @@ static Value *simplifyICmpWithBinOp(CmpInst::Predicate Pred, Value *LHS,
|
|||||||
// - CI2 is one
|
// - CI2 is one
|
||||||
// - CI isn't zero
|
// - CI isn't zero
|
||||||
if (LBO->hasNoSignedWrap() || LBO->hasNoUnsignedWrap() ||
|
if (LBO->hasNoSignedWrap() || LBO->hasNoUnsignedWrap() ||
|
||||||
*CI2Val == 1 || !CI->isZero()) {
|
CI2Val->isOneValue() || !CI->isZero()) {
|
||||||
if (Pred == ICmpInst::ICMP_EQ)
|
if (Pred == ICmpInst::ICMP_EQ)
|
||||||
return ConstantInt::getFalse(RHS->getContext());
|
return ConstantInt::getFalse(RHS->getContext());
|
||||||
if (Pred == ICmpInst::ICMP_NE)
|
if (Pred == ICmpInst::ICMP_NE)
|
||||||
return ConstantInt::getTrue(RHS->getContext());
|
return ConstantInt::getTrue(RHS->getContext());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (CIVal->isSignMask() && *CI2Val == 1) {
|
if (CIVal->isSignMask() && CI2Val->isOneValue()) {
|
||||||
if (Pred == ICmpInst::ICMP_UGT)
|
if (Pred == ICmpInst::ICMP_UGT)
|
||||||
return ConstantInt::getFalse(RHS->getContext());
|
return ConstantInt::getFalse(RHS->getContext());
|
||||||
if (Pred == ICmpInst::ICMP_ULE)
|
if (Pred == ICmpInst::ICMP_ULE)
|
||||||
|
@ -991,8 +991,9 @@ static Instruction *foldAddWithConstant(BinaryOperator &Add,
|
|||||||
// Shifts and add used to flip and mask off the low bit:
|
// Shifts and add used to flip and mask off the low bit:
|
||||||
// add (ashr (shl i32 X, 31), 31), 1 --> and (not X), 1
|
// add (ashr (shl i32 X, 31), 31), 1 --> and (not X), 1
|
||||||
const APInt *C3;
|
const APInt *C3;
|
||||||
if (*C == 1 && match(Op0, m_OneUse(m_AShr(m_Shl(m_Value(X), m_APInt(C2)),
|
if (C->isOneValue() &&
|
||||||
m_APInt(C3)))) &&
|
match(Op0,
|
||||||
|
m_OneUse(m_AShr(m_Shl(m_Value(X), m_APInt(C2)), m_APInt(C3)))) &&
|
||||||
C2 == C3 && *C2 == Ty->getScalarSizeInBits() - 1) {
|
C2 == C3 && *C2 == Ty->getScalarSizeInBits() - 1) {
|
||||||
Value *NotX = Builder.CreateNot(X);
|
Value *NotX = Builder.CreateNot(X);
|
||||||
return BinaryOperator::CreateAnd(NotX, ConstantInt::get(Ty, 1));
|
return BinaryOperator::CreateAnd(NotX, ConstantInt::get(Ty, 1));
|
||||||
@ -1554,7 +1555,7 @@ Instruction *InstCombiner::visitSub(BinaryOperator &I) {
|
|||||||
|
|
||||||
// -(X >>u 31) -> (X >>s 31)
|
// -(X >>u 31) -> (X >>s 31)
|
||||||
// -(X >>s 31) -> (X >>u 31)
|
// -(X >>s 31) -> (X >>u 31)
|
||||||
if (*Op0C == 0) {
|
if (Op0C->isNullValue()) {
|
||||||
Value *X;
|
Value *X;
|
||||||
const APInt *ShAmt;
|
const APInt *ShAmt;
|
||||||
if (match(Op1, m_LShr(m_Value(X), m_APInt(ShAmt))) &&
|
if (match(Op1, m_LShr(m_Value(X), m_APInt(ShAmt))) &&
|
||||||
|
@ -172,12 +172,12 @@ Instruction *InstCombiner::OptAndOp(BinaryOperator *Op,
|
|||||||
const APInt& AddRHS = OpRHS->getValue();
|
const APInt& AddRHS = OpRHS->getValue();
|
||||||
|
|
||||||
// Check to see if any bits below the one bit set in AndRHSV are set.
|
// Check to see if any bits below the one bit set in AndRHSV are set.
|
||||||
if ((AddRHS & (AndRHSV-1)) == 0) {
|
if ((AddRHS & (AndRHSV - 1)).isNullValue()) {
|
||||||
// If not, the only thing that can effect the output of the AND is
|
// If not, the only thing that can effect the output of the AND is
|
||||||
// the bit specified by AndRHSV. If that bit is set, the effect of
|
// the bit specified by AndRHSV. If that bit is set, the effect of
|
||||||
// the XOR is to toggle the bit. If it is clear, then the ADD has
|
// the XOR is to toggle the bit. If it is clear, then the ADD has
|
||||||
// no effect.
|
// no effect.
|
||||||
if ((AddRHS & AndRHSV) == 0) { // Bit is not set, noop
|
if ((AddRHS & AndRHSV).isNullValue()) { // Bit is not set, noop
|
||||||
TheAnd.setOperand(0, X);
|
TheAnd.setOperand(0, X);
|
||||||
return &TheAnd;
|
return &TheAnd;
|
||||||
} else {
|
} else {
|
||||||
@ -641,7 +641,7 @@ static Value *foldLogOpOfMaskedICmps(ICmpInst *LHS, ICmpInst *RHS, bool IsAnd,
|
|||||||
// If there is a conflict, we should actually return a false for the
|
// If there is a conflict, we should actually return a false for the
|
||||||
// whole construct.
|
// whole construct.
|
||||||
if (((BCst->getValue() & DCst->getValue()) &
|
if (((BCst->getValue() & DCst->getValue()) &
|
||||||
(CCst->getValue() ^ ECst->getValue())) != 0)
|
(CCst->getValue() ^ ECst->getValue())).getBoolValue())
|
||||||
return ConstantInt::get(LHS->getType(), !IsAnd);
|
return ConstantInt::get(LHS->getType(), !IsAnd);
|
||||||
|
|
||||||
Value *NewOr1 = Builder->CreateOr(B, D);
|
Value *NewOr1 = Builder->CreateOr(B, D);
|
||||||
@ -748,7 +748,7 @@ foldAndOrOfEqualityCmpsWithConstants(ICmpInst *LHS, ICmpInst *RHS,
|
|||||||
|
|
||||||
// Special case: get the ordering right when the values wrap around zero.
|
// Special case: get the ordering right when the values wrap around zero.
|
||||||
// Ie, we assumed the constants were unsigned when swapping earlier.
|
// Ie, we assumed the constants were unsigned when swapping earlier.
|
||||||
if (*C1 == 0 && C2->isAllOnesValue())
|
if (C1->isNullValue() && C2->isAllOnesValue())
|
||||||
std::swap(C1, C2);
|
std::swap(C1, C2);
|
||||||
|
|
||||||
if (*C1 == *C2 - 1) {
|
if (*C1 == *C2 - 1) {
|
||||||
@ -840,7 +840,8 @@ Value *InstCombiner::foldAndOfICmps(ICmpInst *LHS, ICmpInst *RHS) {
|
|||||||
|
|
||||||
// Check that the low bits are zero.
|
// Check that the low bits are zero.
|
||||||
APInt Low = APInt::getLowBitsSet(BigBitSize, SmallBitSize);
|
APInt Low = APInt::getLowBitsSet(BigBitSize, SmallBitSize);
|
||||||
if ((Low & AndC->getValue()) == 0 && (Low & BigC->getValue()) == 0) {
|
if ((Low & AndC->getValue()).isNullValue() &&
|
||||||
|
(Low & BigC->getValue()).isNullValue()) {
|
||||||
Value *NewAnd = Builder->CreateAnd(V, Low | AndC->getValue());
|
Value *NewAnd = Builder->CreateAnd(V, Low | AndC->getValue());
|
||||||
APInt N = SmallC->getValue().zext(BigBitSize) | BigC->getValue();
|
APInt N = SmallC->getValue().zext(BigBitSize) | BigC->getValue();
|
||||||
Value *NewVal = ConstantInt::get(AndC->getType()->getContext(), N);
|
Value *NewVal = ConstantInt::get(AndC->getType()->getContext(), N);
|
||||||
@ -1286,7 +1287,7 @@ Instruction *InstCombiner::visitAnd(BinaryOperator &I) {
|
|||||||
}
|
}
|
||||||
case Instruction::Sub:
|
case Instruction::Sub:
|
||||||
// -x & 1 -> x & 1
|
// -x & 1 -> x & 1
|
||||||
if (AndRHSMask == 1 && match(Op0LHS, m_Zero()))
|
if (AndRHSMask.isOneValue() && match(Op0LHS, m_Zero()))
|
||||||
return BinaryOperator::CreateAnd(Op0RHS, AndRHS);
|
return BinaryOperator::CreateAnd(Op0RHS, AndRHS);
|
||||||
|
|
||||||
break;
|
break;
|
||||||
@ -1295,7 +1296,7 @@ Instruction *InstCombiner::visitAnd(BinaryOperator &I) {
|
|||||||
case Instruction::LShr:
|
case Instruction::LShr:
|
||||||
// (1 << x) & 1 --> zext(x == 0)
|
// (1 << x) & 1 --> zext(x == 0)
|
||||||
// (1 >> x) & 1 --> zext(x == 0)
|
// (1 >> x) & 1 --> zext(x == 0)
|
||||||
if (AndRHSMask == 1 && Op0LHS == AndRHS) {
|
if (AndRHSMask.isOneValue() && Op0LHS == AndRHS) {
|
||||||
Value *NewICmp =
|
Value *NewICmp =
|
||||||
Builder->CreateICmpEQ(Op0RHS, Constant::getNullValue(I.getType()));
|
Builder->CreateICmpEQ(Op0RHS, Constant::getNullValue(I.getType()));
|
||||||
return new ZExtInst(NewICmp, I.getType());
|
return new ZExtInst(NewICmp, I.getType());
|
||||||
@ -2033,7 +2034,7 @@ Instruction *InstCombiner::visitOr(BinaryOperator &I) {
|
|||||||
ConstantInt *C1 = dyn_cast<ConstantInt>(C);
|
ConstantInt *C1 = dyn_cast<ConstantInt>(C);
|
||||||
ConstantInt *C2 = dyn_cast<ConstantInt>(D);
|
ConstantInt *C2 = dyn_cast<ConstantInt>(D);
|
||||||
if (C1 && C2) { // (A & C1)|(B & C2)
|
if (C1 && C2) { // (A & C1)|(B & C2)
|
||||||
if ((C1->getValue() & C2->getValue()) == 0) {
|
if ((C1->getValue() & C2->getValue()).isNullValue()) {
|
||||||
// ((V | N) & C1) | (V & C2) --> (V|N) & (C1|C2)
|
// ((V | N) & C1) | (V & C2) --> (V|N) & (C1|C2)
|
||||||
// iff (C1&C2) == 0 and (N&~C1) == 0
|
// iff (C1&C2) == 0 and (N&~C1) == 0
|
||||||
if (match(A, m_Or(m_Value(V1), m_Value(V2))) &&
|
if (match(A, m_Or(m_Value(V1), m_Value(V2))) &&
|
||||||
@ -2056,9 +2057,9 @@ Instruction *InstCombiner::visitOr(BinaryOperator &I) {
|
|||||||
// iff (C1&C2) == 0 and (C3&~C1) == 0 and (C4&~C2) == 0.
|
// iff (C1&C2) == 0 and (C3&~C1) == 0 and (C4&~C2) == 0.
|
||||||
ConstantInt *C3 = nullptr, *C4 = nullptr;
|
ConstantInt *C3 = nullptr, *C4 = nullptr;
|
||||||
if (match(A, m_Or(m_Value(V1), m_ConstantInt(C3))) &&
|
if (match(A, m_Or(m_Value(V1), m_ConstantInt(C3))) &&
|
||||||
(C3->getValue() & ~C1->getValue()) == 0 &&
|
(C3->getValue() & ~C1->getValue()).isNullValue() &&
|
||||||
match(B, m_Or(m_Specific(V1), m_ConstantInt(C4))) &&
|
match(B, m_Or(m_Specific(V1), m_ConstantInt(C4))) &&
|
||||||
(C4->getValue() & ~C2->getValue()) == 0) {
|
(C4->getValue() & ~C2->getValue()).isNullValue()) {
|
||||||
V2 = Builder->CreateOr(V1, ConstantExpr::getOr(C3, C4), "bitfield");
|
V2 = Builder->CreateOr(V1, ConstantExpr::getOr(C3, C4), "bitfield");
|
||||||
return BinaryOperator::CreateAnd(V2,
|
return BinaryOperator::CreateAnd(V2,
|
||||||
Builder->getInt(C1->getValue()|C2->getValue()));
|
Builder->getInt(C1->getValue()|C2->getValue()));
|
||||||
|
@ -393,7 +393,7 @@ static Value *simplifyX86immShift(const IntrinsicInst &II,
|
|||||||
unsigned BitWidth = SVT->getPrimitiveSizeInBits();
|
unsigned BitWidth = SVT->getPrimitiveSizeInBits();
|
||||||
|
|
||||||
// If shift-by-zero then just return the original value.
|
// If shift-by-zero then just return the original value.
|
||||||
if (Count == 0)
|
if (Count.isNullValue())
|
||||||
return Vec;
|
return Vec;
|
||||||
|
|
||||||
// Handle cases when Shift >= BitWidth.
|
// Handle cases when Shift >= BitWidth.
|
||||||
@ -1395,7 +1395,7 @@ static Instruction *foldCttzCtlz(IntrinsicInst &II, InstCombiner &IC) {
|
|||||||
// If the input to cttz/ctlz is known to be non-zero,
|
// If the input to cttz/ctlz is known to be non-zero,
|
||||||
// then change the 'ZeroIsUndef' parameter to 'true'
|
// then change the 'ZeroIsUndef' parameter to 'true'
|
||||||
// because we know the zero behavior can't affect the result.
|
// because we know the zero behavior can't affect the result.
|
||||||
if (Known.One != 0 ||
|
if (!Known.One.isNullValue() ||
|
||||||
isKnownNonZero(Op0, IC.getDataLayout(), 0, &IC.getAssumptionCache(), &II,
|
isKnownNonZero(Op0, IC.getDataLayout(), 0, &IC.getAssumptionCache(), &II,
|
||||||
&IC.getDominatorTree())) {
|
&IC.getDominatorTree())) {
|
||||||
if (!match(II.getArgOperand(1), m_One())) {
|
if (!match(II.getArgOperand(1), m_One())) {
|
||||||
|
@ -661,7 +661,7 @@ Instruction *InstCombiner::transformZExtICmp(ICmpInst *ICI, ZExtInst &CI,
|
|||||||
|
|
||||||
// zext (x <s 0) to i32 --> x>>u31 true if signbit set.
|
// zext (x <s 0) to i32 --> x>>u31 true if signbit set.
|
||||||
// zext (x >s -1) to i32 --> (x>>u31)^1 true if signbit clear.
|
// zext (x >s -1) to i32 --> (x>>u31)^1 true if signbit clear.
|
||||||
if ((ICI->getPredicate() == ICmpInst::ICMP_SLT && Op1CV == 0) ||
|
if ((ICI->getPredicate() == ICmpInst::ICMP_SLT && Op1CV.isNullValue()) ||
|
||||||
(ICI->getPredicate() == ICmpInst::ICMP_SGT && Op1CV.isAllOnesValue())) {
|
(ICI->getPredicate() == ICmpInst::ICMP_SGT && Op1CV.isAllOnesValue())) {
|
||||||
if (!DoTransform) return ICI;
|
if (!DoTransform) return ICI;
|
||||||
|
|
||||||
@ -688,7 +688,7 @@ Instruction *InstCombiner::transformZExtICmp(ICmpInst *ICI, ZExtInst &CI,
|
|||||||
// zext (X != 0) to i32 --> X>>1 iff X has only the 2nd bit set.
|
// zext (X != 0) to i32 --> X>>1 iff X has only the 2nd bit set.
|
||||||
// zext (X != 1) to i32 --> X^1 iff X has only the low bit set.
|
// zext (X != 1) to i32 --> X^1 iff X has only the low bit set.
|
||||||
// zext (X != 2) to i32 --> (X>>1)^1 iff X has only the 2nd bit set.
|
// zext (X != 2) to i32 --> (X>>1)^1 iff X has only the 2nd bit set.
|
||||||
if ((Op1CV == 0 || Op1CV.isPowerOf2()) &&
|
if ((Op1CV.isNullValue() || Op1CV.isPowerOf2()) &&
|
||||||
// This only works for EQ and NE
|
// This only works for EQ and NE
|
||||||
ICI->isEquality()) {
|
ICI->isEquality()) {
|
||||||
// If Op1C some other power of two, convert:
|
// If Op1C some other power of two, convert:
|
||||||
@ -699,7 +699,7 @@ Instruction *InstCombiner::transformZExtICmp(ICmpInst *ICI, ZExtInst &CI,
|
|||||||
if (!DoTransform) return ICI;
|
if (!DoTransform) return ICI;
|
||||||
|
|
||||||
bool isNE = ICI->getPredicate() == ICmpInst::ICMP_NE;
|
bool isNE = ICI->getPredicate() == ICmpInst::ICMP_NE;
|
||||||
if (Op1CV != 0 && (Op1CV != KnownZeroMask)) {
|
if (!Op1CV.isNullValue() && (Op1CV != KnownZeroMask)) {
|
||||||
// (X&4) == 2 --> false
|
// (X&4) == 2 --> false
|
||||||
// (X&4) != 2 --> true
|
// (X&4) != 2 --> true
|
||||||
Constant *Res = ConstantInt::get(Type::getInt1Ty(CI.getContext()),
|
Constant *Res = ConstantInt::get(Type::getInt1Ty(CI.getContext()),
|
||||||
@ -717,7 +717,7 @@ Instruction *InstCombiner::transformZExtICmp(ICmpInst *ICI, ZExtInst &CI,
|
|||||||
In->getName() + ".lobit");
|
In->getName() + ".lobit");
|
||||||
}
|
}
|
||||||
|
|
||||||
if ((Op1CV != 0) == isNE) { // Toggle the low bit.
|
if (!Op1CV.isNullValue() == isNE) { // Toggle the low bit.
|
||||||
Constant *One = ConstantInt::get(In->getType(), 1);
|
Constant *One = ConstantInt::get(In->getType(), 1);
|
||||||
In = Builder->CreateXor(In, One);
|
In = Builder->CreateXor(In, One);
|
||||||
}
|
}
|
||||||
|
@ -127,7 +127,7 @@ static bool isSignBitCheck(ICmpInst::Predicate Pred, const APInt &RHS,
|
|||||||
switch (Pred) {
|
switch (Pred) {
|
||||||
case ICmpInst::ICMP_SLT: // True if LHS s< 0
|
case ICmpInst::ICMP_SLT: // True if LHS s< 0
|
||||||
TrueIfSigned = true;
|
TrueIfSigned = true;
|
||||||
return RHS == 0;
|
return RHS.isNullValue();
|
||||||
case ICmpInst::ICMP_SLE: // True if LHS s<= RHS and RHS == -1
|
case ICmpInst::ICMP_SLE: // True if LHS s<= RHS and RHS == -1
|
||||||
TrueIfSigned = true;
|
TrueIfSigned = true;
|
||||||
return RHS.isAllOnesValue();
|
return RHS.isAllOnesValue();
|
||||||
@ -155,10 +155,10 @@ static bool isSignTest(ICmpInst::Predicate &Pred, const APInt &C) {
|
|||||||
if (!ICmpInst::isSigned(Pred))
|
if (!ICmpInst::isSigned(Pred))
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
if (C == 0)
|
if (C.isNullValue())
|
||||||
return ICmpInst::isRelational(Pred);
|
return ICmpInst::isRelational(Pred);
|
||||||
|
|
||||||
if (C == 1) {
|
if (C.isOneValue()) {
|
||||||
if (Pred == ICmpInst::ICMP_SLT) {
|
if (Pred == ICmpInst::ICMP_SLT) {
|
||||||
Pred = ICmpInst::ICMP_SLE;
|
Pred = ICmpInst::ICMP_SLE;
|
||||||
return true;
|
return true;
|
||||||
@ -1193,7 +1193,7 @@ Instruction *InstCombiner::foldICmpShrConstConst(ICmpInst &I, Value *A,
|
|||||||
};
|
};
|
||||||
|
|
||||||
// Don't bother doing any work for cases which InstSimplify handles.
|
// Don't bother doing any work for cases which InstSimplify handles.
|
||||||
if (AP2 == 0)
|
if (AP2.isNullValue())
|
||||||
return nullptr;
|
return nullptr;
|
||||||
|
|
||||||
bool IsAShr = isa<AShrOperator>(I.getOperand(0));
|
bool IsAShr = isa<AShrOperator>(I.getOperand(0));
|
||||||
@ -1252,7 +1252,7 @@ Instruction *InstCombiner::foldICmpShlConstConst(ICmpInst &I, Value *A,
|
|||||||
};
|
};
|
||||||
|
|
||||||
// Don't bother doing any work for cases which InstSimplify handles.
|
// Don't bother doing any work for cases which InstSimplify handles.
|
||||||
if (AP2 == 0)
|
if (AP2.isNullValue())
|
||||||
return nullptr;
|
return nullptr;
|
||||||
|
|
||||||
unsigned AP2TrailingZeros = AP2.countTrailingZeros();
|
unsigned AP2TrailingZeros = AP2.countTrailingZeros();
|
||||||
@ -1399,7 +1399,7 @@ Instruction *InstCombiner::foldICmpWithConstant(ICmpInst &Cmp) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// (icmp sgt smin(PosA, B) 0) -> (icmp sgt B 0)
|
// (icmp sgt smin(PosA, B) 0) -> (icmp sgt B 0)
|
||||||
if (*C == 0 && Pred == ICmpInst::ICMP_SGT) {
|
if (C->isNullValue() && Pred == ICmpInst::ICMP_SGT) {
|
||||||
SelectPatternResult SPR = matchSelectPattern(X, A, B);
|
SelectPatternResult SPR = matchSelectPattern(X, A, B);
|
||||||
if (SPR.Flavor == SPF_SMIN) {
|
if (SPR.Flavor == SPF_SMIN) {
|
||||||
if (isKnownPositive(A, DL, 0, &AC, &Cmp, &DT))
|
if (isKnownPositive(A, DL, 0, &AC, &Cmp, &DT))
|
||||||
@ -1465,7 +1465,7 @@ Instruction *InstCombiner::foldICmpTruncConstant(ICmpInst &Cmp,
|
|||||||
const APInt *C) {
|
const APInt *C) {
|
||||||
ICmpInst::Predicate Pred = Cmp.getPredicate();
|
ICmpInst::Predicate Pred = Cmp.getPredicate();
|
||||||
Value *X = Trunc->getOperand(0);
|
Value *X = Trunc->getOperand(0);
|
||||||
if (*C == 1 && C->getBitWidth() > 1) {
|
if (C->isOneValue() && C->getBitWidth() > 1) {
|
||||||
// icmp slt trunc(signum(V)) 1 --> icmp slt V, 1
|
// icmp slt trunc(signum(V)) 1 --> icmp slt V, 1
|
||||||
Value *V = nullptr;
|
Value *V = nullptr;
|
||||||
if (Pred == ICmpInst::ICMP_SLT && match(X, m_Signum(m_Value(V))))
|
if (Pred == ICmpInst::ICMP_SLT && match(X, m_Signum(m_Value(V))))
|
||||||
@ -1505,7 +1505,7 @@ Instruction *InstCombiner::foldICmpXorConstant(ICmpInst &Cmp,
|
|||||||
// If this is a comparison that tests the signbit (X < 0) or (x > -1),
|
// If this is a comparison that tests the signbit (X < 0) or (x > -1),
|
||||||
// fold the xor.
|
// fold the xor.
|
||||||
ICmpInst::Predicate Pred = Cmp.getPredicate();
|
ICmpInst::Predicate Pred = Cmp.getPredicate();
|
||||||
if ((Pred == ICmpInst::ICMP_SLT && *C == 0) ||
|
if ((Pred == ICmpInst::ICMP_SLT && C->isNullValue()) ||
|
||||||
(Pred == ICmpInst::ICMP_SGT && C->isAllOnesValue())) {
|
(Pred == ICmpInst::ICMP_SGT && C->isAllOnesValue())) {
|
||||||
|
|
||||||
// If the sign bit of the XorCst is not set, there is no change to
|
// If the sign bit of the XorCst is not set, there is no change to
|
||||||
@ -1623,7 +1623,7 @@ Instruction *InstCombiner::foldICmpAndShift(ICmpInst &Cmp, BinaryOperator *And,
|
|||||||
// Turn ((X >> Y) & C2) == 0 into (X & (C2 << Y)) == 0. The latter is
|
// Turn ((X >> Y) & C2) == 0 into (X & (C2 << Y)) == 0. The latter is
|
||||||
// preferable because it allows the C2 << Y expression to be hoisted out of a
|
// preferable because it allows the C2 << Y expression to be hoisted out of a
|
||||||
// loop if Y is invariant and X is not.
|
// loop if Y is invariant and X is not.
|
||||||
if (Shift->hasOneUse() && *C1 == 0 && Cmp.isEquality() &&
|
if (Shift->hasOneUse() && C1->isNullValue() && Cmp.isEquality() &&
|
||||||
!Shift->isArithmeticShift() && !isa<Constant>(Shift->getOperand(0))) {
|
!Shift->isArithmeticShift() && !isa<Constant>(Shift->getOperand(0))) {
|
||||||
// Compute C2 << Y.
|
// Compute C2 << Y.
|
||||||
Value *NewShift =
|
Value *NewShift =
|
||||||
@ -1681,7 +1681,8 @@ Instruction *InstCombiner::foldICmpAndConstConst(ICmpInst &Cmp,
|
|||||||
// (icmp pred (and A, (or (shl 1, B), 1), 0))
|
// (icmp pred (and A, (or (shl 1, B), 1), 0))
|
||||||
//
|
//
|
||||||
// iff pred isn't signed
|
// iff pred isn't signed
|
||||||
if (!Cmp.isSigned() && *C1 == 0 && match(And->getOperand(1), m_One())) {
|
if (!Cmp.isSigned() && C1->isNullValue() &&
|
||||||
|
match(And->getOperand(1), m_One())) {
|
||||||
Constant *One = cast<Constant>(And->getOperand(1));
|
Constant *One = cast<Constant>(And->getOperand(1));
|
||||||
Value *Or = And->getOperand(0);
|
Value *Or = And->getOperand(0);
|
||||||
Value *A, *B, *LShr;
|
Value *A, *B, *LShr;
|
||||||
@ -1764,7 +1765,7 @@ Instruction *InstCombiner::foldICmpAndConstant(ICmpInst &Cmp,
|
|||||||
// (X & C2) != 0 -> (trunc X) < 0
|
// (X & C2) != 0 -> (trunc X) < 0
|
||||||
// iff C2 is a power of 2 and it masks the sign bit of a legal integer type.
|
// iff C2 is a power of 2 and it masks the sign bit of a legal integer type.
|
||||||
const APInt *C2;
|
const APInt *C2;
|
||||||
if (And->hasOneUse() && *C == 0 && match(Y, m_APInt(C2))) {
|
if (And->hasOneUse() && C->isNullValue() && match(Y, m_APInt(C2))) {
|
||||||
int32_t ExactLogBase2 = C2->exactLogBase2();
|
int32_t ExactLogBase2 = C2->exactLogBase2();
|
||||||
if (ExactLogBase2 != -1 && DL.isLegalInteger(ExactLogBase2 + 1)) {
|
if (ExactLogBase2 != -1 && DL.isLegalInteger(ExactLogBase2 + 1)) {
|
||||||
Type *NTy = IntegerType::get(Cmp.getContext(), ExactLogBase2 + 1);
|
Type *NTy = IntegerType::get(Cmp.getContext(), ExactLogBase2 + 1);
|
||||||
@ -1784,7 +1785,7 @@ Instruction *InstCombiner::foldICmpAndConstant(ICmpInst &Cmp,
|
|||||||
Instruction *InstCombiner::foldICmpOrConstant(ICmpInst &Cmp, BinaryOperator *Or,
|
Instruction *InstCombiner::foldICmpOrConstant(ICmpInst &Cmp, BinaryOperator *Or,
|
||||||
const APInt *C) {
|
const APInt *C) {
|
||||||
ICmpInst::Predicate Pred = Cmp.getPredicate();
|
ICmpInst::Predicate Pred = Cmp.getPredicate();
|
||||||
if (*C == 1) {
|
if (C->isOneValue()) {
|
||||||
// icmp slt signum(V) 1 --> icmp slt V, 1
|
// icmp slt signum(V) 1 --> icmp slt V, 1
|
||||||
Value *V = nullptr;
|
Value *V = nullptr;
|
||||||
if (Pred == ICmpInst::ICMP_SLT && match(Or, m_Signum(m_Value(V))))
|
if (Pred == ICmpInst::ICMP_SLT && match(Or, m_Signum(m_Value(V))))
|
||||||
@ -1801,7 +1802,7 @@ Instruction *InstCombiner::foldICmpOrConstant(ICmpInst &Cmp, BinaryOperator *Or,
|
|||||||
return new ICmpInst(Pred, Or->getOperand(0), Or->getOperand(1));
|
return new ICmpInst(Pred, Or->getOperand(0), Or->getOperand(1));
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!Cmp.isEquality() || *C != 0 || !Or->hasOneUse())
|
if (!Cmp.isEquality() || !C->isNullValue() || !Or->hasOneUse())
|
||||||
return nullptr;
|
return nullptr;
|
||||||
|
|
||||||
Value *P, *Q;
|
Value *P, *Q;
|
||||||
@ -2036,7 +2037,8 @@ Instruction *InstCombiner::foldICmpShrConstant(ICmpInst &Cmp,
|
|||||||
// icmp eq/ne (shr X, Y), 0 --> icmp eq/ne X, 0
|
// icmp eq/ne (shr X, Y), 0 --> icmp eq/ne X, 0
|
||||||
Value *X = Shr->getOperand(0);
|
Value *X = Shr->getOperand(0);
|
||||||
CmpInst::Predicate Pred = Cmp.getPredicate();
|
CmpInst::Predicate Pred = Cmp.getPredicate();
|
||||||
if (Cmp.isEquality() && Shr->isExact() && Shr->hasOneUse() && *C == 0)
|
if (Cmp.isEquality() && Shr->isExact() && Shr->hasOneUse() &&
|
||||||
|
C->isNullValue())
|
||||||
return new ICmpInst(Pred, X, Cmp.getOperand(1));
|
return new ICmpInst(Pred, X, Cmp.getOperand(1));
|
||||||
|
|
||||||
const APInt *ShiftVal;
|
const APInt *ShiftVal;
|
||||||
@ -2178,7 +2180,8 @@ Instruction *InstCombiner::foldICmpDivConstant(ICmpInst &Cmp,
|
|||||||
// INT_MIN will also fail if the divisor is 1. Although folds of all these
|
// INT_MIN will also fail if the divisor is 1. Although folds of all these
|
||||||
// division-by-constant cases should be present, we can not assert that they
|
// division-by-constant cases should be present, we can not assert that they
|
||||||
// have happened before we reach this icmp instruction.
|
// have happened before we reach this icmp instruction.
|
||||||
if (*C2 == 0 || *C2 == 1 || (DivIsSigned && C2->isAllOnesValue()))
|
if (C2->isNullValue() || C2->isOneValue() ||
|
||||||
|
(DivIsSigned && C2->isAllOnesValue()))
|
||||||
return nullptr;
|
return nullptr;
|
||||||
|
|
||||||
// TODO: We could do all of the computations below using APInt.
|
// TODO: We could do all of the computations below using APInt.
|
||||||
@ -2224,7 +2227,7 @@ Instruction *InstCombiner::foldICmpDivConstant(ICmpInst &Cmp,
|
|||||||
HiOverflow = addWithOverflow(HiBound, LoBound, RangeSize, false);
|
HiOverflow = addWithOverflow(HiBound, LoBound, RangeSize, false);
|
||||||
}
|
}
|
||||||
} else if (C2->isStrictlyPositive()) { // Divisor is > 0.
|
} else if (C2->isStrictlyPositive()) { // Divisor is > 0.
|
||||||
if (*C == 0) { // (X / pos) op 0
|
if (C->isNullValue()) { // (X / pos) op 0
|
||||||
// Can't overflow. e.g. X/2 op 0 --> [-1, 2)
|
// Can't overflow. e.g. X/2 op 0 --> [-1, 2)
|
||||||
LoBound = ConstantExpr::getNeg(SubOne(RangeSize));
|
LoBound = ConstantExpr::getNeg(SubOne(RangeSize));
|
||||||
HiBound = RangeSize;
|
HiBound = RangeSize;
|
||||||
@ -2245,7 +2248,7 @@ Instruction *InstCombiner::foldICmpDivConstant(ICmpInst &Cmp,
|
|||||||
} else if (C2->isNegative()) { // Divisor is < 0.
|
} else if (C2->isNegative()) { // Divisor is < 0.
|
||||||
if (Div->isExact())
|
if (Div->isExact())
|
||||||
RangeSize = ConstantExpr::getNeg(RangeSize);
|
RangeSize = ConstantExpr::getNeg(RangeSize);
|
||||||
if (*C == 0) { // (X / neg) op 0
|
if (C->isNullValue()) { // (X / neg) op 0
|
||||||
// e.g. X/-5 op 0 --> [-4, 5)
|
// e.g. X/-5 op 0 --> [-4, 5)
|
||||||
LoBound = AddOne(RangeSize);
|
LoBound = AddOne(RangeSize);
|
||||||
HiBound = ConstantExpr::getNeg(RangeSize);
|
HiBound = ConstantExpr::getNeg(RangeSize);
|
||||||
@ -2337,15 +2340,15 @@ Instruction *InstCombiner::foldICmpSubConstant(ICmpInst &Cmp,
|
|||||||
return new ICmpInst(ICmpInst::ICMP_SGE, X, Y);
|
return new ICmpInst(ICmpInst::ICMP_SGE, X, Y);
|
||||||
|
|
||||||
// (icmp sgt (sub nsw X, Y), 0) -> (icmp sgt X, Y)
|
// (icmp sgt (sub nsw X, Y), 0) -> (icmp sgt X, Y)
|
||||||
if (Pred == ICmpInst::ICMP_SGT && *C == 0)
|
if (Pred == ICmpInst::ICMP_SGT && C->isNullValue())
|
||||||
return new ICmpInst(ICmpInst::ICMP_SGT, X, Y);
|
return new ICmpInst(ICmpInst::ICMP_SGT, X, Y);
|
||||||
|
|
||||||
// (icmp slt (sub nsw X, Y), 0) -> (icmp slt X, Y)
|
// (icmp slt (sub nsw X, Y), 0) -> (icmp slt X, Y)
|
||||||
if (Pred == ICmpInst::ICMP_SLT && *C == 0)
|
if (Pred == ICmpInst::ICMP_SLT && C->isNullValue())
|
||||||
return new ICmpInst(ICmpInst::ICMP_SLT, X, Y);
|
return new ICmpInst(ICmpInst::ICMP_SLT, X, Y);
|
||||||
|
|
||||||
// (icmp slt (sub nsw X, Y), 1) -> (icmp sle X, Y)
|
// (icmp slt (sub nsw X, Y), 1) -> (icmp sle X, Y)
|
||||||
if (Pred == ICmpInst::ICMP_SLT && *C == 1)
|
if (Pred == ICmpInst::ICMP_SLT && C->isOneValue())
|
||||||
return new ICmpInst(ICmpInst::ICMP_SLE, X, Y);
|
return new ICmpInst(ICmpInst::ICMP_SLE, X, Y);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -2520,7 +2523,7 @@ Instruction *InstCombiner::foldICmpBinOpEqualityWithConstant(ICmpInst &Cmp,
|
|||||||
switch (BO->getOpcode()) {
|
switch (BO->getOpcode()) {
|
||||||
case Instruction::SRem:
|
case Instruction::SRem:
|
||||||
// If we have a signed (X % (2^c)) == 0, turn it into an unsigned one.
|
// If we have a signed (X % (2^c)) == 0, turn it into an unsigned one.
|
||||||
if (*C == 0 && BO->hasOneUse()) {
|
if (C->isNullValue() && BO->hasOneUse()) {
|
||||||
const APInt *BOC;
|
const APInt *BOC;
|
||||||
if (match(BOp1, m_APInt(BOC)) && BOC->sgt(1) && BOC->isPowerOf2()) {
|
if (match(BOp1, m_APInt(BOC)) && BOC->sgt(1) && BOC->isPowerOf2()) {
|
||||||
Value *NewRem = Builder->CreateURem(BOp0, BOp1, BO->getName());
|
Value *NewRem = Builder->CreateURem(BOp0, BOp1, BO->getName());
|
||||||
@ -2537,7 +2540,7 @@ Instruction *InstCombiner::foldICmpBinOpEqualityWithConstant(ICmpInst &Cmp,
|
|||||||
Constant *SubC = ConstantExpr::getSub(RHS, cast<Constant>(BOp1));
|
Constant *SubC = ConstantExpr::getSub(RHS, cast<Constant>(BOp1));
|
||||||
return new ICmpInst(Pred, BOp0, SubC);
|
return new ICmpInst(Pred, BOp0, SubC);
|
||||||
}
|
}
|
||||||
} else if (*C == 0) {
|
} else if (C->isNullValue()) {
|
||||||
// Replace ((add A, B) != 0) with (A != -B) if A or B is
|
// Replace ((add A, B) != 0) with (A != -B) if A or B is
|
||||||
// efficiently invertible, or if the add has just this one use.
|
// efficiently invertible, or if the add has just this one use.
|
||||||
if (Value *NegVal = dyn_castNegVal(BOp1))
|
if (Value *NegVal = dyn_castNegVal(BOp1))
|
||||||
@ -2558,7 +2561,7 @@ Instruction *InstCombiner::foldICmpBinOpEqualityWithConstant(ICmpInst &Cmp,
|
|||||||
// For the xor case, we can xor two constants together, eliminating
|
// For the xor case, we can xor two constants together, eliminating
|
||||||
// the explicit xor.
|
// the explicit xor.
|
||||||
return new ICmpInst(Pred, BOp0, ConstantExpr::getXor(RHS, BOC));
|
return new ICmpInst(Pred, BOp0, ConstantExpr::getXor(RHS, BOC));
|
||||||
} else if (*C == 0) {
|
} else if (C->isNullValue()) {
|
||||||
// Replace ((xor A, B) != 0) with (A != B)
|
// Replace ((xor A, B) != 0) with (A != B)
|
||||||
return new ICmpInst(Pred, BOp0, BOp1);
|
return new ICmpInst(Pred, BOp0, BOp1);
|
||||||
}
|
}
|
||||||
@ -2571,7 +2574,7 @@ Instruction *InstCombiner::foldICmpBinOpEqualityWithConstant(ICmpInst &Cmp,
|
|||||||
// Replace ((sub BOC, B) != C) with (B != BOC-C).
|
// Replace ((sub BOC, B) != C) with (B != BOC-C).
|
||||||
Constant *SubC = ConstantExpr::getSub(cast<Constant>(BOp0), RHS);
|
Constant *SubC = ConstantExpr::getSub(cast<Constant>(BOp0), RHS);
|
||||||
return new ICmpInst(Pred, BOp1, SubC);
|
return new ICmpInst(Pred, BOp1, SubC);
|
||||||
} else if (*C == 0) {
|
} else if (C->isNullValue()) {
|
||||||
// Replace ((sub A, B) != 0) with (A != B).
|
// Replace ((sub A, B) != 0) with (A != B).
|
||||||
return new ICmpInst(Pred, BOp0, BOp1);
|
return new ICmpInst(Pred, BOp0, BOp1);
|
||||||
}
|
}
|
||||||
@ -2609,7 +2612,7 @@ Instruction *InstCombiner::foldICmpBinOpEqualityWithConstant(ICmpInst &Cmp,
|
|||||||
}
|
}
|
||||||
|
|
||||||
// ((X & ~7) == 0) --> X < 8
|
// ((X & ~7) == 0) --> X < 8
|
||||||
if (*C == 0 && (~(*BOC) + 1).isPowerOf2()) {
|
if (C->isNullValue() && (~(*BOC) + 1).isPowerOf2()) {
|
||||||
Constant *NegBOC = ConstantExpr::getNeg(cast<Constant>(BOp1));
|
Constant *NegBOC = ConstantExpr::getNeg(cast<Constant>(BOp1));
|
||||||
auto NewPred = isICMP_NE ? ICmpInst::ICMP_UGE : ICmpInst::ICMP_ULT;
|
auto NewPred = isICMP_NE ? ICmpInst::ICMP_UGE : ICmpInst::ICMP_ULT;
|
||||||
return new ICmpInst(NewPred, BOp0, NegBOC);
|
return new ICmpInst(NewPred, BOp0, NegBOC);
|
||||||
@ -2618,9 +2621,9 @@ Instruction *InstCombiner::foldICmpBinOpEqualityWithConstant(ICmpInst &Cmp,
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case Instruction::Mul:
|
case Instruction::Mul:
|
||||||
if (*C == 0 && BO->hasNoSignedWrap()) {
|
if (C->isNullValue() && BO->hasNoSignedWrap()) {
|
||||||
const APInt *BOC;
|
const APInt *BOC;
|
||||||
if (match(BOp1, m_APInt(BOC)) && *BOC != 0) {
|
if (match(BOp1, m_APInt(BOC)) && !BOC->isNullValue()) {
|
||||||
// The trivial case (mul X, 0) is handled by InstSimplify.
|
// The trivial case (mul X, 0) is handled by InstSimplify.
|
||||||
// General case : (mul X, C) != 0 iff X != 0
|
// General case : (mul X, C) != 0 iff X != 0
|
||||||
// (mul X, C) == 0 iff X == 0
|
// (mul X, C) == 0 iff X == 0
|
||||||
@ -2629,7 +2632,7 @@ Instruction *InstCombiner::foldICmpBinOpEqualityWithConstant(ICmpInst &Cmp,
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case Instruction::UDiv:
|
case Instruction::UDiv:
|
||||||
if (*C == 0) {
|
if (C->isNullValue()) {
|
||||||
// (icmp eq/ne (udiv A, B), 0) -> (icmp ugt/ule i32 B, A)
|
// (icmp eq/ne (udiv A, B), 0) -> (icmp ugt/ule i32 B, A)
|
||||||
auto NewPred = isICMP_NE ? ICmpInst::ICMP_ULE : ICmpInst::ICMP_UGT;
|
auto NewPred = isICMP_NE ? ICmpInst::ICMP_ULE : ICmpInst::ICMP_UGT;
|
||||||
return new ICmpInst(NewPred, BOp1, BOp0);
|
return new ICmpInst(NewPred, BOp1, BOp0);
|
||||||
@ -2668,7 +2671,7 @@ Instruction *InstCombiner::foldICmpIntrinsicWithConstant(ICmpInst &Cmp,
|
|||||||
case Intrinsic::ctpop: {
|
case Intrinsic::ctpop: {
|
||||||
// popcount(A) == 0 -> A == 0 and likewise for !=
|
// popcount(A) == 0 -> A == 0 and likewise for !=
|
||||||
// popcount(A) == bitwidth(A) -> A == -1 and likewise for !=
|
// popcount(A) == bitwidth(A) -> A == -1 and likewise for !=
|
||||||
bool IsZero = *C == 0;
|
bool IsZero = C->isNullValue();
|
||||||
if (IsZero || *C == C->getBitWidth()) {
|
if (IsZero || *C == C->getBitWidth()) {
|
||||||
Worklist.Add(II);
|
Worklist.Add(II);
|
||||||
Cmp.setOperand(0, II->getArgOperand(0));
|
Cmp.setOperand(0, II->getArgOperand(0));
|
||||||
@ -3057,7 +3060,8 @@ Instruction *InstCombiner::foldICmpBinOp(ICmpInst &I) {
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
const APInt *C;
|
const APInt *C;
|
||||||
if (match(BO0->getOperand(1), m_APInt(C)) && *C != 0 && *C != 1) {
|
if (match(BO0->getOperand(1), m_APInt(C)) && !C->isNullValue() &&
|
||||||
|
!C->isOneValue()) {
|
||||||
// icmp eq/ne (X * C), (Y * C) --> icmp (X & Mask), (Y & Mask)
|
// icmp eq/ne (X * C), (Y * C) --> icmp (X & Mask), (Y & Mask)
|
||||||
// Mask = -1 >> count-trailing-zeros(C).
|
// Mask = -1 >> count-trailing-zeros(C).
|
||||||
if (unsigned TZs = C->countTrailingZeros()) {
|
if (unsigned TZs = C->countTrailingZeros()) {
|
||||||
@ -4093,7 +4097,7 @@ Instruction *InstCombiner::foldICmpUsingKnownBits(ICmpInst &I) {
|
|||||||
|
|
||||||
// Check if the LHS is 8 >>u x and the result is a power of 2 like 1.
|
// Check if the LHS is 8 >>u x and the result is a power of 2 like 1.
|
||||||
const APInt *CI;
|
const APInt *CI;
|
||||||
if (Op0KnownZeroInverted == 1 &&
|
if (Op0KnownZeroInverted.isOneValue() &&
|
||||||
match(LHS, m_LShr(m_Power2(CI), m_Value(X)))) {
|
match(LHS, m_LShr(m_Power2(CI), m_Value(X)))) {
|
||||||
// ((8 >>u X) & 1) == 0 -> X != 3
|
// ((8 >>u X) & 1) == 0 -> X != 3
|
||||||
// ((8 >>u X) & 1) != 0 -> X == 3
|
// ((8 >>u X) & 1) != 0 -> X == 3
|
||||||
|
@ -930,7 +930,7 @@ Instruction *InstCombiner::commonIDivTransforms(BinaryOperator &I) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (*C2 != 0) // avoid X udiv 0
|
if (!C2->isNullValue()) // avoid X udiv 0
|
||||||
if (Instruction *FoldedDiv = foldOpWithConstantIntoOperand(I))
|
if (Instruction *FoldedDiv = foldOpWithConstantIntoOperand(I))
|
||||||
return FoldedDiv;
|
return FoldedDiv;
|
||||||
}
|
}
|
||||||
|
@ -1478,9 +1478,9 @@ Instruction *InstCombiner::visitSelectInst(SelectInst &SI) {
|
|||||||
if (!CondVal->getType()->isVectorTy() && !AC.assumptions().empty()) {
|
if (!CondVal->getType()->isVectorTy() && !AC.assumptions().empty()) {
|
||||||
KnownBits Known(1);
|
KnownBits Known(1);
|
||||||
computeKnownBits(CondVal, Known, 0, &SI);
|
computeKnownBits(CondVal, Known, 0, &SI);
|
||||||
if (Known.One == 1)
|
if (Known.One.isOneValue())
|
||||||
return replaceInstUsesWith(SI, TrueVal);
|
return replaceInstUsesWith(SI, TrueVal);
|
||||||
if (Known.Zero == 1)
|
if (Known.Zero.isOneValue())
|
||||||
return replaceInstUsesWith(SI, FalseVal);
|
return replaceInstUsesWith(SI, FalseVal);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -121,7 +121,7 @@ Value *InstCombiner::SimplifyDemandedUseBits(Value *V, APInt DemandedMask,
|
|||||||
}
|
}
|
||||||
|
|
||||||
Known.resetAll();
|
Known.resetAll();
|
||||||
if (DemandedMask == 0) // Not demanding any bits from V.
|
if (DemandedMask.isNullValue()) // Not demanding any bits from V.
|
||||||
return UndefValue::get(VTy);
|
return UndefValue::get(VTy);
|
||||||
|
|
||||||
if (Depth == 6) // Limit search depth.
|
if (Depth == 6) // Limit search depth.
|
||||||
@ -488,7 +488,7 @@ Value *InstCombiner::SimplifyDemandedUseBits(Value *V, APInt DemandedMask,
|
|||||||
// always convert this into a logical shr, even if the shift amount is
|
// always convert this into a logical shr, even if the shift amount is
|
||||||
// variable. The low bit of the shift cannot be an input sign bit unless
|
// variable. The low bit of the shift cannot be an input sign bit unless
|
||||||
// the shift amount is >= the size of the datatype, which is undefined.
|
// the shift amount is >= the size of the datatype, which is undefined.
|
||||||
if (DemandedMask == 1) {
|
if (DemandedMask.isOneValue()) {
|
||||||
// Perform the logical shift right.
|
// Perform the logical shift right.
|
||||||
Instruction *NewVal = BinaryOperator::CreateLShr(
|
Instruction *NewVal = BinaryOperator::CreateLShr(
|
||||||
I->getOperand(0), I->getOperand(1), I->getName());
|
I->getOperand(0), I->getOperand(1), I->getName());
|
||||||
@ -656,7 +656,7 @@ Value *InstCombiner::SimplifyDemandedUseBits(Value *V, APInt DemandedMask,
|
|||||||
// If we don't need any of low bits then return zero,
|
// If we don't need any of low bits then return zero,
|
||||||
// we know that DemandedMask is non-zero already.
|
// we know that DemandedMask is non-zero already.
|
||||||
APInt DemandedElts = DemandedMask.zextOrTrunc(ArgWidth);
|
APInt DemandedElts = DemandedMask.zextOrTrunc(ArgWidth);
|
||||||
if (DemandedElts == 0)
|
if (DemandedElts.isNullValue())
|
||||||
return ConstantInt::getNullValue(VTy);
|
return ConstantInt::getNullValue(VTy);
|
||||||
|
|
||||||
// We know that the upper bits are set to zero.
|
// We know that the upper bits are set to zero.
|
||||||
@ -908,7 +908,7 @@ Value *InstCombiner::SimplifyDemandedVectorElts(Value *V, APInt DemandedElts,
|
|||||||
return nullptr;
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (DemandedElts == 0) { // If nothing is demanded, provide undef.
|
if (DemandedElts.isNullValue()) { // If nothing is demanded, provide undef.
|
||||||
UndefElts = EltMask;
|
UndefElts = EltMask;
|
||||||
return UndefValue::get(V->getType());
|
return UndefValue::get(V->getType());
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user