[llvm] [VectorCombine] Fix crash with poison mask elements in shrinkLoadForShuffles (PR #178920)

via llvm-commits llvm-commits at lists.llvm.org
Fri Jan 30 09:50:25 PST 2026


https://github.com/mugiwaraluffy56 updated https://github.com/llvm/llvm-project/pull/178920

>From 63edf775afc7eeb301aa680085593b36547c740e Mon Sep 17 00:00:00 2001
From: mugiwaraluffy56 <myakampuneeth at gmail.com>
Date: Fri, 30 Jan 2026 22:35:07 +0530
Subject: [PATCH] [VectorCombine] Fix crash with poison mask elements in
 shrinkLoadForShuffles

The mask index adjustment for load trimming was incorrectly modifying
poison indices (represented as -1), resulting in invalid values like -2
that caused assertion failures in isSingleSourceMaskImpl.

Preserve poison indices without modification since they don't reference
any actual vector elements.

Fixes #178917

Co-Authored-By: Claude <noreply at anthropic.com>
---
 llvm/lib/Transforms/Vectorize/VectorCombine.cpp    |  5 +++++
 .../Transforms/VectorCombine/load-shufflevector.ll | 14 ++++++++++++++
 2 files changed, 19 insertions(+)

diff --git a/llvm/lib/Transforms/Vectorize/VectorCombine.cpp b/llvm/lib/Transforms/Vectorize/VectorCombine.cpp
index d173afd24e54c..c1cca6e28a8ec 100644
--- a/llvm/lib/Transforms/Vectorize/VectorCombine.cpp
+++ b/llvm/lib/Transforms/Vectorize/VectorCombine.cpp
@@ -5453,6 +5453,11 @@ bool VectorCombine::shrinkLoadForShuffles(Instruction &I) {
         NewUses.push_back({Shuffle, {}});
         std::vector<int> &NewMask = NewUses.back().second;
         for (int Index : OldMask) {
+          // Preserve poison indices without modification.
+          if (Index == PoisonMaskElem) {
+            NewMask.push_back(Index);
+            continue;
+          }
           int NewIndex = Index >= static_cast<int>(OldNumElements)
                              ? Index - LowOffset - HighOffset
                              : Index - LowOffset;
diff --git a/llvm/test/Transforms/VectorCombine/load-shufflevector.ll b/llvm/test/Transforms/VectorCombine/load-shufflevector.ll
index 2b5cec9ccfde5..3626a5d8e731f 100644
--- a/llvm/test/Transforms/VectorCombine/load-shufflevector.ll
+++ b/llvm/test/Transforms/VectorCombine/load-shufflevector.ll
@@ -411,3 +411,17 @@ define <16 x i8> @shuffle_v16_v16i8_r0_31(ptr %arg) {
   %shuf = shufflevector <16 x i8> %load, <16 x i8> poison, <16 x i32> <i32 0, i32 1, i32 2, i32 3, i32 4, i32 5, i32 6, i32 7, i32 24, i32 25, i32 26, i32 27, i32 28, i32 29, i32 30, i32 31>
   ret <16 x i8> %shuf
 }
+
+; GH#178917: Verify poison mask elements are preserved when trimming loads.
+define <8 x i16> @shuffle_with_poison_mask(ptr %p) {
+; CHECK-LABEL: define <8 x i16> @shuffle_with_poison_mask(
+; CHECK-SAME: ptr [[P:%.*]]) {
+; CHECK-NEXT:    [[TMP1:%.*]] = getelementptr inbounds i8, ptr [[P]], i64 1
+; CHECK-NEXT:    [[TMP2:%.*]] = load <7 x i16>, ptr [[TMP1]], align 1
+; CHECK-NEXT:    [[SHUF:%.*]] = shufflevector <7 x i16> [[TMP2]], <7 x i16> poison, <8 x i32> <i32 0, i32 2, i32 poison, i32 poison, i32 poison, i32 4, i32 poison, i32 6>
+; CHECK-NEXT:    ret <8 x i16> [[SHUF]]
+;
+  %pre = load <8 x i16>, ptr %p, align 1
+  %shuf = shufflevector <8 x i16> %pre, <8 x i16> poison, <8 x i32> <i32 1, i32 3, i32 poison, i32 poison, i32 poison, i32 5, i32 poison, i32 7>
+  ret <8 x i16> %shuf
+}



More information about the llvm-commits mailing list