From: Benjamin Kramer Date: Sun, 20 Feb 2011 15:20:01 +0000 (+0000) Subject: Move "A | ~(A & ?) -> -1" from InstCombine to InstructionSimplify. X-Git-Url: http://plrg.eecs.uci.edu/git/?a=commitdiff_plain;h=38f7f66fcc6ed5e43be4d9c96c782d4eabdb7342;p=oota-llvm.git Move "A | ~(A & ?) -> -1" from InstCombine to InstructionSimplify. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@126082 91177308-0d34-0410-b5e6-96231b3b80d8 --- diff --git a/lib/Analysis/InstructionSimplify.cpp b/lib/Analysis/InstructionSimplify.cpp index a2f9862383f..982dacb50bf 100644 --- a/lib/Analysis/InstructionSimplify.cpp +++ b/lib/Analysis/InstructionSimplify.cpp @@ -1161,6 +1161,16 @@ static Value *SimplifyOrInst(Value *Op0, Value *Op1, const TargetData *TD, (A == Op0 || B == Op0)) return Op0; + // ~(A & ?) | A = -1 + if (match(Op0, m_Not(m_And(m_Value(A), m_Value(B)))) && + (A == Op1 || B == Op1)) + return Constant::getAllOnesValue(Op1->getType()); + + // A | ~(A & ?) = -1 + if (match(Op1, m_Not(m_And(m_Value(A), m_Value(B)))) && + (A == Op0 || B == Op0)) + return Constant::getAllOnesValue(Op0->getType()); + // Try some generic simplifications for associative operations. if (Value *V = SimplifyAssociativeBinOp(Instruction::Or, Op0, Op1, TD, DT, MaxRecurse)) diff --git a/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp b/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp index 07069ada9a2..7986d1aca76 100644 --- a/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp +++ b/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp @@ -1919,24 +1919,16 @@ Instruction *InstCombiner::visitOr(BinaryOperator &I) { // A | ~(A | B) -> A | ~B // A | ~(A ^ B) -> A | ~B - // A | ~(A & B) -> -1 if (match(Op1, m_Not(m_Value(A)))) if (BinaryOperator *B = dyn_cast(A)) - if (Op0 == B->getOperand(0) || Op0 == B->getOperand(1)) - switch (B->getOpcode()) { - default: break; - case Instruction::Or: - case Instruction::Xor: - if (Op1->hasOneUse()) { - Value *NotOp = Op0 == B->getOperand(0) ? B->getOperand(1) : - B->getOperand(0); - Value *Not = Builder->CreateNot(NotOp, NotOp->getName()+".not"); - return BinaryOperator::CreateOr(Not, Op0); - } - break; - case Instruction::And: - return ReplaceInstUsesWith(I, Constant::getAllOnesValue(I.getType())); - } + if ((Op0 == B->getOperand(0) || Op0 == B->getOperand(1)) && + Op1->hasOneUse() && (B->getOpcode() == Instruction::Or || + B->getOpcode() == Instruction::Xor)) { + Value *NotOp = Op0 == B->getOperand(0) ? B->getOperand(1) : + B->getOperand(0); + Value *Not = Builder->CreateNot(NotOp, NotOp->getName()+".not"); + return BinaryOperator::CreateOr(Not, Op0); + } if (ICmpInst *RHS = dyn_cast(I.getOperand(1))) if (ICmpInst *LHS = dyn_cast(I.getOperand(0)))