[llvm] [AArch64] Disable coalescing of SUBREG_TO_REG with subreg liveness. (PR #174185)

via llvm-commits llvm-commits at lists.llvm.org
Fri Jan 2 00:17:27 PST 2026


llvmbot wrote:


<!--LLVM PR SUMMARY COMMENT-->

@llvm/pr-subscribers-backend-aarch64

Author: Sander de Smalen (sdesmalen-arm)

<details>
<summary>Changes</summary>

Handling of SUBREG_TO_REG is currently broken, see #<!-- -->168353 for details.

---
Full diff: https://github.com/llvm/llvm-project/pull/174185.diff


5 Files Affected:

- (modified) llvm/lib/Target/AArch64/AArch64RegisterInfo.cpp (+7-1) 
- (modified) llvm/test/CodeGen/AArch64/arm64-addrmode.ll (+90-40) 
- (modified) llvm/test/CodeGen/AArch64/preserve_nonecc_varargs_darwin.ll (+10-5) 
- (modified) llvm/test/CodeGen/AArch64/register-coalesce-update-subranges-remat.mir (+1) 
- (added) llvm/test/CodeGen/AArch64/subreg_to_reg_coalescing_issue.mir (+34) 


``````````diff
diff --git a/llvm/lib/Target/AArch64/AArch64RegisterInfo.cpp b/llvm/lib/Target/AArch64/AArch64RegisterInfo.cpp
index ee43448d5baec..a90cad4f19ef7 100644
--- a/llvm/lib/Target/AArch64/AArch64RegisterInfo.cpp
+++ b/llvm/lib/Target/AArch64/AArch64RegisterInfo.cpp
@@ -1380,7 +1380,13 @@ bool AArch64RegisterInfo::shouldCoalesce(
     MachineInstr *MI, const TargetRegisterClass *SrcRC, unsigned SubReg,
     const TargetRegisterClass *DstRC, unsigned DstSubReg,
     const TargetRegisterClass *NewRC, LiveIntervals &LIS) const {
-  MachineRegisterInfo &MRI = MI->getMF()->getRegInfo();
+  MachineFunction &MF = *MI->getMF();
+  MachineRegisterInfo &MRI = MF.getRegInfo();
+
+  // Coalescing of SUBREG_TO_REG is broken when using subreg liveness tracking,
+  // we must disable it for now.
+  if (MI->isSubregToReg() && MRI.subRegLivenessEnabled())
+    return false;
 
   if (MI->isCopy() &&
       ((DstRC->getID() == AArch64::GPR64RegClassID) ||
diff --git a/llvm/test/CodeGen/AArch64/arm64-addrmode.ll b/llvm/test/CodeGen/AArch64/arm64-addrmode.ll
index f8695b62619c0..c8b7035b7c6e3 100644
--- a/llvm/test/CodeGen/AArch64/arm64-addrmode.ll
+++ b/llvm/test/CodeGen/AArch64/arm64-addrmode.ll
@@ -43,6 +43,7 @@ define void @t4(ptr %object) {
 ; CHECK-LABEL: t4:
 ; CHECK:       // %bb.0:
 ; CHECK-NEXT:    mov w8, #32768 // =0x8000
+; CHECK-NEXT:    // kill: def $x8 killed $w8
 ; CHECK-NEXT:    ldr xzr, [x0, x8]
 ; CHECK-NEXT:    ret
   %incdec.ptr = getelementptr inbounds i64, ptr %object, i64 4096
@@ -69,6 +70,7 @@ define void @t6(i64 %a, ptr %object) {
 ; CHECK:       // %bb.0:
 ; CHECK-NEXT:    add x8, x1, x0, lsl #3
 ; CHECK-NEXT:    mov w9, #32768 // =0x8000
+; CHECK-NEXT:    // kill: def $x9 killed $w9
 ; CHECK-NEXT:    ldr xzr, [x8, x9]
 ; CHECK-NEXT:    ret
   %tmp1 = getelementptr inbounds i64, ptr %object, i64 %a
@@ -82,6 +84,7 @@ define void @t7(i64 %a) {
 ; CHECK-LABEL: t7:
 ; CHECK:       // %bb.0:
 ; CHECK-NEXT:    mov w8, #65535 // =0xffff
+; CHECK-NEXT:    // kill: def $x8 killed $w8
 ; CHECK-NEXT:    ldr xzr, [x0, x8]
 ; CHECK-NEXT:    ret
   %1 = add i64 %a, 65535   ;0xffff
@@ -131,6 +134,7 @@ define void @t11(i64 %a) {
 ; CHECK:       // %bb.0:
 ; CHECK-NEXT:    mov w8, #17767 // =0x4567
 ; CHECK-NEXT:    movk w8, #291, lsl #16
+; CHECK-NEXT:    // kill: def $x8 killed $w8
 ; CHECK-NEXT:    ldr xzr, [x0, x8]
 ; CHECK-NEXT:    ret
   %1 = add i64 %a, 19088743   ;0x1234567
@@ -214,8 +218,10 @@ define void @t17(i64 %a) {
 define i8 @LdOffset_i8(ptr %a)  {
 ; CHECK-LABEL: LdOffset_i8:
 ; CHECK:       // %bb.0:
-; CHECK-NEXT:    add x8, x0, #253, lsl #12 // =1036288
-; CHECK-NEXT:    ldrb w0, [x8, #3704]
+; CHECK-NEXT:    mov w8, #56952 // =0xde78
+; CHECK-NEXT:    movk w8, #15, lsl #16
+; CHECK-NEXT:    // kill: def $x8 killed $w8
+; CHECK-NEXT:    ldrb w0, [x0, x8]
 ; CHECK-NEXT:    ret
   %arrayidx = getelementptr inbounds i8, ptr %a, i64 1039992
   %val = load i8, ptr %arrayidx, align 1
@@ -226,8 +232,10 @@ define i8 @LdOffset_i8(ptr %a)  {
 define i32 @LdOffset_i8_zext32(ptr %a)  {
 ; CHECK-LABEL: LdOffset_i8_zext32:
 ; CHECK:       // %bb.0:
-; CHECK-NEXT:    add x8, x0, #253, lsl #12 // =1036288
-; CHECK-NEXT:    ldrb w0, [x8, #3704]
+; CHECK-NEXT:    mov w8, #56952 // =0xde78
+; CHECK-NEXT:    movk w8, #15, lsl #16
+; CHECK-NEXT:    // kill: def $x8 killed $w8
+; CHECK-NEXT:    ldrb w0, [x0, x8]
 ; CHECK-NEXT:    ret
   %arrayidx = getelementptr inbounds i8, ptr %a, i64 1039992
   %val = load i8, ptr %arrayidx, align 1
@@ -239,8 +247,10 @@ define i32 @LdOffset_i8_zext32(ptr %a)  {
 define i32 @LdOffset_i8_sext32(ptr %a)  {
 ; CHECK-LABEL: LdOffset_i8_sext32:
 ; CHECK:       // %bb.0:
-; CHECK-NEXT:    add x8, x0, #253, lsl #12 // =1036288
-; CHECK-NEXT:    ldrsb w0, [x8, #3704]
+; CHECK-NEXT:    mov w8, #56952 // =0xde78
+; CHECK-NEXT:    movk w8, #15, lsl #16
+; CHECK-NEXT:    // kill: def $x8 killed $w8
+; CHECK-NEXT:    ldrsb w0, [x0, x8]
 ; CHECK-NEXT:    ret
   %arrayidx = getelementptr inbounds i8, ptr %a, i64 1039992
   %val = load i8, ptr %arrayidx, align 1
@@ -252,8 +262,11 @@ define i32 @LdOffset_i8_sext32(ptr %a)  {
 define i64 @LdOffset_i8_zext64(ptr %a)  {
 ; CHECK-LABEL: LdOffset_i8_zext64:
 ; CHECK:       // %bb.0:
-; CHECK-NEXT:    add x8, x0, #253, lsl #12 // =1036288
-; CHECK-NEXT:    ldrb w0, [x8, #3704]
+; CHECK-NEXT:    mov w8, #56952 // =0xde78
+; CHECK-NEXT:    movk w8, #15, lsl #16
+; CHECK-NEXT:    // kill: def $x8 killed $w8
+; CHECK-NEXT:    ldrb w8, [x0, x8]
+; CHECK-NEXT:    mov w0, w8
 ; CHECK-NEXT:    ret
   %arrayidx = getelementptr inbounds i8, ptr %a, i64 1039992
   %val = load i8, ptr %arrayidx, align 1
@@ -265,8 +278,10 @@ define i64 @LdOffset_i8_zext64(ptr %a)  {
 define i64 @LdOffset_i8_sext64(ptr %a)  {
 ; CHECK-LABEL: LdOffset_i8_sext64:
 ; CHECK:       // %bb.0:
-; CHECK-NEXT:    add x8, x0, #253, lsl #12 // =1036288
-; CHECK-NEXT:    ldrsb x0, [x8, #3704]
+; CHECK-NEXT:    mov w8, #56952 // =0xde78
+; CHECK-NEXT:    movk w8, #15, lsl #16
+; CHECK-NEXT:    // kill: def $x8 killed $w8
+; CHECK-NEXT:    ldrsb x0, [x0, x8]
 ; CHECK-NEXT:    ret
   %arrayidx = getelementptr inbounds i8, ptr %a, i64 1039992
   %val = load i8, ptr %arrayidx, align 1
@@ -278,8 +293,10 @@ define i64 @LdOffset_i8_sext64(ptr %a)  {
 define i16 @LdOffset_i16(ptr %a)  {
 ; CHECK-LABEL: LdOffset_i16:
 ; CHECK:       // %bb.0:
-; CHECK-NEXT:    add x8, x0, #506, lsl #12 // =2072576
-; CHECK-NEXT:    ldrh w0, [x8, #7408]
+; CHECK-NEXT:    mov w8, #48368 // =0xbcf0
+; CHECK-NEXT:    movk w8, #31, lsl #16
+; CHECK-NEXT:    // kill: def $x8 killed $w8
+; CHECK-NEXT:    ldrh w0, [x0, x8]
 ; CHECK-NEXT:    ret
   %arrayidx = getelementptr inbounds i16, ptr %a, i64 1039992
   %val = load i16, ptr %arrayidx, align 2
@@ -290,8 +307,10 @@ define i16 @LdOffset_i16(ptr %a)  {
 define i32 @LdOffset_i16_zext32(ptr %a)  {
 ; CHECK-LABEL: LdOffset_i16_zext32:
 ; CHECK:       // %bb.0:
-; CHECK-NEXT:    add x8, x0, #506, lsl #12 // =2072576
-; CHECK-NEXT:    ldrh w0, [x8, #7408]
+; CHECK-NEXT:    mov w8, #48368 // =0xbcf0
+; CHECK-NEXT:    movk w8, #31, lsl #16
+; CHECK-NEXT:    // kill: def $x8 killed $w8
+; CHECK-NEXT:    ldrh w0, [x0, x8]
 ; CHECK-NEXT:    ret
   %arrayidx = getelementptr inbounds i16, ptr %a, i64 1039992
   %val = load i16, ptr %arrayidx, align 2
@@ -303,8 +322,10 @@ define i32 @LdOffset_i16_zext32(ptr %a)  {
 define i32 @LdOffset_i16_sext32(ptr %a)  {
 ; CHECK-LABEL: LdOffset_i16_sext32:
 ; CHECK:       // %bb.0:
-; CHECK-NEXT:    add x8, x0, #506, lsl #12 // =2072576
-; CHECK-NEXT:    ldrsh w0, [x8, #7408]
+; CHECK-NEXT:    mov w8, #48368 // =0xbcf0
+; CHECK-NEXT:    movk w8, #31, lsl #16
+; CHECK-NEXT:    // kill: def $x8 killed $w8
+; CHECK-NEXT:    ldrsh w0, [x0, x8]
 ; CHECK-NEXT:    ret
   %arrayidx = getelementptr inbounds i16, ptr %a, i64 1039992
   %val = load i16, ptr %arrayidx, align 2
@@ -316,8 +337,11 @@ define i32 @LdOffset_i16_sext32(ptr %a)  {
 define i64 @LdOffset_i16_zext64(ptr %a)  {
 ; CHECK-LABEL: LdOffset_i16_zext64:
 ; CHECK:       // %bb.0:
-; CHECK-NEXT:    add x8, x0, #506, lsl #12 // =2072576
-; CHECK-NEXT:    ldrh w0, [x8, #7408]
+; CHECK-NEXT:    mov w8, #48368 // =0xbcf0
+; CHECK-NEXT:    movk w8, #31, lsl #16
+; CHECK-NEXT:    // kill: def $x8 killed $w8
+; CHECK-NEXT:    ldrh w8, [x0, x8]
+; CHECK-NEXT:    mov w0, w8
 ; CHECK-NEXT:    ret
   %arrayidx = getelementptr inbounds i16, ptr %a, i64 1039992
   %val = load i16, ptr %arrayidx, align 2
@@ -329,8 +353,10 @@ define i64 @LdOffset_i16_zext64(ptr %a)  {
 define i64 @LdOffset_i16_sext64(ptr %a)  {
 ; CHECK-LABEL: LdOffset_i16_sext64:
 ; CHECK:       // %bb.0:
-; CHECK-NEXT:    add x8, x0, #506, lsl #12 // =2072576
-; CHECK-NEXT:    ldrsh x0, [x8, #7408]
+; CHECK-NEXT:    mov w8, #48368 // =0xbcf0
+; CHECK-NEXT:    movk w8, #31, lsl #16
+; CHECK-NEXT:    // kill: def $x8 killed $w8
+; CHECK-NEXT:    ldrsh x0, [x0, x8]
 ; CHECK-NEXT:    ret
   %arrayidx = getelementptr inbounds i16, ptr %a, i64 1039992
   %val = load i16, ptr %arrayidx, align 2
@@ -342,8 +368,10 @@ define i64 @LdOffset_i16_sext64(ptr %a)  {
 define i32 @LdOffset_i32(ptr %a)  {
 ; CHECK-LABEL: LdOffset_i32:
 ; CHECK:       // %bb.0:
-; CHECK-NEXT:    add x8, x0, #1012, lsl #12 // =4145152
-; CHECK-NEXT:    ldr w0, [x8, #14816]
+; CHECK-NEXT:    mov w8, #31200 // =0x79e0
+; CHECK-NEXT:    movk w8, #63, lsl #16
+; CHECK-NEXT:    // kill: def $x8 killed $w8
+; CHECK-NEXT:    ldr w0, [x0, x8]
 ; CHECK-NEXT:    ret
   %arrayidx = getelementptr inbounds i32, ptr %a, i64 1039992
   %val = load i32, ptr %arrayidx, align 4
@@ -354,8 +382,11 @@ define i32 @LdOffset_i32(ptr %a)  {
 define i64 @LdOffset_i32_zext64(ptr %a)  {
 ; CHECK-LABEL: LdOffset_i32_zext64:
 ; CHECK:       // %bb.0:
-; CHECK-NEXT:    add x8, x0, #1012, lsl #12 // =4145152
-; CHECK-NEXT:    ldr w0, [x8, #14816]
+; CHECK-NEXT:    mov w8, #31200 // =0x79e0
+; CHECK-NEXT:    movk w8, #63, lsl #16
+; CHECK-NEXT:    // kill: def $x8 killed $w8
+; CHECK-NEXT:    ldr w8, [x0, x8]
+; CHECK-NEXT:    mov w0, w8
 ; CHECK-NEXT:    ret
   %arrayidx = getelementptr inbounds i32, ptr %a, i64 1039992
   %val = load i32, ptr %arrayidx, align 2
@@ -367,8 +398,10 @@ define i64 @LdOffset_i32_zext64(ptr %a)  {
 define i64 @LdOffset_i32_sext64(ptr %a)  {
 ; CHECK-LABEL: LdOffset_i32_sext64:
 ; CHECK:       // %bb.0:
-; CHECK-NEXT:    add x8, x0, #1012, lsl #12 // =4145152
-; CHECK-NEXT:    ldrsw x0, [x8, #14816]
+; CHECK-NEXT:    mov w8, #31200 // =0x79e0
+; CHECK-NEXT:    movk w8, #63, lsl #16
+; CHECK-NEXT:    // kill: def $x8 killed $w8
+; CHECK-NEXT:    ldrsw x0, [x0, x8]
 ; CHECK-NEXT:    ret
   %arrayidx = getelementptr inbounds i32, ptr %a, i64 1039992
   %val = load i32, ptr %arrayidx, align 2
@@ -380,8 +413,10 @@ define i64 @LdOffset_i32_sext64(ptr %a)  {
 define i64 @LdOffset_i64(ptr %a)  {
 ; CHECK-LABEL: LdOffset_i64:
 ; CHECK:       // %bb.0:
-; CHECK-NEXT:    add x8, x0, #2024, lsl #12 // =8290304
-; CHECK-NEXT:    ldr x0, [x8, #29632]
+; CHECK-NEXT:    mov w8, #62400 // =0xf3c0
+; CHECK-NEXT:    movk w8, #126, lsl #16
+; CHECK-NEXT:    // kill: def $x8 killed $w8
+; CHECK-NEXT:    ldr x0, [x0, x8]
 ; CHECK-NEXT:    ret
   %arrayidx = getelementptr inbounds i64, ptr %a, i64 1039992
   %val = load i64, ptr %arrayidx, align 4
@@ -392,8 +427,10 @@ define i64 @LdOffset_i64(ptr %a)  {
 define <2 x i32> @LdOffset_v2i32(ptr %a)  {
 ; CHECK-LABEL: LdOffset_v2i32:
 ; CHECK:       // %bb.0:
-; CHECK-NEXT:    add x8, x0, #2024, lsl #12 // =8290304
-; CHECK-NEXT:    ldr d0, [x8, #29632]
+; CHECK-NEXT:    mov w8, #62400 // =0xf3c0
+; CHECK-NEXT:    movk w8, #126, lsl #16
+; CHECK-NEXT:    // kill: def $x8 killed $w8
+; CHECK-NEXT:    ldr d0, [x0, x8]
 ; CHECK-NEXT:    ret
   %arrayidx = getelementptr inbounds <2 x i32>, ptr %a, i64 1039992
   %val = load <2 x i32>, ptr %arrayidx, align 4
@@ -404,8 +441,10 @@ define <2 x i32> @LdOffset_v2i32(ptr %a)  {
 define <2 x i64> @LdOffset_v2i64(ptr %a)  {
 ; CHECK-LABEL: LdOffset_v2i64:
 ; CHECK:       // %bb.0:
-; CHECK-NEXT:    add x8, x0, #4048, lsl #12 // =16580608
-; CHECK-NEXT:    ldr q0, [x8, #59264]
+; CHECK-NEXT:    mov w8, #59264 // =0xe780
+; CHECK-NEXT:    movk w8, #253, lsl #16
+; CHECK-NEXT:    // kill: def $x8 killed $w8
+; CHECK-NEXT:    ldr q0, [x0, x8]
 ; CHECK-NEXT:    ret
   %arrayidx = getelementptr inbounds <2 x i64>, ptr %a, i64 1039992
   %val = load <2 x i64>, ptr %arrayidx, align 4
@@ -416,8 +455,10 @@ define <2 x i64> @LdOffset_v2i64(ptr %a)  {
 define double @LdOffset_i8_f64(ptr %a)  {
 ; CHECK-LABEL: LdOffset_i8_f64:
 ; CHECK:       // %bb.0:
-; CHECK-NEXT:    add x8, x0, #253, lsl #12 // =1036288
-; CHECK-NEXT:    ldrsb w8, [x8, #3704]
+; CHECK-NEXT:    mov w8, #56952 // =0xde78
+; CHECK-NEXT:    movk w8, #15, lsl #16
+; CHECK-NEXT:    // kill: def $x8 killed $w8
+; CHECK-NEXT:    ldrsb w8, [x0, x8]
 ; CHECK-NEXT:    scvtf d0, w8
 ; CHECK-NEXT:    ret
   %arrayidx = getelementptr inbounds i8, ptr %a, i64 1039992
@@ -430,8 +471,10 @@ define double @LdOffset_i8_f64(ptr %a)  {
 define double @LdOffset_i16_f64(ptr %a)  {
 ; CHECK-LABEL: LdOffset_i16_f64:
 ; CHECK:       // %bb.0:
-; CHECK-NEXT:    add x8, x0, #506, lsl #12 // =2072576
-; CHECK-NEXT:    ldrsh w8, [x8, #7408]
+; CHECK-NEXT:    mov w8, #48368 // =0xbcf0
+; CHECK-NEXT:    movk w8, #31, lsl #16
+; CHECK-NEXT:    // kill: def $x8 killed $w8
+; CHECK-NEXT:    ldrsh w8, [x0, x8]
 ; CHECK-NEXT:    scvtf d0, w8
 ; CHECK-NEXT:    ret
   %arrayidx = getelementptr inbounds i16, ptr %a, i64 1039992
@@ -444,8 +487,10 @@ define double @LdOffset_i16_f64(ptr %a)  {
 define double @LdOffset_i32_f64(ptr %a)  {
 ; CHECK-LABEL: LdOffset_i32_f64:
 ; CHECK:       // %bb.0:
-; CHECK-NEXT:    add x8, x0, #1012, lsl #12 // =4145152
-; CHECK-NEXT:    ldr s0, [x8, #14816]
+; CHECK-NEXT:    mov w8, #31200 // =0x79e0
+; CHECK-NEXT:    movk w8, #63, lsl #16
+; CHECK-NEXT:    // kill: def $x8 killed $w8
+; CHECK-NEXT:    ldr s0, [x0, x8]
 ; CHECK-NEXT:    ucvtf d0, d0
 ; CHECK-NEXT:    ret
   %arrayidx = getelementptr inbounds i32, ptr %a, i64 1039992
@@ -458,8 +503,10 @@ define double @LdOffset_i32_f64(ptr %a)  {
 define double @LdOffset_i64_f64(ptr %a)  {
 ; CHECK-LABEL: LdOffset_i64_f64:
 ; CHECK:       // %bb.0:
-; CHECK-NEXT:    add x8, x0, #2024, lsl #12 // =8290304
-; CHECK-NEXT:    ldr d0, [x8, #29632]
+; CHECK-NEXT:    mov w8, #62400 // =0xf3c0
+; CHECK-NEXT:    movk w8, #126, lsl #16
+; CHECK-NEXT:    // kill: def $x8 killed $w8
+; CHECK-NEXT:    ldr d0, [x0, x8]
 ; CHECK-NEXT:    scvtf d0, d0
 ; CHECK-NEXT:    ret
   %arrayidx = getelementptr inbounds i64, ptr %a, i64 1039992
@@ -507,6 +554,7 @@ define i32 @LdOffset_i16_odd_offset(ptr nocapture noundef readonly %a)  {
 ; CHECK:       // %bb.0:
 ; CHECK-NEXT:    mov w8, #56953 // =0xde79
 ; CHECK-NEXT:    movk w8, #15, lsl #16
+; CHECK-NEXT:    // kill: def $x8 killed $w8
 ; CHECK-NEXT:    ldrsh w0, [x0, x8]
 ; CHECK-NEXT:    ret
   %arrayidx = getelementptr inbounds i8, ptr %a, i64 1039993
@@ -520,6 +568,7 @@ define i8 @LdOffset_i8_movnwi(ptr %a)  {
 ; CHECK-LABEL: LdOffset_i8_movnwi:
 ; CHECK:       // %bb.0:
 ; CHECK-NEXT:    mov w8, #16777215 // =0xffffff
+; CHECK-NEXT:    // kill: def $x8 killed $w8
 ; CHECK-NEXT:    ldrb w0, [x0, x8]
 ; CHECK-NEXT:    ret
   %arrayidx = getelementptr inbounds i8, ptr %a, i64 16777215
@@ -533,6 +582,7 @@ define i8 @LdOffset_i8_too_large(ptr %a)  {
 ; CHECK:       // %bb.0:
 ; CHECK-NEXT:    mov w8, #1 // =0x1
 ; CHECK-NEXT:    movk w8, #256, lsl #16
+; CHECK-NEXT:    // kill: def $x8 killed $w8
 ; CHECK-NEXT:    ldrb w0, [x0, x8]
 ; CHECK-NEXT:    ret
   %arrayidx = getelementptr inbounds i8, ptr %a, i64 16777217
diff --git a/llvm/test/CodeGen/AArch64/preserve_nonecc_varargs_darwin.ll b/llvm/test/CodeGen/AArch64/preserve_nonecc_varargs_darwin.ll
index 2a77d4dd33fe5..f03804d0064fd 100644
--- a/llvm/test/CodeGen/AArch64/preserve_nonecc_varargs_darwin.ll
+++ b/llvm/test/CodeGen/AArch64/preserve_nonecc_varargs_darwin.ll
@@ -28,15 +28,21 @@ define i32 @caller() nounwind ssp {
 ; CHECK-NEXT:    mov w8, #10 ; =0xa
 ; CHECK-NEXT:    mov w9, #9 ; =0x9
 ; CHECK-NEXT:    mov w10, #8 ; =0x8
-; CHECK-NEXT:    stp x9, x8, [sp, #24]
-; CHECK-NEXT:    mov w8, #7 ; =0x7
-; CHECK-NEXT:    mov w9, #6 ; =0x6
+; CHECK-NEXT:    ; kill: def $x8 killed $w8
+; CHECK-NEXT:    mov w11, #6 ; =0x6
+; CHECK-NEXT:    ; kill: def $x9 killed $w9
+; CHECK-NEXT:    str x8, [sp, #32]
+; CHECK-NEXT:    ; kill: def $x10 killed $w10
 ; CHECK-NEXT:    mov w0, #1 ; =0x1
+; CHECK-NEXT:    mov w8, #7 ; =0x7
+; CHECK-NEXT:    stp x10, x9, [sp, #16]
+; CHECK-NEXT:    mov w9, w11
 ; CHECK-NEXT:    mov w1, #2 ; =0x2
 ; CHECK-NEXT:    mov w2, #3 ; =0x3
 ; CHECK-NEXT:    mov w3, #4 ; =0x4
 ; CHECK-NEXT:    mov w4, #5 ; =0x5
 ; CHECK-NEXT:    stp d15, d14, [sp, #48] ; 16-byte Folded Spill
+; CHECK-NEXT:    ; kill: def $x8 killed $w8
 ; CHECK-NEXT:    stp d13, d12, [sp, #64] ; 16-byte Folded Spill
 ; CHECK-NEXT:    stp d11, d10, [sp, #80] ; 16-byte Folded Spill
 ; CHECK-NEXT:    stp d9, d8, [sp, #96] ; 16-byte Folded Spill
@@ -46,8 +52,7 @@ define i32 @caller() nounwind ssp {
 ; CHECK-NEXT:    stp x22, x21, [sp, #160] ; 16-byte Folded Spill
 ; CHECK-NEXT:    stp x20, x19, [sp, #176] ; 16-byte Folded Spill
 ; CHECK-NEXT:    stp x29, x30, [sp, #192] ; 16-byte Folded Spill
-; CHECK-NEXT:    stp x8, x10, [sp, #8]
-; CHECK-NEXT:    str x9, [sp]
+; CHECK-NEXT:    stp x9, x8, [sp]
 ; CHECK-NEXT:    bl _callee
 ; CHECK-NEXT:    ldp x29, x30, [sp, #192] ; 16-byte Folded Reload
 ; CHECK-NEXT:    ldp x20, x19, [sp, #176] ; 16-byte Folded Reload
diff --git a/llvm/test/CodeGen/AArch64/register-coalesce-update-subranges-remat.mir b/llvm/test/CodeGen/AArch64/register-coalesce-update-subranges-remat.mir
index 08fc47d9480ce..68032643bcf4d 100644
--- a/llvm/test/CodeGen/AArch64/register-coalesce-update-subranges-remat.mir
+++ b/llvm/test/CodeGen/AArch64/register-coalesce-update-subranges-remat.mir
@@ -1,5 +1,6 @@
 # RUN: llc -mtriple=aarch64 -o /dev/null -run-pass=register-coalescer -aarch64-enable-subreg-liveness-tracking -debug-only=regalloc %s 2>&1 | FileCheck %s --check-prefix=CHECK-DBG
 # RUN: llc -mtriple=aarch64 -verify-machineinstrs -o - -run-pass=register-coalescer -aarch64-enable-subreg-liveness-tracking %s | FileCheck %s --check-prefix=CHECK
+# XFAIL: *
 # REQUIRES: asserts
 
 # CHECK-DBG: ********** REGISTER COALESCER **********
diff --git a/llvm/test/CodeGen/AArch64/subreg_to_reg_coalescing_issue.mir b/llvm/test/CodeGen/AArch64/subreg_to_reg_coalescing_issue.mir
new file mode 100644
index 0000000000000..0d472fba05039
--- /dev/null
+++ b/llvm/test/CodeGen/AArch64/subreg_to_reg_coalescing_issue.mir
@@ -0,0 +1,34 @@
+# NOTE: Assertions have been autogenerated by utils/update_mir_test_checks.py UTC_ARGS: --version 6
+# RUN: llc -mtriple=aarch64 -O3 -start-before=register-coalescer -stop-before=aarch64-expand-pseudo -enable-subreg-liveness=true  -o - %s | FileCheck %s --check-prefix=SRLT
+# RUN: llc -mtriple=aarch64 -O3 -start-before=register-coalescer -stop-before=aarch64-expand-pseudo -enable-subreg-liveness=false -o - %s | FileCheck %s --check-prefix=NOSRLT
+
+# Test that the ORRWrr is not copy-propagated away,
+# because the ORRWrr exists to zero the top bits of x1.
+---
+name: dont_remove_orr_w
+tracksRegLiveness: true
+body: |
+  bb.0:
+    liveins: $x1
+    ; SRLT-LABEL: name: dont_remove_orr_w
+    ; SRLT: liveins: $x1
+    ; SRLT-NEXT: {{  $}}
+    ; SRLT-NEXT: $x0 = ORRXrr $xzr, $x1
+    ; SRLT-NEXT: renamable $w8 = ORRWrr $wzr, renamable $w0
+    ; SRLT-NEXT: $w1 = ORRWrr $wzr, killed $w8, implicit-def $x1
+    ; SRLT-NEXT: RET_ReallyLR implicit $x1, implicit $x0
+    ;
+    ; NOSRLT-LABEL: name: dont_remove_orr_w
+    ; NOSRLT: liveins: $x1
+    ; NOSRLT-NEXT: {{  $}}
+    ; NOSRLT-NEXT: $x0 = ORRXrr $xzr, $x1
+    ; NOSRLT-NEXT: renamable $w1 = ORRWrr $wzr, renamable $w0, implicit-def $x1
+    ; NOSRLT-NEXT: RET_ReallyLR implicit $x1, implicit $x0
+    %0:gpr64 = COPY killed $x1
+    %1:gpr32 = COPY %0.sub_32:gpr64
+    %2:gpr32 = ORRWrr $wzr, killed %1:gpr32
+    %3:gpr64all = SUBREG_TO_REG 0, killed %2:gpr32, %subreg.sub_32
+    $x0 = COPY killed %0:gpr64
+    $x1 = COPY killed %3:gpr64all
+    RET_ReallyLR implicit $x1, implicit $x0
+...

``````````

</details>


https://github.com/llvm/llvm-project/pull/174185


More information about the llvm-commits mailing list