forked from OSchip/llvm-project
[IR][InstCombine] Add m_ImmConstant(), that matches on non-ConstantExpr constants, and use it
A pattern to ignore ConstantExpr's is quite common, since they frequently lead into infinite combine loops, so let's make writing it easier.
This commit is contained in:
parent
ff3749fc79
commit
b3021a72a6
|
@ -88,11 +88,6 @@ inline class_match<BinaryOperator> m_BinOp() {
|
|||
/// Matches any compare instruction and ignore it.
|
||||
inline class_match<CmpInst> m_Cmp() { return class_match<CmpInst>(); }
|
||||
|
||||
/// Match an arbitrary ConstantInt and ignore it.
|
||||
inline class_match<ConstantInt> m_ConstantInt() {
|
||||
return class_match<ConstantInt>();
|
||||
}
|
||||
|
||||
/// Match an arbitrary undef constant.
|
||||
inline class_match<UndefValue> m_Undef() { return class_match<UndefValue>(); }
|
||||
|
||||
|
@ -102,6 +97,21 @@ inline class_match<PoisonValue> m_Poison() { return class_match<PoisonValue>();
|
|||
/// Match an arbitrary Constant and ignore it.
|
||||
inline class_match<Constant> m_Constant() { return class_match<Constant>(); }
|
||||
|
||||
/// Match an arbitrary ConstantInt and ignore it.
|
||||
inline class_match<ConstantInt> m_ConstantInt() {
|
||||
return class_match<ConstantInt>();
|
||||
}
|
||||
|
||||
/// Match an arbitrary ConstantFP and ignore it.
|
||||
inline class_match<ConstantFP> m_ConstantFP() {
|
||||
return class_match<ConstantFP>();
|
||||
}
|
||||
|
||||
/// Match an arbitrary ConstantExpr and ignore it.
|
||||
inline class_match<ConstantExpr> m_ConstantExpr() {
|
||||
return class_match<ConstantExpr>();
|
||||
}
|
||||
|
||||
/// Match an arbitrary basic block value and ignore it.
|
||||
inline class_match<BasicBlock> m_BasicBlock() {
|
||||
return class_match<BasicBlock>();
|
||||
|
@ -699,21 +709,38 @@ inline bind_ty<BinaryOperator> m_BinOp(BinaryOperator *&I) { return I; }
|
|||
/// Match a with overflow intrinsic, capturing it if we match.
|
||||
inline bind_ty<WithOverflowInst> m_WithOverflowInst(WithOverflowInst *&I) { return I; }
|
||||
|
||||
/// Match a ConstantInt, capturing the value if we match.
|
||||
inline bind_ty<ConstantInt> m_ConstantInt(ConstantInt *&CI) { return CI; }
|
||||
|
||||
/// Match a Constant, capturing the value if we match.
|
||||
inline bind_ty<Constant> m_Constant(Constant *&C) { return C; }
|
||||
|
||||
/// Match a ConstantInt, capturing the value if we match.
|
||||
inline bind_ty<ConstantInt> m_ConstantInt(ConstantInt *&CI) { return CI; }
|
||||
|
||||
/// Match a ConstantFP, capturing the value if we match.
|
||||
inline bind_ty<ConstantFP> m_ConstantFP(ConstantFP *&C) { return C; }
|
||||
|
||||
/// Match a ConstantExpr, capturing the value if we match.
|
||||
inline bind_ty<ConstantExpr> m_ConstantExpr(ConstantExpr *&C) { return C; }
|
||||
|
||||
/// Match a basic block value, capturing it if we match.
|
||||
inline bind_ty<BasicBlock> m_BasicBlock(BasicBlock *&V) { return V; }
|
||||
inline bind_ty<const BasicBlock> m_BasicBlock(const BasicBlock *&V) {
|
||||
return V;
|
||||
}
|
||||
|
||||
/// Match an arbitrary immediate Constant and ignore it.
|
||||
inline match_combine_and<class_match<Constant>,
|
||||
match_unless<class_match<ConstantExpr>>>
|
||||
m_ImmConstant() {
|
||||
return m_CombineAnd(m_Constant(), m_Unless(m_ConstantExpr()));
|
||||
}
|
||||
|
||||
/// Match an immediate Constant, capturing the value if we match.
|
||||
inline match_combine_and<bind_ty<Constant>,
|
||||
match_unless<class_match<ConstantExpr>>>
|
||||
m_ImmConstant(Constant *&C) {
|
||||
return m_CombineAnd(m_Constant(C), m_Unless(m_ConstantExpr()));
|
||||
}
|
||||
|
||||
/// Match a specified Value*.
|
||||
struct specificval_ty {
|
||||
const Value *Val;
|
||||
|
|
|
@ -1841,7 +1841,7 @@ Instruction *InstCombinerImpl::visitSub(BinaryOperator &I) {
|
|||
Constant *C2;
|
||||
|
||||
// C-(C2-X) --> X+(C-C2)
|
||||
if (match(Op1, m_Sub(m_Constant(C2), m_Value(X))) && !isa<ConstantExpr>(C2))
|
||||
if (match(Op1, m_Sub(m_ImmConstant(C2), m_Value(X))))
|
||||
return BinaryOperator::CreateAdd(X, ConstantExpr::getSub(C, C2));
|
||||
}
|
||||
|
||||
|
@ -2198,7 +2198,7 @@ Instruction *InstCombinerImpl::visitFSub(BinaryOperator &I) {
|
|||
// X - C --> X + (-C)
|
||||
// But don't transform constant expressions because there's an inverse fold
|
||||
// for X + (-Y) --> X - Y.
|
||||
if (match(Op1, m_Constant(C)) && !isa<ConstantExpr>(Op1))
|
||||
if (match(Op1, m_ImmConstant(C)))
|
||||
return BinaryOperator::CreateFAddFMF(Op0, ConstantExpr::getFNeg(C), &I);
|
||||
|
||||
// X - (-Y) --> X + Y
|
||||
|
|
|
@ -883,8 +883,8 @@ Instruction *InstCombinerImpl::visitCallInst(CallInst &CI) {
|
|||
Type *Ty = II->getType();
|
||||
unsigned BitWidth = Ty->getScalarSizeInBits();
|
||||
Constant *ShAmtC;
|
||||
if (match(II->getArgOperand(2), m_Constant(ShAmtC)) &&
|
||||
!isa<ConstantExpr>(ShAmtC) && !ShAmtC->containsConstantExpression()) {
|
||||
if (match(II->getArgOperand(2), m_ImmConstant(ShAmtC)) &&
|
||||
!ShAmtC->containsConstantExpression()) {
|
||||
// Canonicalize a shift amount constant operand to modulo the bit-width.
|
||||
Constant *WidthC = ConstantInt::get(Ty, BitWidth);
|
||||
Constant *ModuloC = ConstantExpr::getURem(ShAmtC, WidthC);
|
||||
|
|
|
@ -220,8 +220,7 @@ LLVM_NODISCARD Value *Negator::visitImpl(Value *V, unsigned Depth) {
|
|||
}
|
||||
|
||||
if (I->getOpcode() == Instruction::Sub &&
|
||||
(I->hasOneUse() || (isa<Constant>(I->getOperand(0)) &&
|
||||
!isa<ConstantExpr>(I->getOperand(0))))) {
|
||||
(I->hasOneUse() || match(I->getOperand(0), m_ImmConstant()))) {
|
||||
// `sub` is always negatible.
|
||||
// However, only do this either if the old `sub` doesn't stick around, or
|
||||
// it was subtracting from a constant. Otherwise, this isn't profitable.
|
||||
|
|
|
@ -1056,7 +1056,7 @@ Instruction *InstCombinerImpl::foldOpIntoPhi(Instruction &I, PHINode *PN) {
|
|||
for (unsigned i = 0; i != NumPHIValues; ++i) {
|
||||
Value *InVal = PN->getIncomingValue(i);
|
||||
// If I is a freeze instruction, count undef as a non-constant.
|
||||
if (isa<Constant>(InVal) && !isa<ConstantExpr>(InVal) &&
|
||||
if (match(InVal, m_ImmConstant()) &&
|
||||
(!isa<FreezeInst>(I) || isGuaranteedNotToBeUndefOrPoison(InVal)))
|
||||
continue;
|
||||
|
||||
|
@ -1118,7 +1118,7 @@ Instruction *InstCombinerImpl::foldOpIntoPhi(Instruction &I, PHINode *PN) {
|
|||
// FalseVInPred versus TrueVInPred. When we have individual nonzero
|
||||
// elements in the vector, we will incorrectly fold InC to
|
||||
// `TrueVInPred`.
|
||||
if (InC && !isa<ConstantExpr>(InC) && isa<ConstantInt>(InC))
|
||||
if (InC && isa<ConstantInt>(InC))
|
||||
InV = InC->isNullValue() ? FalseVInPred : TrueVInPred;
|
||||
else {
|
||||
// Generate the select in the same block as PN's current incoming block.
|
||||
|
@ -1608,8 +1608,7 @@ Instruction *InstCombinerImpl::foldVectorBinop(BinaryOperator &Inst) {
|
|||
if (InstVTy &&
|
||||
match(&Inst,
|
||||
m_c_BinOp(m_OneUse(m_Shuffle(m_Value(V1), m_Undef(), m_Mask(Mask))),
|
||||
m_Constant(C))) &&
|
||||
!isa<ConstantExpr>(C) &&
|
||||
m_ImmConstant(C))) &&
|
||||
cast<FixedVectorType>(V1->getType())->getNumElements() <=
|
||||
InstVTy->getNumElements()) {
|
||||
assert(InstVTy->getScalarType() == V1->getType()->getScalarType() &&
|
||||
|
|
Loading…
Reference in New Issue