[llvm] [AMDGPU] Improved register pressure estimates for rescheduling (PR #213116)

Lucas Ramirez via llvm-commits llvm-commits at lists.llvm.org
Fri Jul 31 04:57:51 PDT 2026


================
@@ -1213,3 +1214,83 @@ LLVM_DUMP_METHOD void llvm::dumpMaxRegPressure(MachineFunction &MF,
   }
 }
 #endif
+
+unsigned llvm::estimateGreedyVGPRPressure(
+    MachineBasicBlock::const_iterator RegionBegin,
+    MachineBasicBlock::const_iterator RegionEnd,
+    const GCNRPTracker::LiveRegSet &LiveIns, LiveIntervals &LIS,
+    const MachineRegisterInfo &MRI, const SIRegisterInfo &TRI) {
+
+  SmallVector<LiveInterval *> RegionIntervals;
+  SmallPtrSet<LiveInterval *, 32> Seen;
+
+  auto IsVGPR = [&MRI, &TRI](Register VReg) {
+    const TargetRegisterClass *RC = MRI.getRegClass(VReg);
+    return TRI.isVGPRClass(RC) || TRI.isVectorSuperClass(RC);
+  };
+
+  // Collect live-ins
+  for (const auto &[RegNum, LaneMask] : LiveIns) {
+    Register VReg(RegNum);
+    if (!VReg.isVirtual() || !LIS.hasInterval(VReg) || !IsVGPR(VReg))
+      continue;
+    LiveInterval &LI = LIS.getInterval(VReg);
+    if (Seen.insert(&LI).second)
+      RegionIntervals.push_back(&LI);
+  }
+
+  // Collect defs in region
+  for (auto I = RegionBegin; I != RegionEnd; ++I) {
+    for (const MachineOperand &MO : I->operands()) {
+      if (!MO.isReg() || !MO.isDef())
+        continue;
+      Register VReg = MO.getReg();
+      if (!VReg.isVirtual() || !LIS.hasInterval(VReg) || !IsVGPR(VReg))
+        continue;
+      LiveInterval &LI = LIS.getInterval(VReg);
+      if (Seen.insert(&LI).second)
+        RegionIntervals.push_back(&LI);
+    }
+  }
+
+  llvm::sort(RegionIntervals, [](auto *LHS, auto *RHS) {
+    return LHS->beginIndex() < RHS->beginIndex();
+  });
+
+  LiveIntervalUnion::Allocator Alloc;
+  std::vector<LiveIntervalUnion> Slots;
+  unsigned MaxSlotUsed = 0;
+
+  // Simulate greedy register allocation, assuming unlimited number
+  // of physical registers (slots).
+  for (LiveInterval *LI : RegionIntervals) {
+    const TargetRegisterClass *RC = MRI.getRegClass(LI->reg());
+    unsigned Width = TRI.getRegClassWeight(RC).RegWeight;
+    unsigned Alignment = std::max(1u, TRI.getRegClassAlignmentNumBits(RC) / 32);
+
+    unsigned Start = 0;
+    while (true) {
+      if (Slots.size() < Start + Width)
----------------
lucas-rami wrote:

nit: put `Start+Width` in a variable to avoid repetition 

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


More information about the llvm-commits mailing list