[llvm-branch-commits] [llvm] MachineLICM: Fix preheader insertion point with SUCC_ARGS (PR #218896)

via llvm-branch-commits llvm-branch-commits at lists.llvm.org
Wed Aug 26 04:45:55 PDT 2026


llvmorg-github-actions[bot] wrote:


<!--LLVM PR SUMMARY COMMENT-->

@llvm/pr-subscribers-backend-x86

Author: Matt Arsenault (arsenm)

<details>
<summary>Changes</summary>

Hoist loop-invariant instructions to getBlockEndInsertPt() instead of
getFirstTerminator(), so they land before the SUCC_ARGS cluster rather
than inside it.

Co-Authored-By: Claude <noreply@<!-- -->anthropic.com> (Claude Opus 4.8)

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


2 Files Affected:

- (modified) llvm/lib/CodeGen/MachineLICM.cpp (+2-2) 
- (added) llvm/test/CodeGen/X86/machinelicm-hoist-before-succ-args.mir (+48) 


``````````diff
diff --git a/llvm/lib/CodeGen/MachineLICM.cpp b/llvm/lib/CodeGen/MachineLICM.cpp
index 6435bbb9382c1..23185bd7d9c85 100644
--- a/llvm/lib/CodeGen/MachineLICM.cpp
+++ b/llvm/lib/CodeGen/MachineLICM.cpp
@@ -745,7 +745,7 @@ void MachineLICMImpl::HoistPostRA(MachineInstr *MI, Register Def,
 
   // Splice the instruction to the preheader.
   MachineBasicBlock *MBB = MI->getParent();
-  Preheader->splice(Preheader->getFirstTerminator(), MBB, MI);
+  Preheader->splice(Preheader->getBlockEndInsertPt(), MBB, MI);
 
   // Since we are moving the instruction out of its basic block, we do not
   // retain its debug location. Doing so would degrade the debugging
@@ -1672,7 +1672,7 @@ unsigned MachineLICMImpl::Hoist(MachineInstr *MI, MachineBasicBlock *Preheader,
 
   if (!HasCSEDone) {
     // Otherwise, splice the instruction to the preheader.
-    Preheader->splice(Preheader->getFirstTerminator(),MI->getParent(),MI);
+    Preheader->splice(Preheader->getBlockEndInsertPt(), MI->getParent(), MI);
 
     // Since we are moving the instruction out of its basic block, we do not
     // retain its debug location. Doing so would degrade the debugging
diff --git a/llvm/test/CodeGen/X86/machinelicm-hoist-before-succ-args.mir b/llvm/test/CodeGen/X86/machinelicm-hoist-before-succ-args.mir
new file mode 100644
index 0000000000000..1161b4a955398
--- /dev/null
+++ b/llvm/test/CodeGen/X86/machinelicm-hoist-before-succ-args.mir
@@ -0,0 +1,48 @@
+# NOTE: Assertions have been autogenerated by utils/update_mir_test_checks.py UTC_ARGS: --version 6
+# RUN: llc -mtriple=x86_64-- -run-pass=early-machinelicm -o - %s | FileCheck %s
+
+# A loop-invariant instruction hoisted into a preheader that ends with a
+# SUCC_ARGS must be spliced before the SUCC_ARGS cluster, not into it, so the
+# cluster stays adjacent to the terminators.
+---
+name: hoist_before_succ_args
+tracksRegLiveness: true
+body: |
+  ; CHECK-LABEL: name: hoist_before_succ_args
+  ; CHECK: bb.0:
+  ; CHECK-NEXT:   successors: %bb.1(0x80000000)
+  ; CHECK-NEXT:   liveins: $edi
+  ; CHECK-NEXT: {{  $}}
+  ; CHECK-NEXT:   [[COPY:%[0-9]+]]:gr32 = COPY $edi
+  ; CHECK-NEXT:   [[MOV32ri:%[0-9]+]]:gr32 = MOV32ri 42
+  ; CHECK-NEXT:   SUCC_ARGS %bb.1, [[COPY]]
+  ; CHECK-NEXT:   JMP_1 %bb.1
+  ; CHECK-NEXT: {{  $}}
+  ; CHECK-NEXT: bb.1:
+  ; CHECK-NEXT:   successors: %bb.1(0x40000000), %bb.2(0x40000000)
+  ; CHECK-NEXT: {{  $}}
+  ; CHECK-NEXT:   TEST32rr [[MOV32ri]], [[MOV32ri]], implicit-def $eflags
+  ; CHECK-NEXT:   JCC_1 %bb.1, 5, implicit $eflags
+  ; CHECK-NEXT:   JMP_1 %bb.2
+  ; CHECK-NEXT: {{  $}}
+  ; CHECK-NEXT: bb.2:
+  ; CHECK-NEXT:   RET64
+  bb.0:
+    successors: %bb.1
+    liveins: $edi
+    %0:gr32 = COPY $edi
+    ; The hoisted MOV32ri must land before the SUCC_ARGS, which stays adjacent
+    ; to the terminator.
+    SUCC_ARGS %bb.1, %0
+    JMP_1 %bb.1
+
+  bb.1:
+    successors: %bb.1, %bb.2
+    %1:gr32 = MOV32ri 42
+    TEST32rr %1, %1, implicit-def $eflags
+    JCC_1 %bb.1, 5, implicit $eflags
+    JMP_1 %bb.2
+
+  bb.2:
+    RET64
+...

``````````

</details>


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


More information about the llvm-branch-commits mailing list