28
28
// / calculation and creates more possibilities for the code unaware of lanemasks
29
29
// ===----------------------------------------------------------------------===//
30
30
31
+ #include " GCNRewritePartialRegUses.h"
31
32
#include " AMDGPU.h"
32
33
#include " MCTargetDesc/AMDGPUMCTargetDesc.h"
33
34
#include " SIRegisterInfo.h"
@@ -44,25 +45,7 @@ using namespace llvm;
44
45
45
46
namespace {
46
47
47
- class GCNRewritePartialRegUses : public MachineFunctionPass {
48
- public:
49
- static char ID;
50
- GCNRewritePartialRegUses () : MachineFunctionPass(ID) {}
51
-
52
- StringRef getPassName () const override {
53
- return " Rewrite Partial Register Uses" ;
54
- }
55
-
56
- void getAnalysisUsage (AnalysisUsage &AU) const override {
57
- AU.setPreservesCFG ();
58
- AU.addPreserved <LiveIntervalsWrapperPass>();
59
- AU.addPreserved <SlotIndexesWrapperPass>();
60
- MachineFunctionPass::getAnalysisUsage (AU);
61
- }
62
-
63
- bool runOnMachineFunction (MachineFunction &MF) override ;
64
-
65
- private:
48
+ class GCNRewritePartialRegUsesImpl {
66
49
MachineRegisterInfo *MRI;
67
50
const SIRegisterInfo *TRI;
68
51
const TargetInstrInfo *TII;
@@ -155,13 +138,36 @@ class GCNRewritePartialRegUses : public MachineFunctionPass {
155
138
// / Cache for getAllocatableAndAlignedRegClassMask method:
156
139
// / AlignNumBits -> Class bitmask.
157
140
mutable SmallDenseMap<unsigned , BitVector> AllocatableAndAlignedRegClassMasks;
141
+
142
+ public:
143
+ GCNRewritePartialRegUsesImpl (LiveIntervals *LS) : LIS(LS) {}
144
+ bool run (MachineFunction &MF);
145
+ };
146
+
147
+ class GCNRewritePartialRegUsesLegacy : public MachineFunctionPass {
148
+ public:
149
+ static char ID;
150
+ GCNRewritePartialRegUsesLegacy () : MachineFunctionPass(ID) {}
151
+
152
+ StringRef getPassName () const override {
153
+ return " Rewrite Partial Register Uses" ;
154
+ }
155
+
156
+ void getAnalysisUsage (AnalysisUsage &AU) const override {
157
+ AU.setPreservesCFG ();
158
+ AU.addPreserved <LiveIntervalsWrapperPass>();
159
+ AU.addPreserved <SlotIndexesWrapperPass>();
160
+ MachineFunctionPass::getAnalysisUsage (AU);
161
+ }
162
+
163
+ bool runOnMachineFunction (MachineFunction &MF) override ;
158
164
};
159
165
160
166
} // end anonymous namespace
161
167
162
168
// TODO: move this to the tablegen and use binary search by Offset.
163
- unsigned GCNRewritePartialRegUses ::getSubReg (unsigned Offset,
164
- unsigned Size) const {
169
+ unsigned GCNRewritePartialRegUsesImpl ::getSubReg (unsigned Offset,
170
+ unsigned Size) const {
165
171
const auto [I, Inserted] = SubRegs.try_emplace ({Offset, Size}, 0 );
166
172
if (Inserted) {
167
173
for (unsigned Idx = 1 , E = TRI->getNumSubRegIndices (); Idx < E; ++Idx) {
@@ -175,15 +181,14 @@ unsigned GCNRewritePartialRegUses::getSubReg(unsigned Offset,
175
181
return I->second ;
176
182
}
177
183
178
- unsigned GCNRewritePartialRegUses ::shiftSubReg (unsigned SubReg,
179
- unsigned RShift) const {
184
+ unsigned GCNRewritePartialRegUsesImpl ::shiftSubReg (unsigned SubReg,
185
+ unsigned RShift) const {
180
186
unsigned Offset = TRI->getSubRegIdxOffset (SubReg) - RShift;
181
187
return getSubReg (Offset, TRI->getSubRegIdxSize (SubReg));
182
188
}
183
189
184
- const uint32_t *
185
- GCNRewritePartialRegUses::getSuperRegClassMask (const TargetRegisterClass *RC,
186
- unsigned SubRegIdx) const {
190
+ const uint32_t *GCNRewritePartialRegUsesImpl::getSuperRegClassMask (
191
+ const TargetRegisterClass *RC, unsigned SubRegIdx) const {
187
192
const auto [I, Inserted] =
188
193
SuperRegMasks.try_emplace ({RC, SubRegIdx}, nullptr );
189
194
if (Inserted) {
@@ -197,7 +202,8 @@ GCNRewritePartialRegUses::getSuperRegClassMask(const TargetRegisterClass *RC,
197
202
return I->second ;
198
203
}
199
204
200
- const BitVector &GCNRewritePartialRegUses::getAllocatableAndAlignedRegClassMask (
205
+ const BitVector &
206
+ GCNRewritePartialRegUsesImpl::getAllocatableAndAlignedRegClassMask (
201
207
unsigned AlignNumBits) const {
202
208
const auto [I, Inserted] =
203
209
AllocatableAndAlignedRegClassMasks.try_emplace (AlignNumBits);
@@ -214,7 +220,7 @@ const BitVector &GCNRewritePartialRegUses::getAllocatableAndAlignedRegClassMask(
214
220
}
215
221
216
222
const TargetRegisterClass *
217
- GCNRewritePartialRegUses ::getRegClassWithShiftedSubregs (
223
+ GCNRewritePartialRegUsesImpl ::getRegClassWithShiftedSubregs (
218
224
const TargetRegisterClass *RC, unsigned RShift, unsigned RegNumBits,
219
225
unsigned CoverSubregIdx, SubRegMap &SubRegs) const {
220
226
@@ -289,8 +295,8 @@ GCNRewritePartialRegUses::getRegClassWithShiftedSubregs(
289
295
}
290
296
291
297
const TargetRegisterClass *
292
- GCNRewritePartialRegUses ::getMinSizeReg (const TargetRegisterClass *RC,
293
- SubRegMap &SubRegs) const {
298
+ GCNRewritePartialRegUsesImpl ::getMinSizeReg (const TargetRegisterClass *RC,
299
+ SubRegMap &SubRegs) const {
294
300
unsigned CoverSubreg = AMDGPU::NoSubRegister;
295
301
unsigned Offset = std::numeric_limits<unsigned >::max ();
296
302
unsigned End = 0 ;
@@ -343,9 +349,8 @@ GCNRewritePartialRegUses::getMinSizeReg(const TargetRegisterClass *RC,
343
349
344
350
// Only the subrange's lanemasks of the original interval need to be modified.
345
351
// Subrange for a covering subreg becomes the main range.
346
- void GCNRewritePartialRegUses::updateLiveIntervals (Register OldReg,
347
- Register NewReg,
348
- SubRegMap &SubRegs) const {
352
+ void GCNRewritePartialRegUsesImpl::updateLiveIntervals (
353
+ Register OldReg, Register NewReg, SubRegMap &SubRegs) const {
349
354
if (!LIS->hasInterval (OldReg))
350
355
return ;
351
356
@@ -400,13 +405,13 @@ void GCNRewritePartialRegUses::updateLiveIntervals(Register OldReg,
400
405
}
401
406
402
407
const TargetRegisterClass *
403
- GCNRewritePartialRegUses ::getOperandRegClass (MachineOperand &MO) const {
408
+ GCNRewritePartialRegUsesImpl ::getOperandRegClass (MachineOperand &MO) const {
404
409
MachineInstr *MI = MO.getParent ();
405
410
return TII->getRegClass (TII->get (MI->getOpcode ()), MI->getOperandNo (&MO), TRI,
406
411
*MI->getParent ()->getParent ());
407
412
}
408
413
409
- bool GCNRewritePartialRegUses ::rewriteReg (Register Reg) const {
414
+ bool GCNRewritePartialRegUsesImpl ::rewriteReg (Register Reg) const {
410
415
auto Range = MRI->reg_nodbg_operands (Reg);
411
416
if (Range.empty () || any_of (Range, [](MachineOperand &MO) {
412
417
return MO.getSubReg () == AMDGPU::NoSubRegister; // Whole reg used. [1]
@@ -476,24 +481,44 @@ bool GCNRewritePartialRegUses::rewriteReg(Register Reg) const {
476
481
return true ;
477
482
}
478
483
479
- bool GCNRewritePartialRegUses::runOnMachineFunction (MachineFunction &MF) {
484
+ bool GCNRewritePartialRegUsesImpl::run (MachineFunction &MF) {
480
485
MRI = &MF.getRegInfo ();
481
486
TRI = static_cast <const SIRegisterInfo *>(MRI->getTargetRegisterInfo ());
482
487
TII = MF.getSubtarget ().getInstrInfo ();
483
- auto *LISWrapper = getAnalysisIfAvailable<LiveIntervalsWrapperPass>();
484
- LIS = LISWrapper ? &LISWrapper->getLIS () : nullptr ;
485
488
bool Changed = false ;
486
489
for (size_t I = 0 , E = MRI->getNumVirtRegs (); I < E; ++I) {
487
490
Changed |= rewriteReg (Register::index2VirtReg (I));
488
491
}
489
492
return Changed;
490
493
}
491
494
492
- char GCNRewritePartialRegUses::ID;
495
+ bool GCNRewritePartialRegUsesLegacy::runOnMachineFunction (MachineFunction &MF) {
496
+ LiveIntervalsWrapperPass *LISWrapper =
497
+ getAnalysisIfAvailable<LiveIntervalsWrapperPass>();
498
+ LiveIntervals *LIS = LISWrapper ? &LISWrapper->getLIS () : nullptr ;
499
+ GCNRewritePartialRegUsesImpl Impl (LIS);
500
+ return Impl.run (MF);
501
+ }
502
+
503
+ PreservedAnalyses
504
+ GCNRewritePartialRegUsesPass::run (MachineFunction &MF,
505
+ MachineFunctionAnalysisManager &MFAM) {
506
+ auto *LIS = MFAM.getCachedResult <LiveIntervalsAnalysis>(MF);
507
+ if (!GCNRewritePartialRegUsesImpl (LIS).run (MF))
508
+ return PreservedAnalyses::all ();
509
+
510
+ auto PA = getMachineFunctionPassPreservedAnalyses ();
511
+ PA.preserveSet <CFGAnalyses>();
512
+ PA.preserve <LiveIntervalsAnalysis>();
513
+ PA.preserve <SlotIndexesAnalysis>();
514
+ return PA;
515
+ }
516
+
517
+ char GCNRewritePartialRegUsesLegacy::ID;
493
518
494
- char &llvm::GCNRewritePartialRegUsesID = GCNRewritePartialRegUses ::ID;
519
+ char &llvm::GCNRewritePartialRegUsesID = GCNRewritePartialRegUsesLegacy ::ID;
495
520
496
- INITIALIZE_PASS_BEGIN (GCNRewritePartialRegUses , DEBUG_TYPE,
521
+ INITIALIZE_PASS_BEGIN (GCNRewritePartialRegUsesLegacy , DEBUG_TYPE,
497
522
" Rewrite Partial Register Uses" , false , false )
498
- INITIALIZE_PASS_END(GCNRewritePartialRegUses , DEBUG_TYPE,
523
+ INITIALIZE_PASS_END(GCNRewritePartialRegUsesLegacy , DEBUG_TYPE,
499
524
" Rewrite Partial Register Uses" , false , false )
0 commit comments