From 582a2bb8aff23fe74ffeffe9544988c834fa9934 Mon Sep 17 00:00:00 2001 From: Craig Topper Date: Fri, 4 Aug 2017 16:07:20 +0000 Subject: [PATCH] [InstCombine] Remove the (not (sext)) case from foldBoolSextMaskToSelect and inline the remaining code to match visitOr Summary: The (not (sext)) case is really (xor (sext), -1) which should have been simplified to (sext (xor, 1)) before we got here. So we shouldn't need to handle it. With that taken care of we only need to two cases so don't need the swap anymore. This makes us in sync with the equivalent code in visitOr so inline this to match. Reviewers: spatel, eli.friedman, majnemer Reviewed By: spatel Subscribers: llvm-commits Differential Revision: https://reviews.llvm.org/D36240 git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@310063 91177308-0d34-0410-b5e6-96231b3b80d8 --- .../InstCombine/InstCombineAndOrXor.cpp | 35 +++++-------------- test/Transforms/InstCombine/vector-casts.ll | 2 +- 2 files changed, 9 insertions(+), 28 deletions(-) diff --git a/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp b/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp index 62a73cca4b7..a3749a1581b 100644 --- a/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp +++ b/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp @@ -1188,31 +1188,6 @@ Instruction *InstCombiner::foldCastedBitwiseLogic(BinaryOperator &I) { return nullptr; } -static Instruction *foldBoolSextMaskToSelect(BinaryOperator &I) { - Value *Op0 = I.getOperand(0), *Op1 = I.getOperand(1); - - // Canonicalize SExt or Not to the LHS - if (match(Op1, m_SExt(m_Value())) || match(Op1, m_Not(m_Value()))) { - std::swap(Op0, Op1); - } - - // Fold (and (sext bool to A), B) --> (select bool, B, 0) - Value *X = nullptr; - if (match(Op0, m_SExt(m_Value(X))) && X->getType()->isIntOrIntVectorTy(1)) { - Value *Zero = Constant::getNullValue(Op1->getType()); - return SelectInst::Create(X, Op1, Zero); - } - - // Fold (and ~(sext bool to A), B) --> (select bool, 0, B) - if (match(Op0, m_Not(m_SExt(m_Value(X)))) && - X->getType()->isIntOrIntVectorTy(1)) { - Value *Zero = Constant::getNullValue(Op0->getType()); - return SelectInst::Create(X, Zero, Op1); - } - - return nullptr; -} - static Instruction *foldAndToXor(BinaryOperator &I, InstCombiner::BuilderTy &Builder) { assert(I.getOpcode() == Instruction::And); @@ -1480,8 +1455,14 @@ Instruction *InstCombiner::visitAnd(BinaryOperator &I) { if (Instruction *CastedAnd = foldCastedBitwiseLogic(I)) return CastedAnd; - if (Instruction *Select = foldBoolSextMaskToSelect(I)) - return Select; + // and(sext(A), B) / and(B, sext(A)) --> A ? B : 0, where A is i1 or . + Value *A; + if (match(Op0, m_OneUse(m_SExt(m_Value(A)))) && + A->getType()->isIntOrIntVectorTy(1)) + return SelectInst::Create(A, Op1, Constant::getNullValue(I.getType())); + if (match(Op1, m_OneUse(m_SExt(m_Value(A)))) && + A->getType()->isIntOrIntVectorTy(1)) + return SelectInst::Create(A, Op0, Constant::getNullValue(I.getType())); return Changed ? &I : nullptr; } diff --git a/test/Transforms/InstCombine/vector-casts.ll b/test/Transforms/InstCombine/vector-casts.ll index e52e063a405..447f86f05d2 100644 --- a/test/Transforms/InstCombine/vector-casts.ll +++ b/test/Transforms/InstCombine/vector-casts.ll @@ -61,7 +61,7 @@ define <2 x i64> @test5(<4 x float> %a, <4 x float> %b) { ; CHECK-LABEL: @test5( ; CHECK-NEXT: [[CMP:%.*]] = fcmp ult <4 x float> %a, zeroinitializer ; CHECK-NEXT: [[CMP4:%.*]] = fcmp ult <4 x float> %b, zeroinitializer -; CHECK-NEXT: [[NARROW:%.*]] = and <4 x i1> [[CMP4]], [[CMP]] +; CHECK-NEXT: [[NARROW:%.*]] = and <4 x i1> [[CMP]], [[CMP4]] ; CHECK-NEXT: [[AND:%.*]] = sext <4 x i1> [[NARROW]] to <4 x i32> ; CHECK-NEXT: [[CONV:%.*]] = bitcast <4 x i32> [[AND]] to <2 x i64> ; CHECK-NEXT: ret <2 x i64> [[CONV]] -- 2.50.1