[llvm] [AMDGPU] Prefer lower total register usage in regions with spilling (PR #71882)
Valery Pykhtin via llvm-commits
llvm-commits at lists.llvm.org
Mon Dec 18 07:43:55 PST 2023
================
@@ -104,18 +105,82 @@ bool GCNRegPressure::less(const GCNSubtarget &ST,
const auto Occ = std::min(SGPROcc, VGPROcc);
const auto OtherOcc = std::min(OtherSGPROcc, OtherVGPROcc);
+
+ // Give first precedence to the better occupancy.
if (Occ != OtherOcc)
return Occ > OtherOcc;
+ unsigned MaxVGPRs = ST.getMaxNumVGPRs(MF);
+ unsigned MaxSGPRs = ST.getMaxNumSGPRs(MF);
+
+ // SGPR excess pressure conditions
+ unsigned ExcessSGPR = std::max(static_cast<int>(getSGPRNum() - MaxSGPRs), 0);
+ unsigned OtherExcessSGPR =
+ std::max(static_cast<int>(O.getSGPRNum() - MaxSGPRs), 0);
+
+ auto WaveSize = ST.getWavefrontSize();
+ // The number of virtual VGPRs required to handle excess SGPR
+ unsigned SGPRSpills = (ExcessSGPR + (WaveSize - 1)) / WaveSize;
+ unsigned OtherSGPRSpills = (OtherExcessSGPR + (WaveSize - 1)) / WaveSize;
+
+ unsigned MaxArchVGPRs = ST.getAddressableNumArchVGPRs();
+
+ // Unified excess pressure conditions, accounting for VGPRs used for SGPR
+ // spills
+ unsigned ExcessVGPR = std::max(
+ static_cast<int>(getVGPRNum(ST.hasGFX90AInsts()) + SGPRSpills - MaxVGPRs),
+ 0);
+ unsigned OtherExcessVGPR =
+ std::max(static_cast<int>(O.getVGPRNum(ST.hasGFX90AInsts()) +
+ OtherSGPRSpills - MaxVGPRs),
+ 0);
+ // Arch VGPR excess pressure conditions, accounting for VGPRs used for SGPR
+ // spills
+ unsigned ExcessArchVGPR = std::max(
+ static_cast<int>(getVGPRNum(false) + SGPRSpills - MaxArchVGPRs), 0);
+ unsigned OtherExcessArchVGPR = std::max(
+ static_cast<int>(O.getVGPRNum(false) + OtherSGPRSpills - MaxArchVGPRs),
+ 0);
+ // AGPR excess pressure conditions
+ unsigned ExcessAGPR = std::max(
+ static_cast<int>(ST.hasGFX90AInsts() ? (getAGPRNum() - MaxArchVGPRs)
+ : (getAGPRNum() - MaxVGPRs)),
+ 0);
+ unsigned OtherExcessAGPR = std::max(
+ static_cast<int>(ST.hasGFX90AInsts() ? (O.getAGPRNum() - MaxArchVGPRs)
+ : (O.getAGPRNum() - MaxVGPRs)),
+ 0);
+
+ bool ExcessRP = ExcessSGPR || ExcessVGPR || ExcessArchVGPR || ExcessAGPR;
+ bool OtherExcessRP = OtherExcessSGPR || OtherExcessVGPR ||
+ OtherExcessArchVGPR || OtherExcessAGPR;
+
+ // Give second precedence to the reduced number of spills to hold the register
+ // pressure.
+ if (ExcessRP || OtherExcessRP) {
+ // The difference in excess VGPR pressure, after including VGPRs used for
+ // SGPR spills
+ int VGPRDiff = ((OtherExcessVGPR + OtherExcessArchVGPR + OtherExcessAGPR) -
+ (ExcessVGPR + ExcessArchVGPR + ExcessAGPR));
+
+ int SGPRDiff = OtherExcessSGPR - ExcessSGPR;
+
+ // If excess VGPR is the same, prefer the lower excess SGPR
+ if (VGPRDiff != 0)
+ return VGPRDiff > 0;
+ else if (SGPRDiff != 0)
----------------
vpykhtin wrote:
Just a nit: 'else' isn't needed due to the return above. SGPRDiff can be calculated after VGPRDiff != 0 is tested.
https://github.com/llvm/llvm-project/pull/71882
More information about the llvm-commits
mailing list