From 9c3a75eabf577f0e0e372be95ec4861600a5acdb Mon Sep 17 00:00:00 2001 From: Alexey Bataev Date: Mon, 9 May 2022 07:31:33 -0700 Subject: [PATCH] [SLP]Fix a crash when preparing a mask for external scalars. Need to use actual index instead of the tree entry position, since the insert index may be different than 0. It mean, that we vectorized part of the buildvector starting from not initial insertelement instruction beause of some reason. --- llvm/lib/Transforms/Vectorize/SLPVectorizer.cpp | 13 ++++--- .../SLPVectorizer/X86/buildvector-shuffle.ll | 43 ++++++++++++++++++++++ 2 files changed, 51 insertions(+), 5 deletions(-) create mode 100644 llvm/test/Transforms/SLPVectorizer/X86/buildvector-shuffle.ll diff --git a/llvm/lib/Transforms/Vectorize/SLPVectorizer.cpp b/llvm/lib/Transforms/Vectorize/SLPVectorizer.cpp index 23af436..ce58d83 100644 --- a/llvm/lib/Transforms/Vectorize/SLPVectorizer.cpp +++ b/llvm/lib/Transforms/Vectorize/SLPVectorizer.cpp @@ -6559,6 +6559,9 @@ InstructionCost BoUpSLP::getTreeCost(ArrayRef VectorizedVals) { int VecId = -1; if (It == FirstUsers.end()) { (void)ShuffleMasks.emplace_back(); + SmallVectorImpl &Mask = ShuffleMasks.back()[ScalarTE]; + if (Mask.empty()) + Mask.assign(FTy->getNumElements(), UndefMaskElem); // Find the insertvector, vectorized in tree, if any. Value *Base = VU; while (auto *IEBase = dyn_cast(Base)) { @@ -6566,12 +6569,12 @@ InstructionCost BoUpSLP::getTreeCost(ArrayRef VectorizedVals) { if (const TreeEntry *E = getTreeEntry(IEBase)) { VU = IEBase; do { - int Idx = E->findLaneForValue(Base); - SmallVectorImpl &Mask = ShuffleMasks.back()[ScalarTE]; - if (Mask.empty()) - Mask.assign(FTy->getNumElements(), UndefMaskElem); + IEBase = cast(Base); + int Idx = *getInsertIndex(IEBase); + assert(Mask[Idx] == UndefMaskElem && + "InsertElementInstruction used already."); Mask[Idx] = Idx; - Base = cast(Base)->getOperand(0); + Base = IEBase->getOperand(0); } while (E == getTreeEntry(Base)); break; } diff --git a/llvm/test/Transforms/SLPVectorizer/X86/buildvector-shuffle.ll b/llvm/test/Transforms/SLPVectorizer/X86/buildvector-shuffle.ll new file mode 100644 index 0000000..92762dd --- /dev/null +++ b/llvm/test/Transforms/SLPVectorizer/X86/buildvector-shuffle.ll @@ -0,0 +1,43 @@ +; NOTE: Assertions have been autogenerated by utils/update_test_checks.py +; RUN: opt -S -slp-vectorizer -mtriple=x86_64-unknown-linux-gnu < %s | FileCheck %s + +define void @b() { +; CHECK-LABEL: @b( +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP0:%.*]] = insertelement <4 x float> poison, float 0x7FF8000000000000, i32 0 +; CHECK-NEXT: [[TMP1:%.*]] = shufflevector <4 x float> [[TMP0]], <4 x float> , <4 x i32> +; CHECK-NEXT: [[TMP2:%.*]] = insertelement <4 x float> [[TMP1]], float 0x7FF8000000000000, i32 3 +; CHECK-NEXT: [[TMP3:%.*]] = call <4 x float> @llvm.fmuladd.v4f32(<4 x float> [[TMP2]], <4 x float> zeroinitializer, <4 x float> zeroinitializer) +; CHECK-NEXT: [[TMP4:%.*]] = fmul <4 x float> [[TMP3]], +; CHECK-NEXT: [[TMP5:%.*]] = fdiv <4 x float> [[TMP4]], zeroinitializer +; CHECK-NEXT: store <4 x float> [[TMP5]], ptr undef, align 4 +; CHECK-NEXT: ret void +; +entry: + %mul = fmul float undef, 2.000000e+00 + %i = tail call float @llvm.fmuladd.f32(float %mul, float 0.000000e+00, float 0.000000e+00) + %mul2 = fmul float undef, %i + %add = fadd float undef, 1.000000e+00 + %neg = fneg float %add + %i1 = tail call float @llvm.fmuladd.f32(float %neg, float 0.000000e+00, float 0.000000e+00) + %mul4 = fmul float undef, %i1 + %neg7 = fneg float %mul + %i2 = tail call float @llvm.fmuladd.f32(float %neg7, float 0.000000e+00, float 0.000000e+00) + %mul8 = fmul float undef, %i2 + %i3 = tail call float @llvm.fmuladd.f32(float %add, float 0.000000e+00, float 0.000000e+00) + %mul11 = fmul float %i3, 2.000000e+00 + %div = fdiv float %mul2, 0.000000e+00 + store float %div, ptr undef, align 4 + %div12 = fdiv float %mul4, 0.000000e+00 + %arrayidx13 = getelementptr inbounds float, ptr undef, i64 1 + store float %div12, ptr %arrayidx13, align 4 + %div14 = fdiv float %mul8, 0.000000e+00 + %arrayidx15 = getelementptr inbounds float, ptr undef, i64 2 + store float %div14, ptr %arrayidx15, align 4 + %div16 = fdiv float %mul11, 0.000000e+00 + %arrayidx17 = getelementptr inbounds float, ptr undef, i64 3 + store float %div16, ptr %arrayidx17, align 4 + ret void +} + +declare float @llvm.fmuladd.f32(float, float, float) -- 2.7.4