diff --git a/llvm/include/llvm/IR/PatternMatch.h b/llvm/include/llvm/IR/PatternMatch.h index 31ff63c8b660..2901c6456c99 100644 --- a/llvm/include/llvm/IR/PatternMatch.h +++ b/llvm/include/llvm/IR/PatternMatch.h @@ -2513,6 +2513,12 @@ struct LogicalOp_match { auto *Cond = Select->getCondition(); auto *TVal = Select->getTrueValue(); auto *FVal = Select->getFalseValue(); + + // Don't match a scalar select of bool vectors. + // Transforms expect a single type for operands if this matches. + if (Cond->getType() != Select->getType()) + return false; + if (Opcode == Instruction::And) { auto *C = dyn_cast(FVal); if (C && C->isNullValue()) diff --git a/llvm/unittests/IR/PatternMatch.cpp b/llvm/unittests/IR/PatternMatch.cpp index d2ec259ec828..ab35df016cdd 100644 --- a/llvm/unittests/IR/PatternMatch.cpp +++ b/llvm/unittests/IR/PatternMatch.cpp @@ -1730,10 +1730,12 @@ TEST_F(PatternMatchTest, VectorLogicalSelects) { // select i1 Scalar, <3 x i1> , <3 x i1> Vector Value *MixedTypeOr = IRB.CreateSelect(Scalar, T, Vector); + // We allow matching a real vector logical select, + // but not a scalar select of vector bools. EXPECT_TRUE(match(VecAnd, m_LogicalAnd(m_Value(), m_Value()))); - EXPECT_TRUE(match(MixedTypeAnd, m_LogicalAnd(m_Value(), m_Value()))); + EXPECT_FALSE(match(MixedTypeAnd, m_LogicalAnd(m_Value(), m_Value()))); EXPECT_TRUE(match(VecOr, m_LogicalOr(m_Value(), m_Value()))); - EXPECT_TRUE(match(MixedTypeOr, m_LogicalOr(m_Value(), m_Value()))); + EXPECT_FALSE(match(MixedTypeOr, m_LogicalOr(m_Value(), m_Value()))); } TEST_F(PatternMatchTest, VScale) {