[llvm] [AArch64]: Replaced assertion with check (PR #173737)
Kevin Per via llvm-commits
llvm-commits at lists.llvm.org
Sat Dec 27 10:27:12 PST 2025
https://github.com/kper created https://github.com/llvm/llvm-project/pull/173737
The crash was triggered because `%38` violates the assertion since `WideTy` is a scalar value and smaller than 128 bits.
LLC debug from referenced issue:
`Select: %32:fpr(s16), %33:fpr(s16) = G_UNMERGE_VALUES %38:fpr(s32)`
This PR replaces the assertion with a check that returns `false` which forces a different instruction selection.
Closes https://github.com/llvm/llvm-project/issues/173722
>From 8646bb0543aa2ae73c448360df9f79b37dfd1372 Mon Sep 17 00:00:00 2001
From: Kevin Per <kevin.per at protonmail.com>
Date: Sat, 27 Dec 2025 19:21:06 +0100
Subject: [PATCH] [AArch64]: Replaced assertion with conditional
---
.../GISel/AArch64InstructionSelector.cpp | 7 +-
...aarch64-avoid-illegal-extract-subvector.ll | 112 +++++++++++++++---
2 files changed, 99 insertions(+), 20 deletions(-)
diff --git a/llvm/lib/Target/AArch64/GISel/AArch64InstructionSelector.cpp b/llvm/lib/Target/AArch64/GISel/AArch64InstructionSelector.cpp
index f9db39e5f8622..f9f78c4242568 100644
--- a/llvm/lib/Target/AArch64/GISel/AArch64InstructionSelector.cpp
+++ b/llvm/lib/Target/AArch64/GISel/AArch64InstructionSelector.cpp
@@ -4085,8 +4085,11 @@ bool AArch64InstructionSelector::selectUnmergeValues(MachineInstr &I,
const LLT NarrowTy = MRI.getType(I.getOperand(0).getReg());
const LLT WideTy = MRI.getType(SrcReg);
(void)WideTy;
- assert((WideTy.isVector() || WideTy.getSizeInBits() == 128) &&
- "can only unmerge from vector or s128 types!");
+ if (!(WideTy.isVector() || WideTy.getSizeInBits() == 128)) {
+ LLVM_DEBUG(dbgs() << "can only unmerge from vector or s128 types!.\n");
+ return false;
+ }
+
assert(WideTy.getSizeInBits() > NarrowTy.getSizeInBits() &&
"source register size too small!");
diff --git a/llvm/test/CodeGen/AArch64/aarch64-avoid-illegal-extract-subvector.ll b/llvm/test/CodeGen/AArch64/aarch64-avoid-illegal-extract-subvector.ll
index 925b4c87ec9a5..d19dcbb577aa3 100644
--- a/llvm/test/CodeGen/AArch64/aarch64-avoid-illegal-extract-subvector.ll
+++ b/llvm/test/CodeGen/AArch64/aarch64-avoid-illegal-extract-subvector.ll
@@ -1,13 +1,25 @@
; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py
-; RUN: llc -mtriple=aarch64-none-linux-gnu < %s -o -| FileCheck %s
+; RUN: llc -mtriple=aarch64-none-linux-gnu < %s -o -| FileCheck %s --check-prefix=O2
+; RUN: llc -O0 -mtriple=aarch64-none-linux-gnu < %s -o -| FileCheck %s --check-prefix=O0
define <2 x i64> @test1(<4 x i32> %x) #0 {
-; CHECK-LABEL: test1:
-; CHECK: // %bb.0:
-; CHECK-NEXT: mov w8, v0.s[1]
-; CHECK-NEXT: mov w9, v0.s[2]
-; CHECK-NEXT: fmov d0, x8
-; CHECK-NEXT: mov v0.d[1], x9
-; CHECK-NEXT: ret
+; O2-LABEL: test1:
+; O2: // %bb.0:
+; O2-NEXT: mov w8, v0.s[1]
+; O2-NEXT: mov w9, v0.s[2]
+; O2-NEXT: fmov d0, x8
+; O2-NEXT: mov v0.d[1], x9
+; O2-NEXT: ret
+;
+; O0-LABEL: test1:
+; O0: // %bb.0:
+; O0-NEXT: mov w8, v0.s[1]
+; O0-NEXT: mov w9, w8
+; O0-NEXT: mov w8, v0.s[2]
+; O0-NEXT: // kill: def $x8 killed $w8
+; O0-NEXT: // implicit-def: $q0
+; O0-NEXT: fmov d0, x9
+; O0-NEXT: mov v0.d[1], x8
+; O0-NEXT: ret
%i1 = extractelement <4 x i32> %x, i32 1
%zi1 = zext i32 %i1 to i64
%i2 = extractelement <4 x i32> %x, i32 2
@@ -18,16 +30,32 @@ define <2 x i64> @test1(<4 x i32> %x) #0 {
}
define <4 x i64> @test2(<4 x i32> %0) {
-; CHECK-LABEL: test2:
-; CHECK: // %bb.0: // %entry
-; CHECK-NEXT: adrp x8, .LCPI1_0
-; CHECK-NEXT: ldr q1, [x8, :lo12:.LCPI1_0]
-; CHECK-NEXT: add v0.4s, v0.4s, v1.4s
-; CHECK-NEXT: mov w8, v0.s[1]
-; CHECK-NEXT: mov w9, v0.s[2]
-; CHECK-NEXT: fmov d1, x8
-; CHECK-NEXT: mov v1.d[1], x9
-; CHECK-NEXT: ret
+; O2-LABEL: test2:
+; O2: // %bb.0: // %entry
+; O2-NEXT: adrp x8, .LCPI1_0
+; O2-NEXT: ldr q1, [x8, :lo12:.LCPI1_0]
+; O2-NEXT: add v0.4s, v0.4s, v1.4s
+; O2-NEXT: mov w8, v0.s[1]
+; O2-NEXT: mov w9, v0.s[2]
+; O2-NEXT: fmov d1, x8
+; O2-NEXT: mov v1.d[1], x9
+; O2-NEXT: ret
+;
+; O0-LABEL: test2:
+; O0: // %bb.0: // %entry
+; O0-NEXT: mov v1.16b, v0.16b
+; O0-NEXT: adrp x8, .LCPI1_0
+; O0-NEXT: ldr q2, [x8, :lo12:.LCPI1_0]
+; O0-NEXT: // implicit-def: $q0
+; O0-NEXT: add v1.4s, v1.4s, v2.4s
+; O0-NEXT: mov w8, v1.s[1]
+; O0-NEXT: mov w9, w8
+; O0-NEXT: mov w8, v1.s[2]
+; O0-NEXT: // kill: def $x8 killed $w8
+; O0-NEXT: // implicit-def: $q1
+; O0-NEXT: fmov d1, x9
+; O0-NEXT: mov v1.d[1], x8
+; O0-NEXT: ret
entry:
%1 = add <4 x i32> %0, <i32 -4, i32 -8, i32 -12, i32 -16>
%2 = extractelement <4 x i32> %1, i32 1
@@ -38,3 +66,51 @@ entry:
%5 = insertelement <4 x i64> %4, i64 %zext2, i32 3
ret <4 x i64> %5
}
+
+; This issue was only triggered with -O0
+define i2 @issue_173722(<1 x i16> %call) {
+; O2-LABEL: issue_173722:
+; O2: // %bb.0: // %entry
+; O2-NEXT: mov w0, wzr
+; O2-NEXT: ret
+;
+; O0-LABEL: issue_173722:
+; O0: // %bb.0: // %entry
+; O0-NEXT: sub sp, sp, #16
+; O0-NEXT: .cfi_def_cfa_offset 16
+; O0-NEXT: str d0, [sp, #8] // 8-byte Spill
+; O0-NEXT: mov w8, #1 // =0x1
+; O0-NEXT: cbnz w8, .LBB2_2
+; O0-NEXT: b .LBB2_1
+; O0-NEXT: .LBB2_1: // %cond.true
+; O0-NEXT: ldr d1, [sp, #8] // 8-byte Reload
+; O0-NEXT: // implicit-def: $q0
+; O0-NEXT: fmov d0, d1
+; O0-NEXT: umov w0, v0.h[0]
+; O0-NEXT: str w0, [sp, #4] // 4-byte Spill
+; O0-NEXT: b .LBB2_3
+; O0-NEXT: .LBB2_2: // %cond.false
+; O0-NEXT: mov w0, wzr
+; O0-NEXT: str w0, [sp, #4] // 4-byte Spill
+; O0-NEXT: b .LBB2_3
+; O0-NEXT: .LBB2_3: // %cond.end
+; O0-NEXT: ldr w0, [sp, #4] // 4-byte Reload
+; O0-NEXT: add sp, sp, #16
+; O0-NEXT: ret
+entry:
+ br i1 false, label %cond.true, label %cond.false
+
+cond.true: ; preds = %entry
+ %vecext = extractelement <1 x i16> %call, i32 0
+ %conv = trunc i16 %vecext to i2
+ br label %cond.end
+
+cond.false: ; preds = %entry
+ %conv3 = zext i32 0 to i104
+ %conv4 = trunc i104 %conv3 to i2
+ br label %cond.end
+
+cond.end: ; preds = %cond.false, %cond.true
+ %cond = phi i2 [ %conv, %cond.true ], [ %conv4, %cond.false ]
+ ret i2 %cond
+}
More information about the llvm-commits
mailing list