Index: llvm/trunk/include/llvm/IR/PatternMatch.h =================================================================== --- llvm/trunk/include/llvm/IR/PatternMatch.h +++ llvm/trunk/include/llvm/IR/PatternMatch.h @@ -215,6 +215,7 @@ // Non-splat vector constant: check each element for a match. unsigned NumElts = V->getType()->getVectorNumElements(); assert(NumElts != 0 && "Constant vector with no elements?"); + bool HasNonUndefElements = false; for (unsigned i = 0; i != NumElts; ++i) { Constant *Elt = C->getAggregateElement(i); if (!Elt) @@ -224,8 +225,9 @@ auto *CI = dyn_cast(Elt); if (!CI || !this->isValue(CI->getValue())) return false; + HasNonUndefElements = true; } - return true; + return HasNonUndefElements; } } return false; @@ -272,6 +274,7 @@ // Non-splat vector constant: check each element for a match. unsigned NumElts = V->getType()->getVectorNumElements(); assert(NumElts != 0 && "Constant vector with no elements?"); + bool HasNonUndefElements = false; for (unsigned i = 0; i != NumElts; ++i) { Constant *Elt = C->getAggregateElement(i); if (!Elt) @@ -281,8 +284,9 @@ auto *CF = dyn_cast(Elt); if (!CF || !this->isValue(CF->getValueAPF())) return false; + HasNonUndefElements = true; } - return true; + return HasNonUndefElements; } } return false; Index: llvm/trunk/test/Transforms/InstSimplify/shr-scalar-vector-consistency.ll =================================================================== --- llvm/trunk/test/Transforms/InstSimplify/shr-scalar-vector-consistency.ll +++ llvm/trunk/test/Transforms/InstSimplify/shr-scalar-vector-consistency.ll @@ -16,7 +16,7 @@ define <2 x i32> @test_vector(<2 x i32> %a, <2 x i1> %b) { ; CHECK-LABEL: @test_vector( -; CHECK-NEXT: ret <2 x i32> zeroinitializer +; CHECK-NEXT: ret <2 x i32> undef ; %c = sext <2 x i1> %b to <2 x i32> %d = ashr <2 x i32> undef, %c Index: llvm/trunk/test/Transforms/Reassociate/fp-expr.ll =================================================================== --- llvm/trunk/test/Transforms/Reassociate/fp-expr.ll +++ llvm/trunk/test/Transforms/Reassociate/fp-expr.ll @@ -4,8 +4,8 @@ define void @test1() { ; CHECK-LABEL: @test1( ; CHECK-NEXT: [[T1:%.*]] = tail call <4 x float> @blam() -; CHECK-NEXT: [[T23:%.*]] = fsub fast <4 x float> undef, [[T1]] -; CHECK-NEXT: [[T24:%.*]] = fadd fast <4 x float> [[T23]], undef +; CHECK-NEXT: [[T1_NEG:%.*]] = fsub fast <4 x float> , [[T1]] +; CHECK-NEXT: [[T24:%.*]] = fadd fast <4 x float> [[T1_NEG]], undef ; CHECK-NEXT: tail call void @wombat(<4 x float> [[T24]]) ; CHECK-NEXT: ret void ; Index: llvm/trunk/unittests/IR/PatternMatch.cpp =================================================================== --- llvm/trunk/unittests/IR/PatternMatch.cpp +++ llvm/trunk/unittests/IR/PatternMatch.cpp @@ -534,6 +534,62 @@ EXPECT_TRUE(A == Val); } +TEST_F(PatternMatchTest, VectorUndefInt) { + Type *ScalarTy = IRB.getInt8Ty(); + Type *VectorTy = VectorType::get(ScalarTy, 4); + Constant *ScalarUndef = UndefValue::get(ScalarTy); + Constant *VectorUndef = UndefValue::get(VectorTy); + Constant *ScalarZero = Constant::getNullValue(ScalarTy); + Constant *VectorZero = Constant::getNullValue(VectorTy); + + SmallVector Elems; + Elems.push_back(ScalarUndef); + Elems.push_back(ScalarZero); + Elems.push_back(ScalarUndef); + Elems.push_back(ScalarZero); + Constant *VectorZeroUndef = ConstantVector::get(Elems); + + EXPECT_TRUE(match(ScalarUndef, m_Undef())); + EXPECT_TRUE(match(VectorUndef, m_Undef())); + EXPECT_FALSE(match(ScalarZero, m_Undef())); + EXPECT_FALSE(match(VectorZero, m_Undef())); + EXPECT_FALSE(match(VectorZeroUndef, m_Undef())); + + EXPECT_FALSE(match(ScalarUndef, m_Zero())); + EXPECT_FALSE(match(VectorUndef, m_Zero())); + EXPECT_TRUE(match(ScalarZero, m_Zero())); + EXPECT_TRUE(match(VectorZero, m_Zero())); + EXPECT_TRUE(match(VectorZeroUndef, m_Zero())); +} + +TEST_F(PatternMatchTest, VectorUndefFloat) { + Type *ScalarTy = IRB.getFloatTy(); + Type *VectorTy = VectorType::get(ScalarTy, 4); + Constant *ScalarUndef = UndefValue::get(ScalarTy); + Constant *VectorUndef = UndefValue::get(VectorTy); + Constant *ScalarZero = Constant::getNullValue(ScalarTy); + Constant *VectorZero = Constant::getNullValue(VectorTy); + + SmallVector Elems; + Elems.push_back(ScalarUndef); + Elems.push_back(ScalarZero); + Elems.push_back(ScalarUndef); + Elems.push_back(ScalarZero); + Constant *VectorZeroUndef = ConstantVector::get(Elems); + + EXPECT_TRUE(match(ScalarUndef, m_Undef())); + EXPECT_TRUE(match(VectorUndef, m_Undef())); + EXPECT_FALSE(match(ScalarZero, m_Undef())); + EXPECT_FALSE(match(VectorZero, m_Undef())); + EXPECT_FALSE(match(VectorZeroUndef, m_Undef())); + + EXPECT_FALSE(match(ScalarUndef, m_AnyZeroFP())); + EXPECT_FALSE(match(VectorUndef, m_AnyZeroFP())); + EXPECT_TRUE(match(ScalarZero, m_AnyZeroFP())); + EXPECT_TRUE(match(VectorZero, m_AnyZeroFP())); + EXPECT_TRUE(match(VectorZeroUndef, m_AnyZeroFP())); +} + template struct MutableConstTest : PatternMatchTest { }; typedef ::testing::Types,