From c0a313b57ca27a9bb703418f9fe6e36d8a6c565a Mon Sep 17 00:00:00 2001 From: David Majnemer Date: Fri, 21 Nov 2014 02:34:55 +0000 Subject: [PATCH] SROA: The alloca type isn't a candidate promotion type for vectors The alloca's type is irrelevant, only those types which are used in a load or store of the exact size of the slice should be considered. This manifested as an assertion failure when we compared the various types: we had a size mismatch. This fixes PR21480. llvm-svn: 222499 --- llvm/lib/Transforms/Scalar/Reassociate.cpp | 7 +++++++ llvm/lib/Transforms/Scalar/SROA.cpp | 5 ++--- llvm/test/Transforms/SROA/vector-promotion.ll | 19 +++++++++++++++++++ 3 files changed, 28 insertions(+), 3 deletions(-) diff --git a/llvm/lib/Transforms/Scalar/Reassociate.cpp b/llvm/lib/Transforms/Scalar/Reassociate.cpp index 1bbaaf3..d37eac5 100644 --- a/llvm/lib/Transforms/Scalar/Reassociate.cpp +++ b/llvm/lib/Transforms/Scalar/Reassociate.cpp @@ -394,6 +394,13 @@ static BinaryOperator *LowerNegateToMultiply(Instruction *Neg) { BinaryOperator *Res = CreateMul(Neg->getOperand(1), NegOne, "", Neg, Neg); Neg->setOperand(1, Constant::getNullValue(Ty)); // Drop use of op. Res->takeName(Neg); + if (Ty->isIntegerTy()) { + bool NSW = cast(Neg)->hasNoSignedWrap(); + bool NUW = cast(Neg)->hasNoUnsignedWrap(); + if (NSW || NUW) + Res->setHasNoSignedWrap(true); + Res->setHasNoUnsignedWrap(NUW); + } Neg->replaceAllUsesWith(Res); Res->setDebugLoc(Neg->getDebugLoc()); return Res; diff --git a/llvm/lib/Transforms/Scalar/SROA.cpp b/llvm/lib/Transforms/Scalar/SROA.cpp index 6135114e..f9ebd75 100644 --- a/llvm/lib/Transforms/Scalar/SROA.cpp +++ b/llvm/lib/Transforms/Scalar/SROA.cpp @@ -1691,7 +1691,7 @@ isVectorPromotionViableForSlice(const DataLayout &DL, uint64_t SliceBeginOffset, /// don't want to do the rewrites unless we are confident that the result will /// be promotable, so we have an early test here. static VectorType * -isVectorPromotionViable(const DataLayout &DL, Type *AllocaTy, +isVectorPromotionViable(const DataLayout &DL, uint64_t SliceBeginOffset, uint64_t SliceEndOffset, AllocaSlices::const_range Slices, ArrayRef SplitUses) { @@ -1709,7 +1709,6 @@ isVectorPromotionViable(const DataLayout &DL, Type *AllocaTy, HaveCommonEltTy = false; } }; - CheckCandidateType(AllocaTy); // Consider any loads or stores that are the exact size of the slice. for (const auto &S : Slices) if (S.beginOffset() == SliceBeginOffset && @@ -3213,7 +3212,7 @@ bool SROA::rewritePartition(AllocaInst &AI, AllocaSlices &AS, VectorType *VecTy = IsIntegerPromotable ? nullptr - : isVectorPromotionViable(*DL, SliceTy, BeginOffset, EndOffset, + : isVectorPromotionViable(*DL, BeginOffset, EndOffset, AllocaSlices::const_range(B, E), SplitUses); if (VecTy) SliceTy = VecTy; diff --git a/llvm/test/Transforms/SROA/vector-promotion.ll b/llvm/test/Transforms/SROA/vector-promotion.ll index 830a22a..c20c635 100644 --- a/llvm/test/Transforms/SROA/vector-promotion.ll +++ b/llvm/test/Transforms/SROA/vector-promotion.ll @@ -604,3 +604,22 @@ entry: ret <2 x float> %result ; CHECK-NEXT: ret <2 x float> %[[V4]] } + +define <4 x float> @test12() { +; CHECK-LABEL: @test12( + %a = alloca <3 x i32>, align 16 +; CHECK-NOT: alloca + + %cast1 = bitcast <3 x i32>* %a to <4 x i32>* + store <4 x i32> undef, <4 x i32>* %cast1, align 16 +; CHECK-NOT: store + + %cast2 = bitcast <3 x i32>* %a to <3 x float>* + %cast3 = bitcast <3 x float>* %cast2 to <4 x float>* + %vec = load <4 x float>* %cast3 +; CHECK-NOT: load + +; CHECK: %[[ret:.*]] = bitcast <4 x i32> undef to <4 x float> +; CHECK-NEXT: ret <4 x float> %[[ret]] + ret <4 x float> %vec +} -- 2.7.4