Skip to content

Commit d7d0aaa

Browse files
[layout] Pack slot indexes before register allocation
Applies: llvm#66334 llvm#67038 Packing the slot indexes before register allocation is useful for us because it evens the gaps between slots after all the optimization passes that happen before `greedy` and may have removed a different number of instructions between AArch64 and X86. This leads to different slot gaps and, hence, slightly different regalloc in some cases. We backport the above patches for our LLVM, with the main difference being the absence of some convenient data structure iterators, which we had to convert to be compatible with our ADT infrastructure. We add the `-pack-indexes` flag to activate this. Addressses: systems-nuts/unifico#291
1 parent 1f5413f commit d7d0aaa

3 files changed

Lines changed: 38 additions & 1 deletion

File tree

llvm/include/llvm/CodeGen/SlotIndexes.h

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -637,8 +637,9 @@ class raw_ostream;
637637
renumberIndexes(newItr);
638638
llvm::sort(idx2MBBMap, less_first());
639639
}
640-
};
641640

641+
void packIndexes();
642+
};
642643
// Specialize IntervalMapInfo for half-open slot index intervals.
643644
template <>
644645
struct IntervalMapInfo<SlotIndex> : IntervalMapHalfOpenInfo<SlotIndex> {

llvm/lib/CodeGen/RegAllocGreedy.cpp

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -149,6 +149,11 @@ static cl::opt<bool>
149149
cl::desc("Simplify costs in greedy register allocation."),
150150
cl::init(false));
151151

152+
static cl::opt<bool>
153+
PackIndexes("pack-indexes",
154+
cl::desc("Pack indexes during register allocation."),
155+
cl::init(false));
156+
152157
static RegisterRegAlloc greedyRegAlloc("greedy", "greedy register allocator",
153158
createGreedyRegisterAllocator);
154159

@@ -3237,6 +3242,10 @@ bool RAGreedy::runOnMachineFunction(MachineFunction &mf) {
32373242
getAnalysis<LiveIntervals>(),
32383243
getAnalysis<LiveRegMatrix>());
32393244
Indexes = &getAnalysis<SlotIndexes>();
3245+
// Renumber to get accurate and consistent results from
3246+
// SlotIndexes::getApproxInstrDistance.
3247+
if (PackIndexes)
3248+
Indexes->packIndexes();
32403249
MBFI = &getAnalysis<MachineBlockFrequencyInfo>();
32413250
DomTree = &getAnalysis<MachineDominatorTree>();
32423251
ORE = &getAnalysis<MachineOptimizationRemarkEmitterPass>().getORE();

llvm/lib/CodeGen/SlotIndexes.cpp

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -234,6 +234,33 @@ void SlotIndexes::repairIndexesInRange(MachineBasicBlock *MBB,
234234
}
235235
}
236236

237+
void SlotIndexes::packIndexes() {
238+
unsigned Index = 0;
239+
MachineBasicBlock *MBB;
240+
// Iterate over basic blocks in slot index order.
241+
for (auto &v : idx2MBBMap) {
242+
// Update entries for each instruction in the block and the dummy entry for
243+
// the end of the block.
244+
MBB = v.second;
245+
auto MBBStartIdx = MBBRanges[MBB->getNumber()].first;
246+
auto MBBEndIdx = MBBRanges[MBB->getNumber()].second;
247+
for (auto I = MBBStartIdx.listEntry()->getIterator(),
248+
E = MBBEndIdx.listEntry()->getIterator();
249+
I++ != E;) {
250+
if (I == E || I->getInstr()) {
251+
Index += SlotIndex::InstrDist;
252+
I->setIndex(Index);
253+
} else {
254+
// LiveIntervals may still refer to entries for instructions that have
255+
// been erased. We have to update these entries but we don't want them
256+
// to affect the rest of the slot numbering, so set them to half way
257+
// between the neighboring real instrucion indexes.
258+
I->setIndex(Index + SlotIndex::InstrDist / 2);
259+
}
260+
}
261+
}
262+
}
263+
237264
#if !defined(NDEBUG) || defined(LLVM_ENABLE_DUMP)
238265
LLVM_DUMP_METHOD void SlotIndexes::dump() const {
239266
for (IndexList::const_iterator itr = indexList.begin();

0 commit comments

Comments
 (0)