[PATCH] D100748: [Greedy RA] Do not split interval on tied-def

Serguei Katkov via Phabricator via llvm-commits llvm-commits at lists.llvm.org
Mon Apr 19 03:11:03 PDT 2021


skatkov created this revision.
skatkov added reviewers: reames, rnk, void.
Herald added subscribers: pengfei, hiraditya.
skatkov requested review of this revision.
Herald added a project: LLVM.

If end of interval for overlap utility is a use which has tied-def we
should not split interval on this instruction due to in this case use
and def may have different registers and it breaks tied-def property.


https://reviews.llvm.org/D100748

Files:
  llvm/lib/CodeGen/SplitKit.cpp
  llvm/lib/CodeGen/SplitKit.h
  llvm/test/CodeGen/X86/statepoint-invoke-ra1.ll


Index: llvm/test/CodeGen/X86/statepoint-invoke-ra1.ll
===================================================================
--- llvm/test/CodeGen/X86/statepoint-invoke-ra1.ll
+++ llvm/test/CodeGen/X86/statepoint-invoke-ra1.ll
@@ -1,10 +1,8 @@
 ; REQUIRES: asserts
-; RUN: not  --crash llc -o /dev/null %s -max-registers-for-gc-values=15 -use-registers-for-gc-values-in-landing-pad=true -verify-regalloc 2>&1 | FileCheck %s
+; RUN: llc -o - %s -max-registers-for-gc-values=15 -use-registers-for-gc-values-in-landing-pad=true -verify-regalloc 2>&1 | FileCheck %s
 
-; The test checks the verification catch the case when RA splits live interval in the
-; way the def is located after invoke statepoint while use is in landing pad.
-
-; CHECK: *** Bad machine code: Two-address instruction operands must be identical ***
+; CHECK-NOT: *** Bad machine code
+; CHECK: wombat
 
 target datalayout = "e-m:e-p270:32:32-p271:32:32-p272:64:64-i64:64-f80:128-n8:16:32:64-S128-ni:1-p2:32:8:8:32-ni:2"
 target triple = "x86_64-unknown-linux-gnu"
Index: llvm/lib/CodeGen/SplitKit.h
===================================================================
--- llvm/lib/CodeGen/SplitKit.h
+++ llvm/lib/CodeGen/SplitKit.h
@@ -511,7 +511,8 @@
   SlotIndex leaveIntvAtTop(MachineBasicBlock &MBB);
 
   /// overlapIntv - Indicate that all instructions in range should use the open
-  /// interval, but also let the complement interval be live.
+  /// interval if End does not have tied-def usage of the register and in this
+  /// case compliment interval is used. Let the complement interval be live.
   ///
   /// This doubles the register pressure, but is sometimes required to deal with
   /// register uses after the last valid split point.
Index: llvm/lib/CodeGen/SplitKit.cpp
===================================================================
--- llvm/lib/CodeGen/SplitKit.cpp
+++ llvm/lib/CodeGen/SplitKit.cpp
@@ -791,6 +791,12 @@
   return VNI->def;
 }
 
+static bool hasTiedUseOf(MachineInstr &MI, unsigned Reg) {
+  return any_of(MI.defs(), [Reg](const MachineOperand &MO) {
+    return MO.isReg() && MO.isTied() && MO.getReg() == Reg;
+  });
+}
+
 void SplitEditor::overlapIntv(SlotIndex Start, SlotIndex End) {
   assert(OpenIdx && "openIntv not called before overlapIntv");
   const VNInfo *ParentVNI = Edit->getParent().getVNInfoAt(Start);
@@ -802,6 +808,16 @@
   // The complement interval will be extended as needed by LICalc.extend().
   if (ParentVNI)
     forceRecompute(0, *ParentVNI);
+
+  // If the last use is tied to a def, we can't mark it as live for the
+  // interval which includes only the use.  That would cause the tied pair
+  // to end up in two different intervals.
+  if (auto *MI = LIS.getInstructionFromIndex(End))
+    if (hasTiedUseOf(*MI, Edit->getReg())) {
+      LLVM_DEBUG(dbgs() << "skip overlap due to tied def at end\n");
+      return;
+    }
+
   LLVM_DEBUG(dbgs() << "    overlapIntv [" << Start << ';' << End << "):");
   RegAssign.insert(Start, End, OpenIdx);
   LLVM_DEBUG(dump());


-------------- next part --------------
A non-text attachment was scrubbed...
Name: D100748.338458.patch
Type: text/x-patch
Size: 3010 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20210419/9878b002/attachment-0001.bin>


More information about the llvm-commits mailing list