1*9880d681SAndroid Build Coastguard Worker //===---------- SplitKit.cpp - Toolkit for splitting live ranges ----------===//
2*9880d681SAndroid Build Coastguard Worker //
3*9880d681SAndroid Build Coastguard Worker // The LLVM Compiler Infrastructure
4*9880d681SAndroid Build Coastguard Worker //
5*9880d681SAndroid Build Coastguard Worker // This file is distributed under the University of Illinois Open Source
6*9880d681SAndroid Build Coastguard Worker // License. See LICENSE.TXT for details.
7*9880d681SAndroid Build Coastguard Worker //
8*9880d681SAndroid Build Coastguard Worker //===----------------------------------------------------------------------===//
9*9880d681SAndroid Build Coastguard Worker //
10*9880d681SAndroid Build Coastguard Worker // This file contains the SplitAnalysis class as well as mutator functions for
11*9880d681SAndroid Build Coastguard Worker // live range splitting.
12*9880d681SAndroid Build Coastguard Worker //
13*9880d681SAndroid Build Coastguard Worker //===----------------------------------------------------------------------===//
14*9880d681SAndroid Build Coastguard Worker
15*9880d681SAndroid Build Coastguard Worker #include "SplitKit.h"
16*9880d681SAndroid Build Coastguard Worker #include "llvm/ADT/Statistic.h"
17*9880d681SAndroid Build Coastguard Worker #include "llvm/CodeGen/LiveIntervalAnalysis.h"
18*9880d681SAndroid Build Coastguard Worker #include "llvm/CodeGen/LiveRangeEdit.h"
19*9880d681SAndroid Build Coastguard Worker #include "llvm/CodeGen/MachineBlockFrequencyInfo.h"
20*9880d681SAndroid Build Coastguard Worker #include "llvm/CodeGen/MachineDominators.h"
21*9880d681SAndroid Build Coastguard Worker #include "llvm/CodeGen/MachineInstrBuilder.h"
22*9880d681SAndroid Build Coastguard Worker #include "llvm/CodeGen/MachineLoopInfo.h"
23*9880d681SAndroid Build Coastguard Worker #include "llvm/CodeGen/MachineRegisterInfo.h"
24*9880d681SAndroid Build Coastguard Worker #include "llvm/CodeGen/VirtRegMap.h"
25*9880d681SAndroid Build Coastguard Worker #include "llvm/Support/Debug.h"
26*9880d681SAndroid Build Coastguard Worker #include "llvm/Support/raw_ostream.h"
27*9880d681SAndroid Build Coastguard Worker #include "llvm/Target/TargetInstrInfo.h"
28*9880d681SAndroid Build Coastguard Worker #include "llvm/Target/TargetMachine.h"
29*9880d681SAndroid Build Coastguard Worker
30*9880d681SAndroid Build Coastguard Worker using namespace llvm;
31*9880d681SAndroid Build Coastguard Worker
32*9880d681SAndroid Build Coastguard Worker #define DEBUG_TYPE "regalloc"
33*9880d681SAndroid Build Coastguard Worker
34*9880d681SAndroid Build Coastguard Worker STATISTIC(NumFinished, "Number of splits finished");
35*9880d681SAndroid Build Coastguard Worker STATISTIC(NumSimple, "Number of splits that were simple");
36*9880d681SAndroid Build Coastguard Worker STATISTIC(NumCopies, "Number of copies inserted for splitting");
37*9880d681SAndroid Build Coastguard Worker STATISTIC(NumRemats, "Number of rematerialized defs for splitting");
38*9880d681SAndroid Build Coastguard Worker STATISTIC(NumRepairs, "Number of invalid live ranges repaired");
39*9880d681SAndroid Build Coastguard Worker
40*9880d681SAndroid Build Coastguard Worker //===----------------------------------------------------------------------===//
41*9880d681SAndroid Build Coastguard Worker // Last Insert Point Analysis
42*9880d681SAndroid Build Coastguard Worker //===----------------------------------------------------------------------===//
43*9880d681SAndroid Build Coastguard Worker
InsertPointAnalysis(const LiveIntervals & lis,unsigned BBNum)44*9880d681SAndroid Build Coastguard Worker InsertPointAnalysis::InsertPointAnalysis(const LiveIntervals &lis,
45*9880d681SAndroid Build Coastguard Worker unsigned BBNum)
46*9880d681SAndroid Build Coastguard Worker : LIS(lis), LastInsertPoint(BBNum) {}
47*9880d681SAndroid Build Coastguard Worker
48*9880d681SAndroid Build Coastguard Worker SlotIndex
computeLastInsertPoint(const LiveInterval & CurLI,const MachineBasicBlock & MBB)49*9880d681SAndroid Build Coastguard Worker InsertPointAnalysis::computeLastInsertPoint(const LiveInterval &CurLI,
50*9880d681SAndroid Build Coastguard Worker const MachineBasicBlock &MBB) {
51*9880d681SAndroid Build Coastguard Worker unsigned Num = MBB.getNumber();
52*9880d681SAndroid Build Coastguard Worker std::pair<SlotIndex, SlotIndex> &LIP = LastInsertPoint[Num];
53*9880d681SAndroid Build Coastguard Worker SlotIndex MBBEnd = LIS.getMBBEndIdx(&MBB);
54*9880d681SAndroid Build Coastguard Worker
55*9880d681SAndroid Build Coastguard Worker SmallVector<const MachineBasicBlock *, 1> EHPadSucessors;
56*9880d681SAndroid Build Coastguard Worker for (const MachineBasicBlock *SMBB : MBB.successors())
57*9880d681SAndroid Build Coastguard Worker if (SMBB->isEHPad())
58*9880d681SAndroid Build Coastguard Worker EHPadSucessors.push_back(SMBB);
59*9880d681SAndroid Build Coastguard Worker
60*9880d681SAndroid Build Coastguard Worker // Compute insert points on the first call. The pair is independent of the
61*9880d681SAndroid Build Coastguard Worker // current live interval.
62*9880d681SAndroid Build Coastguard Worker if (!LIP.first.isValid()) {
63*9880d681SAndroid Build Coastguard Worker MachineBasicBlock::const_iterator FirstTerm = MBB.getFirstTerminator();
64*9880d681SAndroid Build Coastguard Worker if (FirstTerm == MBB.end())
65*9880d681SAndroid Build Coastguard Worker LIP.first = MBBEnd;
66*9880d681SAndroid Build Coastguard Worker else
67*9880d681SAndroid Build Coastguard Worker LIP.first = LIS.getInstructionIndex(*FirstTerm);
68*9880d681SAndroid Build Coastguard Worker
69*9880d681SAndroid Build Coastguard Worker // If there is a landing pad successor, also find the call instruction.
70*9880d681SAndroid Build Coastguard Worker if (EHPadSucessors.empty())
71*9880d681SAndroid Build Coastguard Worker return LIP.first;
72*9880d681SAndroid Build Coastguard Worker // There may not be a call instruction (?) in which case we ignore LPad.
73*9880d681SAndroid Build Coastguard Worker LIP.second = LIP.first;
74*9880d681SAndroid Build Coastguard Worker for (MachineBasicBlock::const_iterator I = MBB.end(), E = MBB.begin();
75*9880d681SAndroid Build Coastguard Worker I != E;) {
76*9880d681SAndroid Build Coastguard Worker --I;
77*9880d681SAndroid Build Coastguard Worker if (I->isCall()) {
78*9880d681SAndroid Build Coastguard Worker LIP.second = LIS.getInstructionIndex(*I);
79*9880d681SAndroid Build Coastguard Worker break;
80*9880d681SAndroid Build Coastguard Worker }
81*9880d681SAndroid Build Coastguard Worker }
82*9880d681SAndroid Build Coastguard Worker }
83*9880d681SAndroid Build Coastguard Worker
84*9880d681SAndroid Build Coastguard Worker // If CurLI is live into a landing pad successor, move the last insert point
85*9880d681SAndroid Build Coastguard Worker // back to the call that may throw.
86*9880d681SAndroid Build Coastguard Worker if (!LIP.second)
87*9880d681SAndroid Build Coastguard Worker return LIP.first;
88*9880d681SAndroid Build Coastguard Worker
89*9880d681SAndroid Build Coastguard Worker if (none_of(EHPadSucessors, [&](const MachineBasicBlock *EHPad) {
90*9880d681SAndroid Build Coastguard Worker return LIS.isLiveInToMBB(CurLI, EHPad);
91*9880d681SAndroid Build Coastguard Worker }))
92*9880d681SAndroid Build Coastguard Worker return LIP.first;
93*9880d681SAndroid Build Coastguard Worker
94*9880d681SAndroid Build Coastguard Worker // Find the value leaving MBB.
95*9880d681SAndroid Build Coastguard Worker const VNInfo *VNI = CurLI.getVNInfoBefore(MBBEnd);
96*9880d681SAndroid Build Coastguard Worker if (!VNI)
97*9880d681SAndroid Build Coastguard Worker return LIP.first;
98*9880d681SAndroid Build Coastguard Worker
99*9880d681SAndroid Build Coastguard Worker // If the value leaving MBB was defined after the call in MBB, it can't
100*9880d681SAndroid Build Coastguard Worker // really be live-in to the landing pad. This can happen if the landing pad
101*9880d681SAndroid Build Coastguard Worker // has a PHI, and this register is undef on the exceptional edge.
102*9880d681SAndroid Build Coastguard Worker // <rdar://problem/10664933>
103*9880d681SAndroid Build Coastguard Worker if (!SlotIndex::isEarlierInstr(VNI->def, LIP.second) && VNI->def < MBBEnd)
104*9880d681SAndroid Build Coastguard Worker return LIP.first;
105*9880d681SAndroid Build Coastguard Worker
106*9880d681SAndroid Build Coastguard Worker // Value is properly live-in to the landing pad.
107*9880d681SAndroid Build Coastguard Worker // Only allow inserts before the call.
108*9880d681SAndroid Build Coastguard Worker return LIP.second;
109*9880d681SAndroid Build Coastguard Worker }
110*9880d681SAndroid Build Coastguard Worker
111*9880d681SAndroid Build Coastguard Worker MachineBasicBlock::iterator
getLastInsertPointIter(const LiveInterval & CurLI,MachineBasicBlock & MBB)112*9880d681SAndroid Build Coastguard Worker InsertPointAnalysis::getLastInsertPointIter(const LiveInterval &CurLI,
113*9880d681SAndroid Build Coastguard Worker MachineBasicBlock &MBB) {
114*9880d681SAndroid Build Coastguard Worker SlotIndex LIP = getLastInsertPoint(CurLI, MBB);
115*9880d681SAndroid Build Coastguard Worker if (LIP == LIS.getMBBEndIdx(&MBB))
116*9880d681SAndroid Build Coastguard Worker return MBB.end();
117*9880d681SAndroid Build Coastguard Worker return LIS.getInstructionFromIndex(LIP);
118*9880d681SAndroid Build Coastguard Worker }
119*9880d681SAndroid Build Coastguard Worker
120*9880d681SAndroid Build Coastguard Worker //===----------------------------------------------------------------------===//
121*9880d681SAndroid Build Coastguard Worker // Split Analysis
122*9880d681SAndroid Build Coastguard Worker //===----------------------------------------------------------------------===//
123*9880d681SAndroid Build Coastguard Worker
SplitAnalysis(const VirtRegMap & vrm,const LiveIntervals & lis,const MachineLoopInfo & mli)124*9880d681SAndroid Build Coastguard Worker SplitAnalysis::SplitAnalysis(const VirtRegMap &vrm, const LiveIntervals &lis,
125*9880d681SAndroid Build Coastguard Worker const MachineLoopInfo &mli)
126*9880d681SAndroid Build Coastguard Worker : MF(vrm.getMachineFunction()), VRM(vrm), LIS(lis), Loops(mli),
127*9880d681SAndroid Build Coastguard Worker TII(*MF.getSubtarget().getInstrInfo()), CurLI(nullptr),
128*9880d681SAndroid Build Coastguard Worker IPA(lis, MF.getNumBlockIDs()) {}
129*9880d681SAndroid Build Coastguard Worker
clear()130*9880d681SAndroid Build Coastguard Worker void SplitAnalysis::clear() {
131*9880d681SAndroid Build Coastguard Worker UseSlots.clear();
132*9880d681SAndroid Build Coastguard Worker UseBlocks.clear();
133*9880d681SAndroid Build Coastguard Worker ThroughBlocks.clear();
134*9880d681SAndroid Build Coastguard Worker CurLI = nullptr;
135*9880d681SAndroid Build Coastguard Worker DidRepairRange = false;
136*9880d681SAndroid Build Coastguard Worker }
137*9880d681SAndroid Build Coastguard Worker
138*9880d681SAndroid Build Coastguard Worker /// analyzeUses - Count instructions, basic blocks, and loops using CurLI.
analyzeUses()139*9880d681SAndroid Build Coastguard Worker void SplitAnalysis::analyzeUses() {
140*9880d681SAndroid Build Coastguard Worker assert(UseSlots.empty() && "Call clear first");
141*9880d681SAndroid Build Coastguard Worker
142*9880d681SAndroid Build Coastguard Worker // First get all the defs from the interval values. This provides the correct
143*9880d681SAndroid Build Coastguard Worker // slots for early clobbers.
144*9880d681SAndroid Build Coastguard Worker for (const VNInfo *VNI : CurLI->valnos)
145*9880d681SAndroid Build Coastguard Worker if (!VNI->isPHIDef() && !VNI->isUnused())
146*9880d681SAndroid Build Coastguard Worker UseSlots.push_back(VNI->def);
147*9880d681SAndroid Build Coastguard Worker
148*9880d681SAndroid Build Coastguard Worker // Get use slots form the use-def chain.
149*9880d681SAndroid Build Coastguard Worker const MachineRegisterInfo &MRI = MF.getRegInfo();
150*9880d681SAndroid Build Coastguard Worker for (MachineOperand &MO : MRI.use_nodbg_operands(CurLI->reg))
151*9880d681SAndroid Build Coastguard Worker if (!MO.isUndef())
152*9880d681SAndroid Build Coastguard Worker UseSlots.push_back(LIS.getInstructionIndex(*MO.getParent()).getRegSlot());
153*9880d681SAndroid Build Coastguard Worker
154*9880d681SAndroid Build Coastguard Worker array_pod_sort(UseSlots.begin(), UseSlots.end());
155*9880d681SAndroid Build Coastguard Worker
156*9880d681SAndroid Build Coastguard Worker // Remove duplicates, keeping the smaller slot for each instruction.
157*9880d681SAndroid Build Coastguard Worker // That is what we want for early clobbers.
158*9880d681SAndroid Build Coastguard Worker UseSlots.erase(std::unique(UseSlots.begin(), UseSlots.end(),
159*9880d681SAndroid Build Coastguard Worker SlotIndex::isSameInstr),
160*9880d681SAndroid Build Coastguard Worker UseSlots.end());
161*9880d681SAndroid Build Coastguard Worker
162*9880d681SAndroid Build Coastguard Worker // Compute per-live block info.
163*9880d681SAndroid Build Coastguard Worker if (!calcLiveBlockInfo()) {
164*9880d681SAndroid Build Coastguard Worker // FIXME: calcLiveBlockInfo found inconsistencies in the live range.
165*9880d681SAndroid Build Coastguard Worker // I am looking at you, RegisterCoalescer!
166*9880d681SAndroid Build Coastguard Worker DidRepairRange = true;
167*9880d681SAndroid Build Coastguard Worker ++NumRepairs;
168*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << "*** Fixing inconsistent live interval! ***\n");
169*9880d681SAndroid Build Coastguard Worker const_cast<LiveIntervals&>(LIS)
170*9880d681SAndroid Build Coastguard Worker .shrinkToUses(const_cast<LiveInterval*>(CurLI));
171*9880d681SAndroid Build Coastguard Worker UseBlocks.clear();
172*9880d681SAndroid Build Coastguard Worker ThroughBlocks.clear();
173*9880d681SAndroid Build Coastguard Worker bool fixed = calcLiveBlockInfo();
174*9880d681SAndroid Build Coastguard Worker (void)fixed;
175*9880d681SAndroid Build Coastguard Worker assert(fixed && "Couldn't fix broken live interval");
176*9880d681SAndroid Build Coastguard Worker }
177*9880d681SAndroid Build Coastguard Worker
178*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << "Analyze counted "
179*9880d681SAndroid Build Coastguard Worker << UseSlots.size() << " instrs in "
180*9880d681SAndroid Build Coastguard Worker << UseBlocks.size() << " blocks, through "
181*9880d681SAndroid Build Coastguard Worker << NumThroughBlocks << " blocks.\n");
182*9880d681SAndroid Build Coastguard Worker }
183*9880d681SAndroid Build Coastguard Worker
184*9880d681SAndroid Build Coastguard Worker /// calcLiveBlockInfo - Fill the LiveBlocks array with information about blocks
185*9880d681SAndroid Build Coastguard Worker /// where CurLI is live.
calcLiveBlockInfo()186*9880d681SAndroid Build Coastguard Worker bool SplitAnalysis::calcLiveBlockInfo() {
187*9880d681SAndroid Build Coastguard Worker ThroughBlocks.resize(MF.getNumBlockIDs());
188*9880d681SAndroid Build Coastguard Worker NumThroughBlocks = NumGapBlocks = 0;
189*9880d681SAndroid Build Coastguard Worker if (CurLI->empty())
190*9880d681SAndroid Build Coastguard Worker return true;
191*9880d681SAndroid Build Coastguard Worker
192*9880d681SAndroid Build Coastguard Worker LiveInterval::const_iterator LVI = CurLI->begin();
193*9880d681SAndroid Build Coastguard Worker LiveInterval::const_iterator LVE = CurLI->end();
194*9880d681SAndroid Build Coastguard Worker
195*9880d681SAndroid Build Coastguard Worker SmallVectorImpl<SlotIndex>::const_iterator UseI, UseE;
196*9880d681SAndroid Build Coastguard Worker UseI = UseSlots.begin();
197*9880d681SAndroid Build Coastguard Worker UseE = UseSlots.end();
198*9880d681SAndroid Build Coastguard Worker
199*9880d681SAndroid Build Coastguard Worker // Loop over basic blocks where CurLI is live.
200*9880d681SAndroid Build Coastguard Worker MachineFunction::iterator MFI =
201*9880d681SAndroid Build Coastguard Worker LIS.getMBBFromIndex(LVI->start)->getIterator();
202*9880d681SAndroid Build Coastguard Worker for (;;) {
203*9880d681SAndroid Build Coastguard Worker BlockInfo BI;
204*9880d681SAndroid Build Coastguard Worker BI.MBB = &*MFI;
205*9880d681SAndroid Build Coastguard Worker SlotIndex Start, Stop;
206*9880d681SAndroid Build Coastguard Worker std::tie(Start, Stop) = LIS.getSlotIndexes()->getMBBRange(BI.MBB);
207*9880d681SAndroid Build Coastguard Worker
208*9880d681SAndroid Build Coastguard Worker // If the block contains no uses, the range must be live through. At one
209*9880d681SAndroid Build Coastguard Worker // point, RegisterCoalescer could create dangling ranges that ended
210*9880d681SAndroid Build Coastguard Worker // mid-block.
211*9880d681SAndroid Build Coastguard Worker if (UseI == UseE || *UseI >= Stop) {
212*9880d681SAndroid Build Coastguard Worker ++NumThroughBlocks;
213*9880d681SAndroid Build Coastguard Worker ThroughBlocks.set(BI.MBB->getNumber());
214*9880d681SAndroid Build Coastguard Worker // The range shouldn't end mid-block if there are no uses. This shouldn't
215*9880d681SAndroid Build Coastguard Worker // happen.
216*9880d681SAndroid Build Coastguard Worker if (LVI->end < Stop)
217*9880d681SAndroid Build Coastguard Worker return false;
218*9880d681SAndroid Build Coastguard Worker } else {
219*9880d681SAndroid Build Coastguard Worker // This block has uses. Find the first and last uses in the block.
220*9880d681SAndroid Build Coastguard Worker BI.FirstInstr = *UseI;
221*9880d681SAndroid Build Coastguard Worker assert(BI.FirstInstr >= Start);
222*9880d681SAndroid Build Coastguard Worker do ++UseI;
223*9880d681SAndroid Build Coastguard Worker while (UseI != UseE && *UseI < Stop);
224*9880d681SAndroid Build Coastguard Worker BI.LastInstr = UseI[-1];
225*9880d681SAndroid Build Coastguard Worker assert(BI.LastInstr < Stop);
226*9880d681SAndroid Build Coastguard Worker
227*9880d681SAndroid Build Coastguard Worker // LVI is the first live segment overlapping MBB.
228*9880d681SAndroid Build Coastguard Worker BI.LiveIn = LVI->start <= Start;
229*9880d681SAndroid Build Coastguard Worker
230*9880d681SAndroid Build Coastguard Worker // When not live in, the first use should be a def.
231*9880d681SAndroid Build Coastguard Worker if (!BI.LiveIn) {
232*9880d681SAndroid Build Coastguard Worker assert(LVI->start == LVI->valno->def && "Dangling Segment start");
233*9880d681SAndroid Build Coastguard Worker assert(LVI->start == BI.FirstInstr && "First instr should be a def");
234*9880d681SAndroid Build Coastguard Worker BI.FirstDef = BI.FirstInstr;
235*9880d681SAndroid Build Coastguard Worker }
236*9880d681SAndroid Build Coastguard Worker
237*9880d681SAndroid Build Coastguard Worker // Look for gaps in the live range.
238*9880d681SAndroid Build Coastguard Worker BI.LiveOut = true;
239*9880d681SAndroid Build Coastguard Worker while (LVI->end < Stop) {
240*9880d681SAndroid Build Coastguard Worker SlotIndex LastStop = LVI->end;
241*9880d681SAndroid Build Coastguard Worker if (++LVI == LVE || LVI->start >= Stop) {
242*9880d681SAndroid Build Coastguard Worker BI.LiveOut = false;
243*9880d681SAndroid Build Coastguard Worker BI.LastInstr = LastStop;
244*9880d681SAndroid Build Coastguard Worker break;
245*9880d681SAndroid Build Coastguard Worker }
246*9880d681SAndroid Build Coastguard Worker
247*9880d681SAndroid Build Coastguard Worker if (LastStop < LVI->start) {
248*9880d681SAndroid Build Coastguard Worker // There is a gap in the live range. Create duplicate entries for the
249*9880d681SAndroid Build Coastguard Worker // live-in snippet and the live-out snippet.
250*9880d681SAndroid Build Coastguard Worker ++NumGapBlocks;
251*9880d681SAndroid Build Coastguard Worker
252*9880d681SAndroid Build Coastguard Worker // Push the Live-in part.
253*9880d681SAndroid Build Coastguard Worker BI.LiveOut = false;
254*9880d681SAndroid Build Coastguard Worker UseBlocks.push_back(BI);
255*9880d681SAndroid Build Coastguard Worker UseBlocks.back().LastInstr = LastStop;
256*9880d681SAndroid Build Coastguard Worker
257*9880d681SAndroid Build Coastguard Worker // Set up BI for the live-out part.
258*9880d681SAndroid Build Coastguard Worker BI.LiveIn = false;
259*9880d681SAndroid Build Coastguard Worker BI.LiveOut = true;
260*9880d681SAndroid Build Coastguard Worker BI.FirstInstr = BI.FirstDef = LVI->start;
261*9880d681SAndroid Build Coastguard Worker }
262*9880d681SAndroid Build Coastguard Worker
263*9880d681SAndroid Build Coastguard Worker // A Segment that starts in the middle of the block must be a def.
264*9880d681SAndroid Build Coastguard Worker assert(LVI->start == LVI->valno->def && "Dangling Segment start");
265*9880d681SAndroid Build Coastguard Worker if (!BI.FirstDef)
266*9880d681SAndroid Build Coastguard Worker BI.FirstDef = LVI->start;
267*9880d681SAndroid Build Coastguard Worker }
268*9880d681SAndroid Build Coastguard Worker
269*9880d681SAndroid Build Coastguard Worker UseBlocks.push_back(BI);
270*9880d681SAndroid Build Coastguard Worker
271*9880d681SAndroid Build Coastguard Worker // LVI is now at LVE or LVI->end >= Stop.
272*9880d681SAndroid Build Coastguard Worker if (LVI == LVE)
273*9880d681SAndroid Build Coastguard Worker break;
274*9880d681SAndroid Build Coastguard Worker }
275*9880d681SAndroid Build Coastguard Worker
276*9880d681SAndroid Build Coastguard Worker // Live segment ends exactly at Stop. Move to the next segment.
277*9880d681SAndroid Build Coastguard Worker if (LVI->end == Stop && ++LVI == LVE)
278*9880d681SAndroid Build Coastguard Worker break;
279*9880d681SAndroid Build Coastguard Worker
280*9880d681SAndroid Build Coastguard Worker // Pick the next basic block.
281*9880d681SAndroid Build Coastguard Worker if (LVI->start < Stop)
282*9880d681SAndroid Build Coastguard Worker ++MFI;
283*9880d681SAndroid Build Coastguard Worker else
284*9880d681SAndroid Build Coastguard Worker MFI = LIS.getMBBFromIndex(LVI->start)->getIterator();
285*9880d681SAndroid Build Coastguard Worker }
286*9880d681SAndroid Build Coastguard Worker
287*9880d681SAndroid Build Coastguard Worker assert(getNumLiveBlocks() == countLiveBlocks(CurLI) && "Bad block count");
288*9880d681SAndroid Build Coastguard Worker return true;
289*9880d681SAndroid Build Coastguard Worker }
290*9880d681SAndroid Build Coastguard Worker
countLiveBlocks(const LiveInterval * cli) const291*9880d681SAndroid Build Coastguard Worker unsigned SplitAnalysis::countLiveBlocks(const LiveInterval *cli) const {
292*9880d681SAndroid Build Coastguard Worker if (cli->empty())
293*9880d681SAndroid Build Coastguard Worker return 0;
294*9880d681SAndroid Build Coastguard Worker LiveInterval *li = const_cast<LiveInterval*>(cli);
295*9880d681SAndroid Build Coastguard Worker LiveInterval::iterator LVI = li->begin();
296*9880d681SAndroid Build Coastguard Worker LiveInterval::iterator LVE = li->end();
297*9880d681SAndroid Build Coastguard Worker unsigned Count = 0;
298*9880d681SAndroid Build Coastguard Worker
299*9880d681SAndroid Build Coastguard Worker // Loop over basic blocks where li is live.
300*9880d681SAndroid Build Coastguard Worker MachineFunction::const_iterator MFI =
301*9880d681SAndroid Build Coastguard Worker LIS.getMBBFromIndex(LVI->start)->getIterator();
302*9880d681SAndroid Build Coastguard Worker SlotIndex Stop = LIS.getMBBEndIdx(&*MFI);
303*9880d681SAndroid Build Coastguard Worker for (;;) {
304*9880d681SAndroid Build Coastguard Worker ++Count;
305*9880d681SAndroid Build Coastguard Worker LVI = li->advanceTo(LVI, Stop);
306*9880d681SAndroid Build Coastguard Worker if (LVI == LVE)
307*9880d681SAndroid Build Coastguard Worker return Count;
308*9880d681SAndroid Build Coastguard Worker do {
309*9880d681SAndroid Build Coastguard Worker ++MFI;
310*9880d681SAndroid Build Coastguard Worker Stop = LIS.getMBBEndIdx(&*MFI);
311*9880d681SAndroid Build Coastguard Worker } while (Stop <= LVI->start);
312*9880d681SAndroid Build Coastguard Worker }
313*9880d681SAndroid Build Coastguard Worker }
314*9880d681SAndroid Build Coastguard Worker
isOriginalEndpoint(SlotIndex Idx) const315*9880d681SAndroid Build Coastguard Worker bool SplitAnalysis::isOriginalEndpoint(SlotIndex Idx) const {
316*9880d681SAndroid Build Coastguard Worker unsigned OrigReg = VRM.getOriginal(CurLI->reg);
317*9880d681SAndroid Build Coastguard Worker const LiveInterval &Orig = LIS.getInterval(OrigReg);
318*9880d681SAndroid Build Coastguard Worker assert(!Orig.empty() && "Splitting empty interval?");
319*9880d681SAndroid Build Coastguard Worker LiveInterval::const_iterator I = Orig.find(Idx);
320*9880d681SAndroid Build Coastguard Worker
321*9880d681SAndroid Build Coastguard Worker // Range containing Idx should begin at Idx.
322*9880d681SAndroid Build Coastguard Worker if (I != Orig.end() && I->start <= Idx)
323*9880d681SAndroid Build Coastguard Worker return I->start == Idx;
324*9880d681SAndroid Build Coastguard Worker
325*9880d681SAndroid Build Coastguard Worker // Range does not contain Idx, previous must end at Idx.
326*9880d681SAndroid Build Coastguard Worker return I != Orig.begin() && (--I)->end == Idx;
327*9880d681SAndroid Build Coastguard Worker }
328*9880d681SAndroid Build Coastguard Worker
analyze(const LiveInterval * li)329*9880d681SAndroid Build Coastguard Worker void SplitAnalysis::analyze(const LiveInterval *li) {
330*9880d681SAndroid Build Coastguard Worker clear();
331*9880d681SAndroid Build Coastguard Worker CurLI = li;
332*9880d681SAndroid Build Coastguard Worker analyzeUses();
333*9880d681SAndroid Build Coastguard Worker }
334*9880d681SAndroid Build Coastguard Worker
335*9880d681SAndroid Build Coastguard Worker
336*9880d681SAndroid Build Coastguard Worker //===----------------------------------------------------------------------===//
337*9880d681SAndroid Build Coastguard Worker // Split Editor
338*9880d681SAndroid Build Coastguard Worker //===----------------------------------------------------------------------===//
339*9880d681SAndroid Build Coastguard Worker
340*9880d681SAndroid Build Coastguard Worker /// Create a new SplitEditor for editing the LiveInterval analyzed by SA.
SplitEditor(SplitAnalysis & sa,AliasAnalysis & aa,LiveIntervals & lis,VirtRegMap & vrm,MachineDominatorTree & mdt,MachineBlockFrequencyInfo & mbfi)341*9880d681SAndroid Build Coastguard Worker SplitEditor::SplitEditor(SplitAnalysis &sa, AliasAnalysis &aa,
342*9880d681SAndroid Build Coastguard Worker LiveIntervals &lis, VirtRegMap &vrm,
343*9880d681SAndroid Build Coastguard Worker MachineDominatorTree &mdt,
344*9880d681SAndroid Build Coastguard Worker MachineBlockFrequencyInfo &mbfi)
345*9880d681SAndroid Build Coastguard Worker : SA(sa), AA(aa), LIS(lis), VRM(vrm),
346*9880d681SAndroid Build Coastguard Worker MRI(vrm.getMachineFunction().getRegInfo()), MDT(mdt),
347*9880d681SAndroid Build Coastguard Worker TII(*vrm.getMachineFunction().getSubtarget().getInstrInfo()),
348*9880d681SAndroid Build Coastguard Worker TRI(*vrm.getMachineFunction().getSubtarget().getRegisterInfo()),
349*9880d681SAndroid Build Coastguard Worker MBFI(mbfi), Edit(nullptr), OpenIdx(0), SpillMode(SM_Partition),
350*9880d681SAndroid Build Coastguard Worker RegAssign(Allocator) {}
351*9880d681SAndroid Build Coastguard Worker
reset(LiveRangeEdit & LRE,ComplementSpillMode SM)352*9880d681SAndroid Build Coastguard Worker void SplitEditor::reset(LiveRangeEdit &LRE, ComplementSpillMode SM) {
353*9880d681SAndroid Build Coastguard Worker Edit = &LRE;
354*9880d681SAndroid Build Coastguard Worker SpillMode = SM;
355*9880d681SAndroid Build Coastguard Worker OpenIdx = 0;
356*9880d681SAndroid Build Coastguard Worker RegAssign.clear();
357*9880d681SAndroid Build Coastguard Worker Values.clear();
358*9880d681SAndroid Build Coastguard Worker
359*9880d681SAndroid Build Coastguard Worker // Reset the LiveRangeCalc instances needed for this spill mode.
360*9880d681SAndroid Build Coastguard Worker LRCalc[0].reset(&VRM.getMachineFunction(), LIS.getSlotIndexes(), &MDT,
361*9880d681SAndroid Build Coastguard Worker &LIS.getVNInfoAllocator());
362*9880d681SAndroid Build Coastguard Worker if (SpillMode)
363*9880d681SAndroid Build Coastguard Worker LRCalc[1].reset(&VRM.getMachineFunction(), LIS.getSlotIndexes(), &MDT,
364*9880d681SAndroid Build Coastguard Worker &LIS.getVNInfoAllocator());
365*9880d681SAndroid Build Coastguard Worker
366*9880d681SAndroid Build Coastguard Worker // We don't need an AliasAnalysis since we will only be performing
367*9880d681SAndroid Build Coastguard Worker // cheap-as-a-copy remats anyway.
368*9880d681SAndroid Build Coastguard Worker Edit->anyRematerializable(nullptr);
369*9880d681SAndroid Build Coastguard Worker }
370*9880d681SAndroid Build Coastguard Worker
371*9880d681SAndroid Build Coastguard Worker #if !defined(NDEBUG) || defined(LLVM_ENABLE_DUMP)
dump() const372*9880d681SAndroid Build Coastguard Worker LLVM_DUMP_METHOD void SplitEditor::dump() const {
373*9880d681SAndroid Build Coastguard Worker if (RegAssign.empty()) {
374*9880d681SAndroid Build Coastguard Worker dbgs() << " empty\n";
375*9880d681SAndroid Build Coastguard Worker return;
376*9880d681SAndroid Build Coastguard Worker }
377*9880d681SAndroid Build Coastguard Worker
378*9880d681SAndroid Build Coastguard Worker for (RegAssignMap::const_iterator I = RegAssign.begin(); I.valid(); ++I)
379*9880d681SAndroid Build Coastguard Worker dbgs() << " [" << I.start() << ';' << I.stop() << "):" << I.value();
380*9880d681SAndroid Build Coastguard Worker dbgs() << '\n';
381*9880d681SAndroid Build Coastguard Worker }
382*9880d681SAndroid Build Coastguard Worker #endif
383*9880d681SAndroid Build Coastguard Worker
defValue(unsigned RegIdx,const VNInfo * ParentVNI,SlotIndex Idx)384*9880d681SAndroid Build Coastguard Worker VNInfo *SplitEditor::defValue(unsigned RegIdx,
385*9880d681SAndroid Build Coastguard Worker const VNInfo *ParentVNI,
386*9880d681SAndroid Build Coastguard Worker SlotIndex Idx) {
387*9880d681SAndroid Build Coastguard Worker assert(ParentVNI && "Mapping NULL value");
388*9880d681SAndroid Build Coastguard Worker assert(Idx.isValid() && "Invalid SlotIndex");
389*9880d681SAndroid Build Coastguard Worker assert(Edit->getParent().getVNInfoAt(Idx) == ParentVNI && "Bad Parent VNI");
390*9880d681SAndroid Build Coastguard Worker LiveInterval *LI = &LIS.getInterval(Edit->get(RegIdx));
391*9880d681SAndroid Build Coastguard Worker
392*9880d681SAndroid Build Coastguard Worker // Create a new value.
393*9880d681SAndroid Build Coastguard Worker VNInfo *VNI = LI->getNextValue(Idx, LIS.getVNInfoAllocator());
394*9880d681SAndroid Build Coastguard Worker
395*9880d681SAndroid Build Coastguard Worker // Use insert for lookup, so we can add missing values with a second lookup.
396*9880d681SAndroid Build Coastguard Worker std::pair<ValueMap::iterator, bool> InsP =
397*9880d681SAndroid Build Coastguard Worker Values.insert(std::make_pair(std::make_pair(RegIdx, ParentVNI->id),
398*9880d681SAndroid Build Coastguard Worker ValueForcePair(VNI, false)));
399*9880d681SAndroid Build Coastguard Worker
400*9880d681SAndroid Build Coastguard Worker // This was the first time (RegIdx, ParentVNI) was mapped.
401*9880d681SAndroid Build Coastguard Worker // Keep it as a simple def without any liveness.
402*9880d681SAndroid Build Coastguard Worker if (InsP.second)
403*9880d681SAndroid Build Coastguard Worker return VNI;
404*9880d681SAndroid Build Coastguard Worker
405*9880d681SAndroid Build Coastguard Worker // If the previous value was a simple mapping, add liveness for it now.
406*9880d681SAndroid Build Coastguard Worker if (VNInfo *OldVNI = InsP.first->second.getPointer()) {
407*9880d681SAndroid Build Coastguard Worker SlotIndex Def = OldVNI->def;
408*9880d681SAndroid Build Coastguard Worker LI->addSegment(LiveInterval::Segment(Def, Def.getDeadSlot(), OldVNI));
409*9880d681SAndroid Build Coastguard Worker // No longer a simple mapping. Switch to a complex, non-forced mapping.
410*9880d681SAndroid Build Coastguard Worker InsP.first->second = ValueForcePair();
411*9880d681SAndroid Build Coastguard Worker }
412*9880d681SAndroid Build Coastguard Worker
413*9880d681SAndroid Build Coastguard Worker // This is a complex mapping, add liveness for VNI
414*9880d681SAndroid Build Coastguard Worker SlotIndex Def = VNI->def;
415*9880d681SAndroid Build Coastguard Worker LI->addSegment(LiveInterval::Segment(Def, Def.getDeadSlot(), VNI));
416*9880d681SAndroid Build Coastguard Worker
417*9880d681SAndroid Build Coastguard Worker return VNI;
418*9880d681SAndroid Build Coastguard Worker }
419*9880d681SAndroid Build Coastguard Worker
forceRecompute(unsigned RegIdx,const VNInfo * ParentVNI)420*9880d681SAndroid Build Coastguard Worker void SplitEditor::forceRecompute(unsigned RegIdx, const VNInfo *ParentVNI) {
421*9880d681SAndroid Build Coastguard Worker assert(ParentVNI && "Mapping NULL value");
422*9880d681SAndroid Build Coastguard Worker ValueForcePair &VFP = Values[std::make_pair(RegIdx, ParentVNI->id)];
423*9880d681SAndroid Build Coastguard Worker VNInfo *VNI = VFP.getPointer();
424*9880d681SAndroid Build Coastguard Worker
425*9880d681SAndroid Build Coastguard Worker // ParentVNI was either unmapped or already complex mapped. Either way, just
426*9880d681SAndroid Build Coastguard Worker // set the force bit.
427*9880d681SAndroid Build Coastguard Worker if (!VNI) {
428*9880d681SAndroid Build Coastguard Worker VFP.setInt(true);
429*9880d681SAndroid Build Coastguard Worker return;
430*9880d681SAndroid Build Coastguard Worker }
431*9880d681SAndroid Build Coastguard Worker
432*9880d681SAndroid Build Coastguard Worker // This was previously a single mapping. Make sure the old def is represented
433*9880d681SAndroid Build Coastguard Worker // by a trivial live range.
434*9880d681SAndroid Build Coastguard Worker SlotIndex Def = VNI->def;
435*9880d681SAndroid Build Coastguard Worker LiveInterval *LI = &LIS.getInterval(Edit->get(RegIdx));
436*9880d681SAndroid Build Coastguard Worker LI->addSegment(LiveInterval::Segment(Def, Def.getDeadSlot(), VNI));
437*9880d681SAndroid Build Coastguard Worker // Mark as complex mapped, forced.
438*9880d681SAndroid Build Coastguard Worker VFP = ValueForcePair(nullptr, true);
439*9880d681SAndroid Build Coastguard Worker }
440*9880d681SAndroid Build Coastguard Worker
defFromParent(unsigned RegIdx,VNInfo * ParentVNI,SlotIndex UseIdx,MachineBasicBlock & MBB,MachineBasicBlock::iterator I)441*9880d681SAndroid Build Coastguard Worker VNInfo *SplitEditor::defFromParent(unsigned RegIdx,
442*9880d681SAndroid Build Coastguard Worker VNInfo *ParentVNI,
443*9880d681SAndroid Build Coastguard Worker SlotIndex UseIdx,
444*9880d681SAndroid Build Coastguard Worker MachineBasicBlock &MBB,
445*9880d681SAndroid Build Coastguard Worker MachineBasicBlock::iterator I) {
446*9880d681SAndroid Build Coastguard Worker MachineInstr *CopyMI = nullptr;
447*9880d681SAndroid Build Coastguard Worker SlotIndex Def;
448*9880d681SAndroid Build Coastguard Worker LiveInterval *LI = &LIS.getInterval(Edit->get(RegIdx));
449*9880d681SAndroid Build Coastguard Worker
450*9880d681SAndroid Build Coastguard Worker // We may be trying to avoid interference that ends at a deleted instruction,
451*9880d681SAndroid Build Coastguard Worker // so always begin RegIdx 0 early and all others late.
452*9880d681SAndroid Build Coastguard Worker bool Late = RegIdx != 0;
453*9880d681SAndroid Build Coastguard Worker
454*9880d681SAndroid Build Coastguard Worker // Attempt cheap-as-a-copy rematerialization.
455*9880d681SAndroid Build Coastguard Worker unsigned Original = VRM.getOriginal(Edit->get(RegIdx));
456*9880d681SAndroid Build Coastguard Worker LiveInterval &OrigLI = LIS.getInterval(Original);
457*9880d681SAndroid Build Coastguard Worker VNInfo *OrigVNI = OrigLI.getVNInfoAt(UseIdx);
458*9880d681SAndroid Build Coastguard Worker LiveRangeEdit::Remat RM(ParentVNI);
459*9880d681SAndroid Build Coastguard Worker RM.OrigMI = LIS.getInstructionFromIndex(OrigVNI->def);
460*9880d681SAndroid Build Coastguard Worker
461*9880d681SAndroid Build Coastguard Worker if (Edit->canRematerializeAt(RM, OrigVNI, UseIdx, true)) {
462*9880d681SAndroid Build Coastguard Worker Def = Edit->rematerializeAt(MBB, I, LI->reg, RM, TRI, Late);
463*9880d681SAndroid Build Coastguard Worker ++NumRemats;
464*9880d681SAndroid Build Coastguard Worker } else {
465*9880d681SAndroid Build Coastguard Worker // Can't remat, just insert a copy from parent.
466*9880d681SAndroid Build Coastguard Worker CopyMI = BuildMI(MBB, I, DebugLoc(), TII.get(TargetOpcode::COPY), LI->reg)
467*9880d681SAndroid Build Coastguard Worker .addReg(Edit->getReg());
468*9880d681SAndroid Build Coastguard Worker Def = LIS.getSlotIndexes()
469*9880d681SAndroid Build Coastguard Worker ->insertMachineInstrInMaps(*CopyMI, Late)
470*9880d681SAndroid Build Coastguard Worker .getRegSlot();
471*9880d681SAndroid Build Coastguard Worker ++NumCopies;
472*9880d681SAndroid Build Coastguard Worker }
473*9880d681SAndroid Build Coastguard Worker
474*9880d681SAndroid Build Coastguard Worker // Define the value in Reg.
475*9880d681SAndroid Build Coastguard Worker return defValue(RegIdx, ParentVNI, Def);
476*9880d681SAndroid Build Coastguard Worker }
477*9880d681SAndroid Build Coastguard Worker
478*9880d681SAndroid Build Coastguard Worker /// Create a new virtual register and live interval.
openIntv()479*9880d681SAndroid Build Coastguard Worker unsigned SplitEditor::openIntv() {
480*9880d681SAndroid Build Coastguard Worker // Create the complement as index 0.
481*9880d681SAndroid Build Coastguard Worker if (Edit->empty())
482*9880d681SAndroid Build Coastguard Worker Edit->createEmptyInterval();
483*9880d681SAndroid Build Coastguard Worker
484*9880d681SAndroid Build Coastguard Worker // Create the open interval.
485*9880d681SAndroid Build Coastguard Worker OpenIdx = Edit->size();
486*9880d681SAndroid Build Coastguard Worker Edit->createEmptyInterval();
487*9880d681SAndroid Build Coastguard Worker return OpenIdx;
488*9880d681SAndroid Build Coastguard Worker }
489*9880d681SAndroid Build Coastguard Worker
selectIntv(unsigned Idx)490*9880d681SAndroid Build Coastguard Worker void SplitEditor::selectIntv(unsigned Idx) {
491*9880d681SAndroid Build Coastguard Worker assert(Idx != 0 && "Cannot select the complement interval");
492*9880d681SAndroid Build Coastguard Worker assert(Idx < Edit->size() && "Can only select previously opened interval");
493*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << " selectIntv " << OpenIdx << " -> " << Idx << '\n');
494*9880d681SAndroid Build Coastguard Worker OpenIdx = Idx;
495*9880d681SAndroid Build Coastguard Worker }
496*9880d681SAndroid Build Coastguard Worker
enterIntvBefore(SlotIndex Idx)497*9880d681SAndroid Build Coastguard Worker SlotIndex SplitEditor::enterIntvBefore(SlotIndex Idx) {
498*9880d681SAndroid Build Coastguard Worker assert(OpenIdx && "openIntv not called before enterIntvBefore");
499*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << " enterIntvBefore " << Idx);
500*9880d681SAndroid Build Coastguard Worker Idx = Idx.getBaseIndex();
501*9880d681SAndroid Build Coastguard Worker VNInfo *ParentVNI = Edit->getParent().getVNInfoAt(Idx);
502*9880d681SAndroid Build Coastguard Worker if (!ParentVNI) {
503*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << ": not live\n");
504*9880d681SAndroid Build Coastguard Worker return Idx;
505*9880d681SAndroid Build Coastguard Worker }
506*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << ": valno " << ParentVNI->id << '\n');
507*9880d681SAndroid Build Coastguard Worker MachineInstr *MI = LIS.getInstructionFromIndex(Idx);
508*9880d681SAndroid Build Coastguard Worker assert(MI && "enterIntvBefore called with invalid index");
509*9880d681SAndroid Build Coastguard Worker
510*9880d681SAndroid Build Coastguard Worker VNInfo *VNI = defFromParent(OpenIdx, ParentVNI, Idx, *MI->getParent(), MI);
511*9880d681SAndroid Build Coastguard Worker return VNI->def;
512*9880d681SAndroid Build Coastguard Worker }
513*9880d681SAndroid Build Coastguard Worker
enterIntvAfter(SlotIndex Idx)514*9880d681SAndroid Build Coastguard Worker SlotIndex SplitEditor::enterIntvAfter(SlotIndex Idx) {
515*9880d681SAndroid Build Coastguard Worker assert(OpenIdx && "openIntv not called before enterIntvAfter");
516*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << " enterIntvAfter " << Idx);
517*9880d681SAndroid Build Coastguard Worker Idx = Idx.getBoundaryIndex();
518*9880d681SAndroid Build Coastguard Worker VNInfo *ParentVNI = Edit->getParent().getVNInfoAt(Idx);
519*9880d681SAndroid Build Coastguard Worker if (!ParentVNI) {
520*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << ": not live\n");
521*9880d681SAndroid Build Coastguard Worker return Idx;
522*9880d681SAndroid Build Coastguard Worker }
523*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << ": valno " << ParentVNI->id << '\n');
524*9880d681SAndroid Build Coastguard Worker MachineInstr *MI = LIS.getInstructionFromIndex(Idx);
525*9880d681SAndroid Build Coastguard Worker assert(MI && "enterIntvAfter called with invalid index");
526*9880d681SAndroid Build Coastguard Worker
527*9880d681SAndroid Build Coastguard Worker VNInfo *VNI = defFromParent(OpenIdx, ParentVNI, Idx, *MI->getParent(),
528*9880d681SAndroid Build Coastguard Worker std::next(MachineBasicBlock::iterator(MI)));
529*9880d681SAndroid Build Coastguard Worker return VNI->def;
530*9880d681SAndroid Build Coastguard Worker }
531*9880d681SAndroid Build Coastguard Worker
enterIntvAtEnd(MachineBasicBlock & MBB)532*9880d681SAndroid Build Coastguard Worker SlotIndex SplitEditor::enterIntvAtEnd(MachineBasicBlock &MBB) {
533*9880d681SAndroid Build Coastguard Worker assert(OpenIdx && "openIntv not called before enterIntvAtEnd");
534*9880d681SAndroid Build Coastguard Worker SlotIndex End = LIS.getMBBEndIdx(&MBB);
535*9880d681SAndroid Build Coastguard Worker SlotIndex Last = End.getPrevSlot();
536*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << " enterIntvAtEnd BB#" << MBB.getNumber() << ", " << Last);
537*9880d681SAndroid Build Coastguard Worker VNInfo *ParentVNI = Edit->getParent().getVNInfoAt(Last);
538*9880d681SAndroid Build Coastguard Worker if (!ParentVNI) {
539*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << ": not live\n");
540*9880d681SAndroid Build Coastguard Worker return End;
541*9880d681SAndroid Build Coastguard Worker }
542*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << ": valno " << ParentVNI->id);
543*9880d681SAndroid Build Coastguard Worker VNInfo *VNI = defFromParent(OpenIdx, ParentVNI, Last, MBB,
544*9880d681SAndroid Build Coastguard Worker SA.getLastSplitPointIter(&MBB));
545*9880d681SAndroid Build Coastguard Worker RegAssign.insert(VNI->def, End, OpenIdx);
546*9880d681SAndroid Build Coastguard Worker DEBUG(dump());
547*9880d681SAndroid Build Coastguard Worker return VNI->def;
548*9880d681SAndroid Build Coastguard Worker }
549*9880d681SAndroid Build Coastguard Worker
550*9880d681SAndroid Build Coastguard Worker /// useIntv - indicate that all instructions in MBB should use OpenLI.
useIntv(const MachineBasicBlock & MBB)551*9880d681SAndroid Build Coastguard Worker void SplitEditor::useIntv(const MachineBasicBlock &MBB) {
552*9880d681SAndroid Build Coastguard Worker useIntv(LIS.getMBBStartIdx(&MBB), LIS.getMBBEndIdx(&MBB));
553*9880d681SAndroid Build Coastguard Worker }
554*9880d681SAndroid Build Coastguard Worker
useIntv(SlotIndex Start,SlotIndex End)555*9880d681SAndroid Build Coastguard Worker void SplitEditor::useIntv(SlotIndex Start, SlotIndex End) {
556*9880d681SAndroid Build Coastguard Worker assert(OpenIdx && "openIntv not called before useIntv");
557*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << " useIntv [" << Start << ';' << End << "):");
558*9880d681SAndroid Build Coastguard Worker RegAssign.insert(Start, End, OpenIdx);
559*9880d681SAndroid Build Coastguard Worker DEBUG(dump());
560*9880d681SAndroid Build Coastguard Worker }
561*9880d681SAndroid Build Coastguard Worker
leaveIntvAfter(SlotIndex Idx)562*9880d681SAndroid Build Coastguard Worker SlotIndex SplitEditor::leaveIntvAfter(SlotIndex Idx) {
563*9880d681SAndroid Build Coastguard Worker assert(OpenIdx && "openIntv not called before leaveIntvAfter");
564*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << " leaveIntvAfter " << Idx);
565*9880d681SAndroid Build Coastguard Worker
566*9880d681SAndroid Build Coastguard Worker // The interval must be live beyond the instruction at Idx.
567*9880d681SAndroid Build Coastguard Worker SlotIndex Boundary = Idx.getBoundaryIndex();
568*9880d681SAndroid Build Coastguard Worker VNInfo *ParentVNI = Edit->getParent().getVNInfoAt(Boundary);
569*9880d681SAndroid Build Coastguard Worker if (!ParentVNI) {
570*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << ": not live\n");
571*9880d681SAndroid Build Coastguard Worker return Boundary.getNextSlot();
572*9880d681SAndroid Build Coastguard Worker }
573*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << ": valno " << ParentVNI->id << '\n');
574*9880d681SAndroid Build Coastguard Worker MachineInstr *MI = LIS.getInstructionFromIndex(Boundary);
575*9880d681SAndroid Build Coastguard Worker assert(MI && "No instruction at index");
576*9880d681SAndroid Build Coastguard Worker
577*9880d681SAndroid Build Coastguard Worker // In spill mode, make live ranges as short as possible by inserting the copy
578*9880d681SAndroid Build Coastguard Worker // before MI. This is only possible if that instruction doesn't redefine the
579*9880d681SAndroid Build Coastguard Worker // value. The inserted COPY is not a kill, and we don't need to recompute
580*9880d681SAndroid Build Coastguard Worker // the source live range. The spiller also won't try to hoist this copy.
581*9880d681SAndroid Build Coastguard Worker if (SpillMode && !SlotIndex::isSameInstr(ParentVNI->def, Idx) &&
582*9880d681SAndroid Build Coastguard Worker MI->readsVirtualRegister(Edit->getReg())) {
583*9880d681SAndroid Build Coastguard Worker forceRecompute(0, ParentVNI);
584*9880d681SAndroid Build Coastguard Worker defFromParent(0, ParentVNI, Idx, *MI->getParent(), MI);
585*9880d681SAndroid Build Coastguard Worker return Idx;
586*9880d681SAndroid Build Coastguard Worker }
587*9880d681SAndroid Build Coastguard Worker
588*9880d681SAndroid Build Coastguard Worker VNInfo *VNI = defFromParent(0, ParentVNI, Boundary, *MI->getParent(),
589*9880d681SAndroid Build Coastguard Worker std::next(MachineBasicBlock::iterator(MI)));
590*9880d681SAndroid Build Coastguard Worker return VNI->def;
591*9880d681SAndroid Build Coastguard Worker }
592*9880d681SAndroid Build Coastguard Worker
leaveIntvBefore(SlotIndex Idx)593*9880d681SAndroid Build Coastguard Worker SlotIndex SplitEditor::leaveIntvBefore(SlotIndex Idx) {
594*9880d681SAndroid Build Coastguard Worker assert(OpenIdx && "openIntv not called before leaveIntvBefore");
595*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << " leaveIntvBefore " << Idx);
596*9880d681SAndroid Build Coastguard Worker
597*9880d681SAndroid Build Coastguard Worker // The interval must be live into the instruction at Idx.
598*9880d681SAndroid Build Coastguard Worker Idx = Idx.getBaseIndex();
599*9880d681SAndroid Build Coastguard Worker VNInfo *ParentVNI = Edit->getParent().getVNInfoAt(Idx);
600*9880d681SAndroid Build Coastguard Worker if (!ParentVNI) {
601*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << ": not live\n");
602*9880d681SAndroid Build Coastguard Worker return Idx.getNextSlot();
603*9880d681SAndroid Build Coastguard Worker }
604*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << ": valno " << ParentVNI->id << '\n');
605*9880d681SAndroid Build Coastguard Worker
606*9880d681SAndroid Build Coastguard Worker MachineInstr *MI = LIS.getInstructionFromIndex(Idx);
607*9880d681SAndroid Build Coastguard Worker assert(MI && "No instruction at index");
608*9880d681SAndroid Build Coastguard Worker VNInfo *VNI = defFromParent(0, ParentVNI, Idx, *MI->getParent(), MI);
609*9880d681SAndroid Build Coastguard Worker return VNI->def;
610*9880d681SAndroid Build Coastguard Worker }
611*9880d681SAndroid Build Coastguard Worker
leaveIntvAtTop(MachineBasicBlock & MBB)612*9880d681SAndroid Build Coastguard Worker SlotIndex SplitEditor::leaveIntvAtTop(MachineBasicBlock &MBB) {
613*9880d681SAndroid Build Coastguard Worker assert(OpenIdx && "openIntv not called before leaveIntvAtTop");
614*9880d681SAndroid Build Coastguard Worker SlotIndex Start = LIS.getMBBStartIdx(&MBB);
615*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << " leaveIntvAtTop BB#" << MBB.getNumber() << ", " << Start);
616*9880d681SAndroid Build Coastguard Worker
617*9880d681SAndroid Build Coastguard Worker VNInfo *ParentVNI = Edit->getParent().getVNInfoAt(Start);
618*9880d681SAndroid Build Coastguard Worker if (!ParentVNI) {
619*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << ": not live\n");
620*9880d681SAndroid Build Coastguard Worker return Start;
621*9880d681SAndroid Build Coastguard Worker }
622*9880d681SAndroid Build Coastguard Worker
623*9880d681SAndroid Build Coastguard Worker VNInfo *VNI = defFromParent(0, ParentVNI, Start, MBB,
624*9880d681SAndroid Build Coastguard Worker MBB.SkipPHIsAndLabels(MBB.begin()));
625*9880d681SAndroid Build Coastguard Worker RegAssign.insert(Start, VNI->def, OpenIdx);
626*9880d681SAndroid Build Coastguard Worker DEBUG(dump());
627*9880d681SAndroid Build Coastguard Worker return VNI->def;
628*9880d681SAndroid Build Coastguard Worker }
629*9880d681SAndroid Build Coastguard Worker
overlapIntv(SlotIndex Start,SlotIndex End)630*9880d681SAndroid Build Coastguard Worker void SplitEditor::overlapIntv(SlotIndex Start, SlotIndex End) {
631*9880d681SAndroid Build Coastguard Worker assert(OpenIdx && "openIntv not called before overlapIntv");
632*9880d681SAndroid Build Coastguard Worker const VNInfo *ParentVNI = Edit->getParent().getVNInfoAt(Start);
633*9880d681SAndroid Build Coastguard Worker assert(ParentVNI == Edit->getParent().getVNInfoBefore(End) &&
634*9880d681SAndroid Build Coastguard Worker "Parent changes value in extended range");
635*9880d681SAndroid Build Coastguard Worker assert(LIS.getMBBFromIndex(Start) == LIS.getMBBFromIndex(End) &&
636*9880d681SAndroid Build Coastguard Worker "Range cannot span basic blocks");
637*9880d681SAndroid Build Coastguard Worker
638*9880d681SAndroid Build Coastguard Worker // The complement interval will be extended as needed by LRCalc.extend().
639*9880d681SAndroid Build Coastguard Worker if (ParentVNI)
640*9880d681SAndroid Build Coastguard Worker forceRecompute(0, ParentVNI);
641*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << " overlapIntv [" << Start << ';' << End << "):");
642*9880d681SAndroid Build Coastguard Worker RegAssign.insert(Start, End, OpenIdx);
643*9880d681SAndroid Build Coastguard Worker DEBUG(dump());
644*9880d681SAndroid Build Coastguard Worker }
645*9880d681SAndroid Build Coastguard Worker
646*9880d681SAndroid Build Coastguard Worker //===----------------------------------------------------------------------===//
647*9880d681SAndroid Build Coastguard Worker // Spill modes
648*9880d681SAndroid Build Coastguard Worker //===----------------------------------------------------------------------===//
649*9880d681SAndroid Build Coastguard Worker
removeBackCopies(SmallVectorImpl<VNInfo * > & Copies)650*9880d681SAndroid Build Coastguard Worker void SplitEditor::removeBackCopies(SmallVectorImpl<VNInfo*> &Copies) {
651*9880d681SAndroid Build Coastguard Worker LiveInterval *LI = &LIS.getInterval(Edit->get(0));
652*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << "Removing " << Copies.size() << " back-copies.\n");
653*9880d681SAndroid Build Coastguard Worker RegAssignMap::iterator AssignI;
654*9880d681SAndroid Build Coastguard Worker AssignI.setMap(RegAssign);
655*9880d681SAndroid Build Coastguard Worker
656*9880d681SAndroid Build Coastguard Worker for (unsigned i = 0, e = Copies.size(); i != e; ++i) {
657*9880d681SAndroid Build Coastguard Worker SlotIndex Def = Copies[i]->def;
658*9880d681SAndroid Build Coastguard Worker MachineInstr *MI = LIS.getInstructionFromIndex(Def);
659*9880d681SAndroid Build Coastguard Worker assert(MI && "No instruction for back-copy");
660*9880d681SAndroid Build Coastguard Worker
661*9880d681SAndroid Build Coastguard Worker MachineBasicBlock *MBB = MI->getParent();
662*9880d681SAndroid Build Coastguard Worker MachineBasicBlock::iterator MBBI(MI);
663*9880d681SAndroid Build Coastguard Worker bool AtBegin;
664*9880d681SAndroid Build Coastguard Worker do AtBegin = MBBI == MBB->begin();
665*9880d681SAndroid Build Coastguard Worker while (!AtBegin && (--MBBI)->isDebugValue());
666*9880d681SAndroid Build Coastguard Worker
667*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << "Removing " << Def << '\t' << *MI);
668*9880d681SAndroid Build Coastguard Worker LIS.removeVRegDefAt(*LI, Def);
669*9880d681SAndroid Build Coastguard Worker LIS.RemoveMachineInstrFromMaps(*MI);
670*9880d681SAndroid Build Coastguard Worker MI->eraseFromParent();
671*9880d681SAndroid Build Coastguard Worker
672*9880d681SAndroid Build Coastguard Worker // Adjust RegAssign if a register assignment is killed at Def. We want to
673*9880d681SAndroid Build Coastguard Worker // avoid calculating the live range of the source register if possible.
674*9880d681SAndroid Build Coastguard Worker AssignI.find(Def.getPrevSlot());
675*9880d681SAndroid Build Coastguard Worker if (!AssignI.valid() || AssignI.start() >= Def)
676*9880d681SAndroid Build Coastguard Worker continue;
677*9880d681SAndroid Build Coastguard Worker // If MI doesn't kill the assigned register, just leave it.
678*9880d681SAndroid Build Coastguard Worker if (AssignI.stop() != Def)
679*9880d681SAndroid Build Coastguard Worker continue;
680*9880d681SAndroid Build Coastguard Worker unsigned RegIdx = AssignI.value();
681*9880d681SAndroid Build Coastguard Worker if (AtBegin || !MBBI->readsVirtualRegister(Edit->getReg())) {
682*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << " cannot find simple kill of RegIdx " << RegIdx << '\n');
683*9880d681SAndroid Build Coastguard Worker forceRecompute(RegIdx, Edit->getParent().getVNInfoAt(Def));
684*9880d681SAndroid Build Coastguard Worker } else {
685*9880d681SAndroid Build Coastguard Worker SlotIndex Kill = LIS.getInstructionIndex(*MBBI).getRegSlot();
686*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << " move kill to " << Kill << '\t' << *MBBI);
687*9880d681SAndroid Build Coastguard Worker AssignI.setStop(Kill);
688*9880d681SAndroid Build Coastguard Worker }
689*9880d681SAndroid Build Coastguard Worker }
690*9880d681SAndroid Build Coastguard Worker }
691*9880d681SAndroid Build Coastguard Worker
692*9880d681SAndroid Build Coastguard Worker MachineBasicBlock*
findShallowDominator(MachineBasicBlock * MBB,MachineBasicBlock * DefMBB)693*9880d681SAndroid Build Coastguard Worker SplitEditor::findShallowDominator(MachineBasicBlock *MBB,
694*9880d681SAndroid Build Coastguard Worker MachineBasicBlock *DefMBB) {
695*9880d681SAndroid Build Coastguard Worker if (MBB == DefMBB)
696*9880d681SAndroid Build Coastguard Worker return MBB;
697*9880d681SAndroid Build Coastguard Worker assert(MDT.dominates(DefMBB, MBB) && "MBB must be dominated by the def.");
698*9880d681SAndroid Build Coastguard Worker
699*9880d681SAndroid Build Coastguard Worker const MachineLoopInfo &Loops = SA.Loops;
700*9880d681SAndroid Build Coastguard Worker const MachineLoop *DefLoop = Loops.getLoopFor(DefMBB);
701*9880d681SAndroid Build Coastguard Worker MachineDomTreeNode *DefDomNode = MDT[DefMBB];
702*9880d681SAndroid Build Coastguard Worker
703*9880d681SAndroid Build Coastguard Worker // Best candidate so far.
704*9880d681SAndroid Build Coastguard Worker MachineBasicBlock *BestMBB = MBB;
705*9880d681SAndroid Build Coastguard Worker unsigned BestDepth = UINT_MAX;
706*9880d681SAndroid Build Coastguard Worker
707*9880d681SAndroid Build Coastguard Worker for (;;) {
708*9880d681SAndroid Build Coastguard Worker const MachineLoop *Loop = Loops.getLoopFor(MBB);
709*9880d681SAndroid Build Coastguard Worker
710*9880d681SAndroid Build Coastguard Worker // MBB isn't in a loop, it doesn't get any better. All dominators have a
711*9880d681SAndroid Build Coastguard Worker // higher frequency by definition.
712*9880d681SAndroid Build Coastguard Worker if (!Loop) {
713*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << "Def in BB#" << DefMBB->getNumber() << " dominates BB#"
714*9880d681SAndroid Build Coastguard Worker << MBB->getNumber() << " at depth 0\n");
715*9880d681SAndroid Build Coastguard Worker return MBB;
716*9880d681SAndroid Build Coastguard Worker }
717*9880d681SAndroid Build Coastguard Worker
718*9880d681SAndroid Build Coastguard Worker // We'll never be able to exit the DefLoop.
719*9880d681SAndroid Build Coastguard Worker if (Loop == DefLoop) {
720*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << "Def in BB#" << DefMBB->getNumber() << " dominates BB#"
721*9880d681SAndroid Build Coastguard Worker << MBB->getNumber() << " in the same loop\n");
722*9880d681SAndroid Build Coastguard Worker return MBB;
723*9880d681SAndroid Build Coastguard Worker }
724*9880d681SAndroid Build Coastguard Worker
725*9880d681SAndroid Build Coastguard Worker // Least busy dominator seen so far.
726*9880d681SAndroid Build Coastguard Worker unsigned Depth = Loop->getLoopDepth();
727*9880d681SAndroid Build Coastguard Worker if (Depth < BestDepth) {
728*9880d681SAndroid Build Coastguard Worker BestMBB = MBB;
729*9880d681SAndroid Build Coastguard Worker BestDepth = Depth;
730*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << "Def in BB#" << DefMBB->getNumber() << " dominates BB#"
731*9880d681SAndroid Build Coastguard Worker << MBB->getNumber() << " at depth " << Depth << '\n');
732*9880d681SAndroid Build Coastguard Worker }
733*9880d681SAndroid Build Coastguard Worker
734*9880d681SAndroid Build Coastguard Worker // Leave loop by going to the immediate dominator of the loop header.
735*9880d681SAndroid Build Coastguard Worker // This is a bigger stride than simply walking up the dominator tree.
736*9880d681SAndroid Build Coastguard Worker MachineDomTreeNode *IDom = MDT[Loop->getHeader()]->getIDom();
737*9880d681SAndroid Build Coastguard Worker
738*9880d681SAndroid Build Coastguard Worker // Too far up the dominator tree?
739*9880d681SAndroid Build Coastguard Worker if (!IDom || !MDT.dominates(DefDomNode, IDom))
740*9880d681SAndroid Build Coastguard Worker return BestMBB;
741*9880d681SAndroid Build Coastguard Worker
742*9880d681SAndroid Build Coastguard Worker MBB = IDom->getBlock();
743*9880d681SAndroid Build Coastguard Worker }
744*9880d681SAndroid Build Coastguard Worker }
745*9880d681SAndroid Build Coastguard Worker
computeRedundantBackCopies(DenseSet<unsigned> & NotToHoistSet,SmallVectorImpl<VNInfo * > & BackCopies)746*9880d681SAndroid Build Coastguard Worker void SplitEditor::computeRedundantBackCopies(
747*9880d681SAndroid Build Coastguard Worker DenseSet<unsigned> &NotToHoistSet, SmallVectorImpl<VNInfo *> &BackCopies) {
748*9880d681SAndroid Build Coastguard Worker LiveInterval *LI = &LIS.getInterval(Edit->get(0));
749*9880d681SAndroid Build Coastguard Worker LiveInterval *Parent = &Edit->getParent();
750*9880d681SAndroid Build Coastguard Worker SmallVector<SmallPtrSet<VNInfo *, 8>, 8> EqualVNs(Parent->getNumValNums());
751*9880d681SAndroid Build Coastguard Worker SmallPtrSet<VNInfo *, 8> DominatedVNIs;
752*9880d681SAndroid Build Coastguard Worker
753*9880d681SAndroid Build Coastguard Worker // Aggregate VNIs having the same value as ParentVNI.
754*9880d681SAndroid Build Coastguard Worker for (VNInfo *VNI : LI->valnos) {
755*9880d681SAndroid Build Coastguard Worker if (VNI->isUnused())
756*9880d681SAndroid Build Coastguard Worker continue;
757*9880d681SAndroid Build Coastguard Worker VNInfo *ParentVNI = Edit->getParent().getVNInfoAt(VNI->def);
758*9880d681SAndroid Build Coastguard Worker EqualVNs[ParentVNI->id].insert(VNI);
759*9880d681SAndroid Build Coastguard Worker }
760*9880d681SAndroid Build Coastguard Worker
761*9880d681SAndroid Build Coastguard Worker // For VNI aggregation of each ParentVNI, collect dominated, i.e.,
762*9880d681SAndroid Build Coastguard Worker // redundant VNIs to BackCopies.
763*9880d681SAndroid Build Coastguard Worker for (unsigned i = 0, e = Parent->getNumValNums(); i != e; ++i) {
764*9880d681SAndroid Build Coastguard Worker VNInfo *ParentVNI = Parent->getValNumInfo(i);
765*9880d681SAndroid Build Coastguard Worker if (!NotToHoistSet.count(ParentVNI->id))
766*9880d681SAndroid Build Coastguard Worker continue;
767*9880d681SAndroid Build Coastguard Worker SmallPtrSetIterator<VNInfo *> It1 = EqualVNs[ParentVNI->id].begin();
768*9880d681SAndroid Build Coastguard Worker SmallPtrSetIterator<VNInfo *> It2 = It1;
769*9880d681SAndroid Build Coastguard Worker for (; It1 != EqualVNs[ParentVNI->id].end(); ++It1) {
770*9880d681SAndroid Build Coastguard Worker It2 = It1;
771*9880d681SAndroid Build Coastguard Worker for (++It2; It2 != EqualVNs[ParentVNI->id].end(); ++It2) {
772*9880d681SAndroid Build Coastguard Worker if (DominatedVNIs.count(*It1) || DominatedVNIs.count(*It2))
773*9880d681SAndroid Build Coastguard Worker continue;
774*9880d681SAndroid Build Coastguard Worker
775*9880d681SAndroid Build Coastguard Worker MachineBasicBlock *MBB1 = LIS.getMBBFromIndex((*It1)->def);
776*9880d681SAndroid Build Coastguard Worker MachineBasicBlock *MBB2 = LIS.getMBBFromIndex((*It2)->def);
777*9880d681SAndroid Build Coastguard Worker if (MBB1 == MBB2) {
778*9880d681SAndroid Build Coastguard Worker DominatedVNIs.insert((*It1)->def < (*It2)->def ? (*It2) : (*It1));
779*9880d681SAndroid Build Coastguard Worker } else if (MDT.dominates(MBB1, MBB2)) {
780*9880d681SAndroid Build Coastguard Worker DominatedVNIs.insert(*It2);
781*9880d681SAndroid Build Coastguard Worker } else if (MDT.dominates(MBB2, MBB1)) {
782*9880d681SAndroid Build Coastguard Worker DominatedVNIs.insert(*It1);
783*9880d681SAndroid Build Coastguard Worker }
784*9880d681SAndroid Build Coastguard Worker }
785*9880d681SAndroid Build Coastguard Worker }
786*9880d681SAndroid Build Coastguard Worker if (!DominatedVNIs.empty()) {
787*9880d681SAndroid Build Coastguard Worker forceRecompute(0, ParentVNI);
788*9880d681SAndroid Build Coastguard Worker for (auto VNI : DominatedVNIs) {
789*9880d681SAndroid Build Coastguard Worker BackCopies.push_back(VNI);
790*9880d681SAndroid Build Coastguard Worker }
791*9880d681SAndroid Build Coastguard Worker DominatedVNIs.clear();
792*9880d681SAndroid Build Coastguard Worker }
793*9880d681SAndroid Build Coastguard Worker }
794*9880d681SAndroid Build Coastguard Worker }
795*9880d681SAndroid Build Coastguard Worker
796*9880d681SAndroid Build Coastguard Worker /// For SM_Size mode, find a common dominator for all the back-copies for
797*9880d681SAndroid Build Coastguard Worker /// the same ParentVNI and hoist the backcopies to the dominator BB.
798*9880d681SAndroid Build Coastguard Worker /// For SM_Speed mode, if the common dominator is hot and it is not beneficial
799*9880d681SAndroid Build Coastguard Worker /// to do the hoisting, simply remove the dominated backcopies for the same
800*9880d681SAndroid Build Coastguard Worker /// ParentVNI.
hoistCopies()801*9880d681SAndroid Build Coastguard Worker void SplitEditor::hoistCopies() {
802*9880d681SAndroid Build Coastguard Worker // Get the complement interval, always RegIdx 0.
803*9880d681SAndroid Build Coastguard Worker LiveInterval *LI = &LIS.getInterval(Edit->get(0));
804*9880d681SAndroid Build Coastguard Worker LiveInterval *Parent = &Edit->getParent();
805*9880d681SAndroid Build Coastguard Worker
806*9880d681SAndroid Build Coastguard Worker // Track the nearest common dominator for all back-copies for each ParentVNI,
807*9880d681SAndroid Build Coastguard Worker // indexed by ParentVNI->id.
808*9880d681SAndroid Build Coastguard Worker typedef std::pair<MachineBasicBlock*, SlotIndex> DomPair;
809*9880d681SAndroid Build Coastguard Worker SmallVector<DomPair, 8> NearestDom(Parent->getNumValNums());
810*9880d681SAndroid Build Coastguard Worker // The total cost of all the back-copies for each ParentVNI.
811*9880d681SAndroid Build Coastguard Worker SmallVector<BlockFrequency, 8> Costs(Parent->getNumValNums());
812*9880d681SAndroid Build Coastguard Worker // The ParentVNI->id set for which hoisting back-copies are not beneficial
813*9880d681SAndroid Build Coastguard Worker // for Speed.
814*9880d681SAndroid Build Coastguard Worker DenseSet<unsigned> NotToHoistSet;
815*9880d681SAndroid Build Coastguard Worker
816*9880d681SAndroid Build Coastguard Worker // Find the nearest common dominator for parent values with multiple
817*9880d681SAndroid Build Coastguard Worker // back-copies. If a single back-copy dominates, put it in DomPair.second.
818*9880d681SAndroid Build Coastguard Worker for (VNInfo *VNI : LI->valnos) {
819*9880d681SAndroid Build Coastguard Worker if (VNI->isUnused())
820*9880d681SAndroid Build Coastguard Worker continue;
821*9880d681SAndroid Build Coastguard Worker VNInfo *ParentVNI = Edit->getParent().getVNInfoAt(VNI->def);
822*9880d681SAndroid Build Coastguard Worker assert(ParentVNI && "Parent not live at complement def");
823*9880d681SAndroid Build Coastguard Worker
824*9880d681SAndroid Build Coastguard Worker // Don't hoist remats. The complement is probably going to disappear
825*9880d681SAndroid Build Coastguard Worker // completely anyway.
826*9880d681SAndroid Build Coastguard Worker if (Edit->didRematerialize(ParentVNI))
827*9880d681SAndroid Build Coastguard Worker continue;
828*9880d681SAndroid Build Coastguard Worker
829*9880d681SAndroid Build Coastguard Worker MachineBasicBlock *ValMBB = LIS.getMBBFromIndex(VNI->def);
830*9880d681SAndroid Build Coastguard Worker
831*9880d681SAndroid Build Coastguard Worker DomPair &Dom = NearestDom[ParentVNI->id];
832*9880d681SAndroid Build Coastguard Worker
833*9880d681SAndroid Build Coastguard Worker // Keep directly defined parent values. This is either a PHI or an
834*9880d681SAndroid Build Coastguard Worker // instruction in the complement range. All other copies of ParentVNI
835*9880d681SAndroid Build Coastguard Worker // should be eliminated.
836*9880d681SAndroid Build Coastguard Worker if (VNI->def == ParentVNI->def) {
837*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << "Direct complement def at " << VNI->def << '\n');
838*9880d681SAndroid Build Coastguard Worker Dom = DomPair(ValMBB, VNI->def);
839*9880d681SAndroid Build Coastguard Worker continue;
840*9880d681SAndroid Build Coastguard Worker }
841*9880d681SAndroid Build Coastguard Worker // Skip the singly mapped values. There is nothing to gain from hoisting a
842*9880d681SAndroid Build Coastguard Worker // single back-copy.
843*9880d681SAndroid Build Coastguard Worker if (Values.lookup(std::make_pair(0, ParentVNI->id)).getPointer()) {
844*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << "Single complement def at " << VNI->def << '\n');
845*9880d681SAndroid Build Coastguard Worker continue;
846*9880d681SAndroid Build Coastguard Worker }
847*9880d681SAndroid Build Coastguard Worker
848*9880d681SAndroid Build Coastguard Worker if (!Dom.first) {
849*9880d681SAndroid Build Coastguard Worker // First time we see ParentVNI. VNI dominates itself.
850*9880d681SAndroid Build Coastguard Worker Dom = DomPair(ValMBB, VNI->def);
851*9880d681SAndroid Build Coastguard Worker } else if (Dom.first == ValMBB) {
852*9880d681SAndroid Build Coastguard Worker // Two defs in the same block. Pick the earlier def.
853*9880d681SAndroid Build Coastguard Worker if (!Dom.second.isValid() || VNI->def < Dom.second)
854*9880d681SAndroid Build Coastguard Worker Dom.second = VNI->def;
855*9880d681SAndroid Build Coastguard Worker } else {
856*9880d681SAndroid Build Coastguard Worker // Different basic blocks. Check if one dominates.
857*9880d681SAndroid Build Coastguard Worker MachineBasicBlock *Near =
858*9880d681SAndroid Build Coastguard Worker MDT.findNearestCommonDominator(Dom.first, ValMBB);
859*9880d681SAndroid Build Coastguard Worker if (Near == ValMBB)
860*9880d681SAndroid Build Coastguard Worker // Def ValMBB dominates.
861*9880d681SAndroid Build Coastguard Worker Dom = DomPair(ValMBB, VNI->def);
862*9880d681SAndroid Build Coastguard Worker else if (Near != Dom.first)
863*9880d681SAndroid Build Coastguard Worker // None dominate. Hoist to common dominator, need new def.
864*9880d681SAndroid Build Coastguard Worker Dom = DomPair(Near, SlotIndex());
865*9880d681SAndroid Build Coastguard Worker Costs[ParentVNI->id] += MBFI.getBlockFreq(ValMBB);
866*9880d681SAndroid Build Coastguard Worker }
867*9880d681SAndroid Build Coastguard Worker
868*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << "Multi-mapped complement " << VNI->id << '@' << VNI->def
869*9880d681SAndroid Build Coastguard Worker << " for parent " << ParentVNI->id << '@' << ParentVNI->def
870*9880d681SAndroid Build Coastguard Worker << " hoist to BB#" << Dom.first->getNumber() << ' '
871*9880d681SAndroid Build Coastguard Worker << Dom.second << '\n');
872*9880d681SAndroid Build Coastguard Worker }
873*9880d681SAndroid Build Coastguard Worker
874*9880d681SAndroid Build Coastguard Worker // Insert the hoisted copies.
875*9880d681SAndroid Build Coastguard Worker for (unsigned i = 0, e = Parent->getNumValNums(); i != e; ++i) {
876*9880d681SAndroid Build Coastguard Worker DomPair &Dom = NearestDom[i];
877*9880d681SAndroid Build Coastguard Worker if (!Dom.first || Dom.second.isValid())
878*9880d681SAndroid Build Coastguard Worker continue;
879*9880d681SAndroid Build Coastguard Worker // This value needs a hoisted copy inserted at the end of Dom.first.
880*9880d681SAndroid Build Coastguard Worker VNInfo *ParentVNI = Parent->getValNumInfo(i);
881*9880d681SAndroid Build Coastguard Worker MachineBasicBlock *DefMBB = LIS.getMBBFromIndex(ParentVNI->def);
882*9880d681SAndroid Build Coastguard Worker // Get a less loopy dominator than Dom.first.
883*9880d681SAndroid Build Coastguard Worker Dom.first = findShallowDominator(Dom.first, DefMBB);
884*9880d681SAndroid Build Coastguard Worker if (SpillMode == SM_Speed &&
885*9880d681SAndroid Build Coastguard Worker MBFI.getBlockFreq(Dom.first) > Costs[ParentVNI->id]) {
886*9880d681SAndroid Build Coastguard Worker NotToHoistSet.insert(ParentVNI->id);
887*9880d681SAndroid Build Coastguard Worker continue;
888*9880d681SAndroid Build Coastguard Worker }
889*9880d681SAndroid Build Coastguard Worker SlotIndex Last = LIS.getMBBEndIdx(Dom.first).getPrevSlot();
890*9880d681SAndroid Build Coastguard Worker Dom.second =
891*9880d681SAndroid Build Coastguard Worker defFromParent(0, ParentVNI, Last, *Dom.first,
892*9880d681SAndroid Build Coastguard Worker SA.getLastSplitPointIter(Dom.first))->def;
893*9880d681SAndroid Build Coastguard Worker }
894*9880d681SAndroid Build Coastguard Worker
895*9880d681SAndroid Build Coastguard Worker // Remove redundant back-copies that are now known to be dominated by another
896*9880d681SAndroid Build Coastguard Worker // def with the same value.
897*9880d681SAndroid Build Coastguard Worker SmallVector<VNInfo*, 8> BackCopies;
898*9880d681SAndroid Build Coastguard Worker for (VNInfo *VNI : LI->valnos) {
899*9880d681SAndroid Build Coastguard Worker if (VNI->isUnused())
900*9880d681SAndroid Build Coastguard Worker continue;
901*9880d681SAndroid Build Coastguard Worker VNInfo *ParentVNI = Edit->getParent().getVNInfoAt(VNI->def);
902*9880d681SAndroid Build Coastguard Worker const DomPair &Dom = NearestDom[ParentVNI->id];
903*9880d681SAndroid Build Coastguard Worker if (!Dom.first || Dom.second == VNI->def ||
904*9880d681SAndroid Build Coastguard Worker NotToHoistSet.count(ParentVNI->id))
905*9880d681SAndroid Build Coastguard Worker continue;
906*9880d681SAndroid Build Coastguard Worker BackCopies.push_back(VNI);
907*9880d681SAndroid Build Coastguard Worker forceRecompute(0, ParentVNI);
908*9880d681SAndroid Build Coastguard Worker }
909*9880d681SAndroid Build Coastguard Worker
910*9880d681SAndroid Build Coastguard Worker // If it is not beneficial to hoist all the BackCopies, simply remove
911*9880d681SAndroid Build Coastguard Worker // redundant BackCopies in speed mode.
912*9880d681SAndroid Build Coastguard Worker if (SpillMode == SM_Speed && !NotToHoistSet.empty())
913*9880d681SAndroid Build Coastguard Worker computeRedundantBackCopies(NotToHoistSet, BackCopies);
914*9880d681SAndroid Build Coastguard Worker
915*9880d681SAndroid Build Coastguard Worker removeBackCopies(BackCopies);
916*9880d681SAndroid Build Coastguard Worker }
917*9880d681SAndroid Build Coastguard Worker
918*9880d681SAndroid Build Coastguard Worker
919*9880d681SAndroid Build Coastguard Worker /// transferValues - Transfer all possible values to the new live ranges.
920*9880d681SAndroid Build Coastguard Worker /// Values that were rematerialized are left alone, they need LRCalc.extend().
transferValues()921*9880d681SAndroid Build Coastguard Worker bool SplitEditor::transferValues() {
922*9880d681SAndroid Build Coastguard Worker bool Skipped = false;
923*9880d681SAndroid Build Coastguard Worker RegAssignMap::const_iterator AssignI = RegAssign.begin();
924*9880d681SAndroid Build Coastguard Worker for (const LiveRange::Segment &S : Edit->getParent()) {
925*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << " blit " << S << ':');
926*9880d681SAndroid Build Coastguard Worker VNInfo *ParentVNI = S.valno;
927*9880d681SAndroid Build Coastguard Worker // RegAssign has holes where RegIdx 0 should be used.
928*9880d681SAndroid Build Coastguard Worker SlotIndex Start = S.start;
929*9880d681SAndroid Build Coastguard Worker AssignI.advanceTo(Start);
930*9880d681SAndroid Build Coastguard Worker do {
931*9880d681SAndroid Build Coastguard Worker unsigned RegIdx;
932*9880d681SAndroid Build Coastguard Worker SlotIndex End = S.end;
933*9880d681SAndroid Build Coastguard Worker if (!AssignI.valid()) {
934*9880d681SAndroid Build Coastguard Worker RegIdx = 0;
935*9880d681SAndroid Build Coastguard Worker } else if (AssignI.start() <= Start) {
936*9880d681SAndroid Build Coastguard Worker RegIdx = AssignI.value();
937*9880d681SAndroid Build Coastguard Worker if (AssignI.stop() < End) {
938*9880d681SAndroid Build Coastguard Worker End = AssignI.stop();
939*9880d681SAndroid Build Coastguard Worker ++AssignI;
940*9880d681SAndroid Build Coastguard Worker }
941*9880d681SAndroid Build Coastguard Worker } else {
942*9880d681SAndroid Build Coastguard Worker RegIdx = 0;
943*9880d681SAndroid Build Coastguard Worker End = std::min(End, AssignI.start());
944*9880d681SAndroid Build Coastguard Worker }
945*9880d681SAndroid Build Coastguard Worker
946*9880d681SAndroid Build Coastguard Worker // The interval [Start;End) is continuously mapped to RegIdx, ParentVNI.
947*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << " [" << Start << ';' << End << ")=" << RegIdx);
948*9880d681SAndroid Build Coastguard Worker LiveRange &LR = LIS.getInterval(Edit->get(RegIdx));
949*9880d681SAndroid Build Coastguard Worker
950*9880d681SAndroid Build Coastguard Worker // Check for a simply defined value that can be blitted directly.
951*9880d681SAndroid Build Coastguard Worker ValueForcePair VFP = Values.lookup(std::make_pair(RegIdx, ParentVNI->id));
952*9880d681SAndroid Build Coastguard Worker if (VNInfo *VNI = VFP.getPointer()) {
953*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << ':' << VNI->id);
954*9880d681SAndroid Build Coastguard Worker LR.addSegment(LiveInterval::Segment(Start, End, VNI));
955*9880d681SAndroid Build Coastguard Worker Start = End;
956*9880d681SAndroid Build Coastguard Worker continue;
957*9880d681SAndroid Build Coastguard Worker }
958*9880d681SAndroid Build Coastguard Worker
959*9880d681SAndroid Build Coastguard Worker // Skip values with forced recomputation.
960*9880d681SAndroid Build Coastguard Worker if (VFP.getInt()) {
961*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << "(recalc)");
962*9880d681SAndroid Build Coastguard Worker Skipped = true;
963*9880d681SAndroid Build Coastguard Worker Start = End;
964*9880d681SAndroid Build Coastguard Worker continue;
965*9880d681SAndroid Build Coastguard Worker }
966*9880d681SAndroid Build Coastguard Worker
967*9880d681SAndroid Build Coastguard Worker LiveRangeCalc &LRC = getLRCalc(RegIdx);
968*9880d681SAndroid Build Coastguard Worker
969*9880d681SAndroid Build Coastguard Worker // This value has multiple defs in RegIdx, but it wasn't rematerialized,
970*9880d681SAndroid Build Coastguard Worker // so the live range is accurate. Add live-in blocks in [Start;End) to the
971*9880d681SAndroid Build Coastguard Worker // LiveInBlocks.
972*9880d681SAndroid Build Coastguard Worker MachineFunction::iterator MBB = LIS.getMBBFromIndex(Start)->getIterator();
973*9880d681SAndroid Build Coastguard Worker SlotIndex BlockStart, BlockEnd;
974*9880d681SAndroid Build Coastguard Worker std::tie(BlockStart, BlockEnd) = LIS.getSlotIndexes()->getMBBRange(&*MBB);
975*9880d681SAndroid Build Coastguard Worker
976*9880d681SAndroid Build Coastguard Worker // The first block may be live-in, or it may have its own def.
977*9880d681SAndroid Build Coastguard Worker if (Start != BlockStart) {
978*9880d681SAndroid Build Coastguard Worker VNInfo *VNI = LR.extendInBlock(BlockStart, std::min(BlockEnd, End));
979*9880d681SAndroid Build Coastguard Worker assert(VNI && "Missing def for complex mapped value");
980*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << ':' << VNI->id << "*BB#" << MBB->getNumber());
981*9880d681SAndroid Build Coastguard Worker // MBB has its own def. Is it also live-out?
982*9880d681SAndroid Build Coastguard Worker if (BlockEnd <= End)
983*9880d681SAndroid Build Coastguard Worker LRC.setLiveOutValue(&*MBB, VNI);
984*9880d681SAndroid Build Coastguard Worker
985*9880d681SAndroid Build Coastguard Worker // Skip to the next block for live-in.
986*9880d681SAndroid Build Coastguard Worker ++MBB;
987*9880d681SAndroid Build Coastguard Worker BlockStart = BlockEnd;
988*9880d681SAndroid Build Coastguard Worker }
989*9880d681SAndroid Build Coastguard Worker
990*9880d681SAndroid Build Coastguard Worker // Handle the live-in blocks covered by [Start;End).
991*9880d681SAndroid Build Coastguard Worker assert(Start <= BlockStart && "Expected live-in block");
992*9880d681SAndroid Build Coastguard Worker while (BlockStart < End) {
993*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << ">BB#" << MBB->getNumber());
994*9880d681SAndroid Build Coastguard Worker BlockEnd = LIS.getMBBEndIdx(&*MBB);
995*9880d681SAndroid Build Coastguard Worker if (BlockStart == ParentVNI->def) {
996*9880d681SAndroid Build Coastguard Worker // This block has the def of a parent PHI, so it isn't live-in.
997*9880d681SAndroid Build Coastguard Worker assert(ParentVNI->isPHIDef() && "Non-phi defined at block start?");
998*9880d681SAndroid Build Coastguard Worker VNInfo *VNI = LR.extendInBlock(BlockStart, std::min(BlockEnd, End));
999*9880d681SAndroid Build Coastguard Worker assert(VNI && "Missing def for complex mapped parent PHI");
1000*9880d681SAndroid Build Coastguard Worker if (End >= BlockEnd)
1001*9880d681SAndroid Build Coastguard Worker LRC.setLiveOutValue(&*MBB, VNI); // Live-out as well.
1002*9880d681SAndroid Build Coastguard Worker } else {
1003*9880d681SAndroid Build Coastguard Worker // This block needs a live-in value. The last block covered may not
1004*9880d681SAndroid Build Coastguard Worker // be live-out.
1005*9880d681SAndroid Build Coastguard Worker if (End < BlockEnd)
1006*9880d681SAndroid Build Coastguard Worker LRC.addLiveInBlock(LR, MDT[&*MBB], End);
1007*9880d681SAndroid Build Coastguard Worker else {
1008*9880d681SAndroid Build Coastguard Worker // Live-through, and we don't know the value.
1009*9880d681SAndroid Build Coastguard Worker LRC.addLiveInBlock(LR, MDT[&*MBB]);
1010*9880d681SAndroid Build Coastguard Worker LRC.setLiveOutValue(&*MBB, nullptr);
1011*9880d681SAndroid Build Coastguard Worker }
1012*9880d681SAndroid Build Coastguard Worker }
1013*9880d681SAndroid Build Coastguard Worker BlockStart = BlockEnd;
1014*9880d681SAndroid Build Coastguard Worker ++MBB;
1015*9880d681SAndroid Build Coastguard Worker }
1016*9880d681SAndroid Build Coastguard Worker Start = End;
1017*9880d681SAndroid Build Coastguard Worker } while (Start != S.end);
1018*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << '\n');
1019*9880d681SAndroid Build Coastguard Worker }
1020*9880d681SAndroid Build Coastguard Worker
1021*9880d681SAndroid Build Coastguard Worker LRCalc[0].calculateValues();
1022*9880d681SAndroid Build Coastguard Worker if (SpillMode)
1023*9880d681SAndroid Build Coastguard Worker LRCalc[1].calculateValues();
1024*9880d681SAndroid Build Coastguard Worker
1025*9880d681SAndroid Build Coastguard Worker return Skipped;
1026*9880d681SAndroid Build Coastguard Worker }
1027*9880d681SAndroid Build Coastguard Worker
extendPHIKillRanges()1028*9880d681SAndroid Build Coastguard Worker void SplitEditor::extendPHIKillRanges() {
1029*9880d681SAndroid Build Coastguard Worker // Extend live ranges to be live-out for successor PHI values.
1030*9880d681SAndroid Build Coastguard Worker for (const VNInfo *PHIVNI : Edit->getParent().valnos) {
1031*9880d681SAndroid Build Coastguard Worker if (PHIVNI->isUnused() || !PHIVNI->isPHIDef())
1032*9880d681SAndroid Build Coastguard Worker continue;
1033*9880d681SAndroid Build Coastguard Worker unsigned RegIdx = RegAssign.lookup(PHIVNI->def);
1034*9880d681SAndroid Build Coastguard Worker LiveRange &LR = LIS.getInterval(Edit->get(RegIdx));
1035*9880d681SAndroid Build Coastguard Worker
1036*9880d681SAndroid Build Coastguard Worker // Check whether PHI is dead.
1037*9880d681SAndroid Build Coastguard Worker const LiveRange::Segment *Segment = LR.getSegmentContaining(PHIVNI->def);
1038*9880d681SAndroid Build Coastguard Worker assert(Segment != nullptr && "Missing segment for VNI");
1039*9880d681SAndroid Build Coastguard Worker if (Segment->end == PHIVNI->def.getDeadSlot()) {
1040*9880d681SAndroid Build Coastguard Worker // This is a dead PHI. Remove it.
1041*9880d681SAndroid Build Coastguard Worker LR.removeSegment(*Segment, true);
1042*9880d681SAndroid Build Coastguard Worker continue;
1043*9880d681SAndroid Build Coastguard Worker }
1044*9880d681SAndroid Build Coastguard Worker
1045*9880d681SAndroid Build Coastguard Worker LiveRangeCalc &LRC = getLRCalc(RegIdx);
1046*9880d681SAndroid Build Coastguard Worker MachineBasicBlock *MBB = LIS.getMBBFromIndex(PHIVNI->def);
1047*9880d681SAndroid Build Coastguard Worker for (MachineBasicBlock::pred_iterator PI = MBB->pred_begin(),
1048*9880d681SAndroid Build Coastguard Worker PE = MBB->pred_end(); PI != PE; ++PI) {
1049*9880d681SAndroid Build Coastguard Worker SlotIndex End = LIS.getMBBEndIdx(*PI);
1050*9880d681SAndroid Build Coastguard Worker SlotIndex LastUse = End.getPrevSlot();
1051*9880d681SAndroid Build Coastguard Worker // The predecessor may not have a live-out value. That is OK, like an
1052*9880d681SAndroid Build Coastguard Worker // undef PHI operand.
1053*9880d681SAndroid Build Coastguard Worker if (Edit->getParent().liveAt(LastUse)) {
1054*9880d681SAndroid Build Coastguard Worker assert(RegAssign.lookup(LastUse) == RegIdx &&
1055*9880d681SAndroid Build Coastguard Worker "Different register assignment in phi predecessor");
1056*9880d681SAndroid Build Coastguard Worker LRC.extend(LR, End);
1057*9880d681SAndroid Build Coastguard Worker }
1058*9880d681SAndroid Build Coastguard Worker }
1059*9880d681SAndroid Build Coastguard Worker }
1060*9880d681SAndroid Build Coastguard Worker }
1061*9880d681SAndroid Build Coastguard Worker
1062*9880d681SAndroid Build Coastguard Worker /// rewriteAssigned - Rewrite all uses of Edit->getReg().
rewriteAssigned(bool ExtendRanges)1063*9880d681SAndroid Build Coastguard Worker void SplitEditor::rewriteAssigned(bool ExtendRanges) {
1064*9880d681SAndroid Build Coastguard Worker for (MachineRegisterInfo::reg_iterator RI = MRI.reg_begin(Edit->getReg()),
1065*9880d681SAndroid Build Coastguard Worker RE = MRI.reg_end(); RI != RE;) {
1066*9880d681SAndroid Build Coastguard Worker MachineOperand &MO = *RI;
1067*9880d681SAndroid Build Coastguard Worker MachineInstr *MI = MO.getParent();
1068*9880d681SAndroid Build Coastguard Worker ++RI;
1069*9880d681SAndroid Build Coastguard Worker // LiveDebugVariables should have handled all DBG_VALUE instructions.
1070*9880d681SAndroid Build Coastguard Worker if (MI->isDebugValue()) {
1071*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << "Zapping " << *MI);
1072*9880d681SAndroid Build Coastguard Worker MO.setReg(0);
1073*9880d681SAndroid Build Coastguard Worker continue;
1074*9880d681SAndroid Build Coastguard Worker }
1075*9880d681SAndroid Build Coastguard Worker
1076*9880d681SAndroid Build Coastguard Worker // <undef> operands don't really read the register, so it doesn't matter
1077*9880d681SAndroid Build Coastguard Worker // which register we choose. When the use operand is tied to a def, we must
1078*9880d681SAndroid Build Coastguard Worker // use the same register as the def, so just do that always.
1079*9880d681SAndroid Build Coastguard Worker SlotIndex Idx = LIS.getInstructionIndex(*MI);
1080*9880d681SAndroid Build Coastguard Worker if (MO.isDef() || MO.isUndef())
1081*9880d681SAndroid Build Coastguard Worker Idx = Idx.getRegSlot(MO.isEarlyClobber());
1082*9880d681SAndroid Build Coastguard Worker
1083*9880d681SAndroid Build Coastguard Worker // Rewrite to the mapped register at Idx.
1084*9880d681SAndroid Build Coastguard Worker unsigned RegIdx = RegAssign.lookup(Idx);
1085*9880d681SAndroid Build Coastguard Worker LiveInterval *LI = &LIS.getInterval(Edit->get(RegIdx));
1086*9880d681SAndroid Build Coastguard Worker MO.setReg(LI->reg);
1087*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << " rewr BB#" << MI->getParent()->getNumber() << '\t'
1088*9880d681SAndroid Build Coastguard Worker << Idx << ':' << RegIdx << '\t' << *MI);
1089*9880d681SAndroid Build Coastguard Worker
1090*9880d681SAndroid Build Coastguard Worker // Extend liveness to Idx if the instruction reads reg.
1091*9880d681SAndroid Build Coastguard Worker if (!ExtendRanges || MO.isUndef())
1092*9880d681SAndroid Build Coastguard Worker continue;
1093*9880d681SAndroid Build Coastguard Worker
1094*9880d681SAndroid Build Coastguard Worker // Skip instructions that don't read Reg.
1095*9880d681SAndroid Build Coastguard Worker if (MO.isDef()) {
1096*9880d681SAndroid Build Coastguard Worker if (!MO.getSubReg() && !MO.isEarlyClobber())
1097*9880d681SAndroid Build Coastguard Worker continue;
1098*9880d681SAndroid Build Coastguard Worker // We may wan't to extend a live range for a partial redef, or for a use
1099*9880d681SAndroid Build Coastguard Worker // tied to an early clobber.
1100*9880d681SAndroid Build Coastguard Worker Idx = Idx.getPrevSlot();
1101*9880d681SAndroid Build Coastguard Worker if (!Edit->getParent().liveAt(Idx))
1102*9880d681SAndroid Build Coastguard Worker continue;
1103*9880d681SAndroid Build Coastguard Worker } else
1104*9880d681SAndroid Build Coastguard Worker Idx = Idx.getRegSlot(true);
1105*9880d681SAndroid Build Coastguard Worker
1106*9880d681SAndroid Build Coastguard Worker getLRCalc(RegIdx).extend(*LI, Idx.getNextSlot());
1107*9880d681SAndroid Build Coastguard Worker }
1108*9880d681SAndroid Build Coastguard Worker }
1109*9880d681SAndroid Build Coastguard Worker
deleteRematVictims()1110*9880d681SAndroid Build Coastguard Worker void SplitEditor::deleteRematVictims() {
1111*9880d681SAndroid Build Coastguard Worker SmallVector<MachineInstr*, 8> Dead;
1112*9880d681SAndroid Build Coastguard Worker for (LiveRangeEdit::iterator I = Edit->begin(), E = Edit->end(); I != E; ++I){
1113*9880d681SAndroid Build Coastguard Worker LiveInterval *LI = &LIS.getInterval(*I);
1114*9880d681SAndroid Build Coastguard Worker for (const LiveRange::Segment &S : LI->segments) {
1115*9880d681SAndroid Build Coastguard Worker // Dead defs end at the dead slot.
1116*9880d681SAndroid Build Coastguard Worker if (S.end != S.valno->def.getDeadSlot())
1117*9880d681SAndroid Build Coastguard Worker continue;
1118*9880d681SAndroid Build Coastguard Worker if (S.valno->isPHIDef())
1119*9880d681SAndroid Build Coastguard Worker continue;
1120*9880d681SAndroid Build Coastguard Worker MachineInstr *MI = LIS.getInstructionFromIndex(S.valno->def);
1121*9880d681SAndroid Build Coastguard Worker assert(MI && "Missing instruction for dead def");
1122*9880d681SAndroid Build Coastguard Worker MI->addRegisterDead(LI->reg, &TRI);
1123*9880d681SAndroid Build Coastguard Worker
1124*9880d681SAndroid Build Coastguard Worker if (!MI->allDefsAreDead())
1125*9880d681SAndroid Build Coastguard Worker continue;
1126*9880d681SAndroid Build Coastguard Worker
1127*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << "All defs dead: " << *MI);
1128*9880d681SAndroid Build Coastguard Worker Dead.push_back(MI);
1129*9880d681SAndroid Build Coastguard Worker }
1130*9880d681SAndroid Build Coastguard Worker }
1131*9880d681SAndroid Build Coastguard Worker
1132*9880d681SAndroid Build Coastguard Worker if (Dead.empty())
1133*9880d681SAndroid Build Coastguard Worker return;
1134*9880d681SAndroid Build Coastguard Worker
1135*9880d681SAndroid Build Coastguard Worker Edit->eliminateDeadDefs(Dead, None, &AA);
1136*9880d681SAndroid Build Coastguard Worker }
1137*9880d681SAndroid Build Coastguard Worker
finish(SmallVectorImpl<unsigned> * LRMap)1138*9880d681SAndroid Build Coastguard Worker void SplitEditor::finish(SmallVectorImpl<unsigned> *LRMap) {
1139*9880d681SAndroid Build Coastguard Worker ++NumFinished;
1140*9880d681SAndroid Build Coastguard Worker
1141*9880d681SAndroid Build Coastguard Worker // At this point, the live intervals in Edit contain VNInfos corresponding to
1142*9880d681SAndroid Build Coastguard Worker // the inserted copies.
1143*9880d681SAndroid Build Coastguard Worker
1144*9880d681SAndroid Build Coastguard Worker // Add the original defs from the parent interval.
1145*9880d681SAndroid Build Coastguard Worker for (const VNInfo *ParentVNI : Edit->getParent().valnos) {
1146*9880d681SAndroid Build Coastguard Worker if (ParentVNI->isUnused())
1147*9880d681SAndroid Build Coastguard Worker continue;
1148*9880d681SAndroid Build Coastguard Worker unsigned RegIdx = RegAssign.lookup(ParentVNI->def);
1149*9880d681SAndroid Build Coastguard Worker defValue(RegIdx, ParentVNI, ParentVNI->def);
1150*9880d681SAndroid Build Coastguard Worker
1151*9880d681SAndroid Build Coastguard Worker // Force rematted values to be recomputed everywhere.
1152*9880d681SAndroid Build Coastguard Worker // The new live ranges may be truncated.
1153*9880d681SAndroid Build Coastguard Worker if (Edit->didRematerialize(ParentVNI))
1154*9880d681SAndroid Build Coastguard Worker for (unsigned i = 0, e = Edit->size(); i != e; ++i)
1155*9880d681SAndroid Build Coastguard Worker forceRecompute(i, ParentVNI);
1156*9880d681SAndroid Build Coastguard Worker }
1157*9880d681SAndroid Build Coastguard Worker
1158*9880d681SAndroid Build Coastguard Worker // Hoist back-copies to the complement interval when in spill mode.
1159*9880d681SAndroid Build Coastguard Worker switch (SpillMode) {
1160*9880d681SAndroid Build Coastguard Worker case SM_Partition:
1161*9880d681SAndroid Build Coastguard Worker // Leave all back-copies as is.
1162*9880d681SAndroid Build Coastguard Worker break;
1163*9880d681SAndroid Build Coastguard Worker case SM_Size:
1164*9880d681SAndroid Build Coastguard Worker case SM_Speed:
1165*9880d681SAndroid Build Coastguard Worker // hoistCopies will behave differently between size and speed.
1166*9880d681SAndroid Build Coastguard Worker hoistCopies();
1167*9880d681SAndroid Build Coastguard Worker }
1168*9880d681SAndroid Build Coastguard Worker
1169*9880d681SAndroid Build Coastguard Worker // Transfer the simply mapped values, check if any are skipped.
1170*9880d681SAndroid Build Coastguard Worker bool Skipped = transferValues();
1171*9880d681SAndroid Build Coastguard Worker
1172*9880d681SAndroid Build Coastguard Worker // Rewrite virtual registers, possibly extending ranges.
1173*9880d681SAndroid Build Coastguard Worker rewriteAssigned(Skipped);
1174*9880d681SAndroid Build Coastguard Worker
1175*9880d681SAndroid Build Coastguard Worker if (Skipped)
1176*9880d681SAndroid Build Coastguard Worker extendPHIKillRanges();
1177*9880d681SAndroid Build Coastguard Worker else
1178*9880d681SAndroid Build Coastguard Worker ++NumSimple;
1179*9880d681SAndroid Build Coastguard Worker
1180*9880d681SAndroid Build Coastguard Worker // Delete defs that were rematted everywhere.
1181*9880d681SAndroid Build Coastguard Worker if (Skipped)
1182*9880d681SAndroid Build Coastguard Worker deleteRematVictims();
1183*9880d681SAndroid Build Coastguard Worker
1184*9880d681SAndroid Build Coastguard Worker // Get rid of unused values and set phi-kill flags.
1185*9880d681SAndroid Build Coastguard Worker for (LiveRangeEdit::iterator I = Edit->begin(), E = Edit->end(); I != E; ++I) {
1186*9880d681SAndroid Build Coastguard Worker LiveInterval &LI = LIS.getInterval(*I);
1187*9880d681SAndroid Build Coastguard Worker LI.RenumberValues();
1188*9880d681SAndroid Build Coastguard Worker }
1189*9880d681SAndroid Build Coastguard Worker
1190*9880d681SAndroid Build Coastguard Worker // Provide a reverse mapping from original indices to Edit ranges.
1191*9880d681SAndroid Build Coastguard Worker if (LRMap) {
1192*9880d681SAndroid Build Coastguard Worker LRMap->clear();
1193*9880d681SAndroid Build Coastguard Worker for (unsigned i = 0, e = Edit->size(); i != e; ++i)
1194*9880d681SAndroid Build Coastguard Worker LRMap->push_back(i);
1195*9880d681SAndroid Build Coastguard Worker }
1196*9880d681SAndroid Build Coastguard Worker
1197*9880d681SAndroid Build Coastguard Worker // Now check if any registers were separated into multiple components.
1198*9880d681SAndroid Build Coastguard Worker ConnectedVNInfoEqClasses ConEQ(LIS);
1199*9880d681SAndroid Build Coastguard Worker for (unsigned i = 0, e = Edit->size(); i != e; ++i) {
1200*9880d681SAndroid Build Coastguard Worker // Don't use iterators, they are invalidated by create() below.
1201*9880d681SAndroid Build Coastguard Worker unsigned VReg = Edit->get(i);
1202*9880d681SAndroid Build Coastguard Worker LiveInterval &LI = LIS.getInterval(VReg);
1203*9880d681SAndroid Build Coastguard Worker SmallVector<LiveInterval*, 8> SplitLIs;
1204*9880d681SAndroid Build Coastguard Worker LIS.splitSeparateComponents(LI, SplitLIs);
1205*9880d681SAndroid Build Coastguard Worker unsigned Original = VRM.getOriginal(VReg);
1206*9880d681SAndroid Build Coastguard Worker for (LiveInterval *SplitLI : SplitLIs)
1207*9880d681SAndroid Build Coastguard Worker VRM.setIsSplitFromReg(SplitLI->reg, Original);
1208*9880d681SAndroid Build Coastguard Worker
1209*9880d681SAndroid Build Coastguard Worker // The new intervals all map back to i.
1210*9880d681SAndroid Build Coastguard Worker if (LRMap)
1211*9880d681SAndroid Build Coastguard Worker LRMap->resize(Edit->size(), i);
1212*9880d681SAndroid Build Coastguard Worker }
1213*9880d681SAndroid Build Coastguard Worker
1214*9880d681SAndroid Build Coastguard Worker // Calculate spill weight and allocation hints for new intervals.
1215*9880d681SAndroid Build Coastguard Worker Edit->calculateRegClassAndHint(VRM.getMachineFunction(), SA.Loops, MBFI);
1216*9880d681SAndroid Build Coastguard Worker
1217*9880d681SAndroid Build Coastguard Worker assert(!LRMap || LRMap->size() == Edit->size());
1218*9880d681SAndroid Build Coastguard Worker }
1219*9880d681SAndroid Build Coastguard Worker
1220*9880d681SAndroid Build Coastguard Worker
1221*9880d681SAndroid Build Coastguard Worker //===----------------------------------------------------------------------===//
1222*9880d681SAndroid Build Coastguard Worker // Single Block Splitting
1223*9880d681SAndroid Build Coastguard Worker //===----------------------------------------------------------------------===//
1224*9880d681SAndroid Build Coastguard Worker
shouldSplitSingleBlock(const BlockInfo & BI,bool SingleInstrs) const1225*9880d681SAndroid Build Coastguard Worker bool SplitAnalysis::shouldSplitSingleBlock(const BlockInfo &BI,
1226*9880d681SAndroid Build Coastguard Worker bool SingleInstrs) const {
1227*9880d681SAndroid Build Coastguard Worker // Always split for multiple instructions.
1228*9880d681SAndroid Build Coastguard Worker if (!BI.isOneInstr())
1229*9880d681SAndroid Build Coastguard Worker return true;
1230*9880d681SAndroid Build Coastguard Worker // Don't split for single instructions unless explicitly requested.
1231*9880d681SAndroid Build Coastguard Worker if (!SingleInstrs)
1232*9880d681SAndroid Build Coastguard Worker return false;
1233*9880d681SAndroid Build Coastguard Worker // Splitting a live-through range always makes progress.
1234*9880d681SAndroid Build Coastguard Worker if (BI.LiveIn && BI.LiveOut)
1235*9880d681SAndroid Build Coastguard Worker return true;
1236*9880d681SAndroid Build Coastguard Worker // No point in isolating a copy. It has no register class constraints.
1237*9880d681SAndroid Build Coastguard Worker if (LIS.getInstructionFromIndex(BI.FirstInstr)->isCopyLike())
1238*9880d681SAndroid Build Coastguard Worker return false;
1239*9880d681SAndroid Build Coastguard Worker // Finally, don't isolate an end point that was created by earlier splits.
1240*9880d681SAndroid Build Coastguard Worker return isOriginalEndpoint(BI.FirstInstr);
1241*9880d681SAndroid Build Coastguard Worker }
1242*9880d681SAndroid Build Coastguard Worker
splitSingleBlock(const SplitAnalysis::BlockInfo & BI)1243*9880d681SAndroid Build Coastguard Worker void SplitEditor::splitSingleBlock(const SplitAnalysis::BlockInfo &BI) {
1244*9880d681SAndroid Build Coastguard Worker openIntv();
1245*9880d681SAndroid Build Coastguard Worker SlotIndex LastSplitPoint = SA.getLastSplitPoint(BI.MBB->getNumber());
1246*9880d681SAndroid Build Coastguard Worker SlotIndex SegStart = enterIntvBefore(std::min(BI.FirstInstr,
1247*9880d681SAndroid Build Coastguard Worker LastSplitPoint));
1248*9880d681SAndroid Build Coastguard Worker if (!BI.LiveOut || BI.LastInstr < LastSplitPoint) {
1249*9880d681SAndroid Build Coastguard Worker useIntv(SegStart, leaveIntvAfter(BI.LastInstr));
1250*9880d681SAndroid Build Coastguard Worker } else {
1251*9880d681SAndroid Build Coastguard Worker // The last use is after the last valid split point.
1252*9880d681SAndroid Build Coastguard Worker SlotIndex SegStop = leaveIntvBefore(LastSplitPoint);
1253*9880d681SAndroid Build Coastguard Worker useIntv(SegStart, SegStop);
1254*9880d681SAndroid Build Coastguard Worker overlapIntv(SegStop, BI.LastInstr);
1255*9880d681SAndroid Build Coastguard Worker }
1256*9880d681SAndroid Build Coastguard Worker }
1257*9880d681SAndroid Build Coastguard Worker
1258*9880d681SAndroid Build Coastguard Worker
1259*9880d681SAndroid Build Coastguard Worker //===----------------------------------------------------------------------===//
1260*9880d681SAndroid Build Coastguard Worker // Global Live Range Splitting Support
1261*9880d681SAndroid Build Coastguard Worker //===----------------------------------------------------------------------===//
1262*9880d681SAndroid Build Coastguard Worker
1263*9880d681SAndroid Build Coastguard Worker // These methods support a method of global live range splitting that uses a
1264*9880d681SAndroid Build Coastguard Worker // global algorithm to decide intervals for CFG edges. They will insert split
1265*9880d681SAndroid Build Coastguard Worker // points and color intervals in basic blocks while avoiding interference.
1266*9880d681SAndroid Build Coastguard Worker //
1267*9880d681SAndroid Build Coastguard Worker // Note that splitSingleBlock is also useful for blocks where both CFG edges
1268*9880d681SAndroid Build Coastguard Worker // are on the stack.
1269*9880d681SAndroid Build Coastguard Worker
splitLiveThroughBlock(unsigned MBBNum,unsigned IntvIn,SlotIndex LeaveBefore,unsigned IntvOut,SlotIndex EnterAfter)1270*9880d681SAndroid Build Coastguard Worker void SplitEditor::splitLiveThroughBlock(unsigned MBBNum,
1271*9880d681SAndroid Build Coastguard Worker unsigned IntvIn, SlotIndex LeaveBefore,
1272*9880d681SAndroid Build Coastguard Worker unsigned IntvOut, SlotIndex EnterAfter){
1273*9880d681SAndroid Build Coastguard Worker SlotIndex Start, Stop;
1274*9880d681SAndroid Build Coastguard Worker std::tie(Start, Stop) = LIS.getSlotIndexes()->getMBBRange(MBBNum);
1275*9880d681SAndroid Build Coastguard Worker
1276*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << "BB#" << MBBNum << " [" << Start << ';' << Stop
1277*9880d681SAndroid Build Coastguard Worker << ") intf " << LeaveBefore << '-' << EnterAfter
1278*9880d681SAndroid Build Coastguard Worker << ", live-through " << IntvIn << " -> " << IntvOut);
1279*9880d681SAndroid Build Coastguard Worker
1280*9880d681SAndroid Build Coastguard Worker assert((IntvIn || IntvOut) && "Use splitSingleBlock for isolated blocks");
1281*9880d681SAndroid Build Coastguard Worker
1282*9880d681SAndroid Build Coastguard Worker assert((!LeaveBefore || LeaveBefore < Stop) && "Interference after block");
1283*9880d681SAndroid Build Coastguard Worker assert((!IntvIn || !LeaveBefore || LeaveBefore > Start) && "Impossible intf");
1284*9880d681SAndroid Build Coastguard Worker assert((!EnterAfter || EnterAfter >= Start) && "Interference before block");
1285*9880d681SAndroid Build Coastguard Worker
1286*9880d681SAndroid Build Coastguard Worker MachineBasicBlock *MBB = VRM.getMachineFunction().getBlockNumbered(MBBNum);
1287*9880d681SAndroid Build Coastguard Worker
1288*9880d681SAndroid Build Coastguard Worker if (!IntvOut) {
1289*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << ", spill on entry.\n");
1290*9880d681SAndroid Build Coastguard Worker //
1291*9880d681SAndroid Build Coastguard Worker // <<<<<<<<< Possible LeaveBefore interference.
1292*9880d681SAndroid Build Coastguard Worker // |-----------| Live through.
1293*9880d681SAndroid Build Coastguard Worker // -____________ Spill on entry.
1294*9880d681SAndroid Build Coastguard Worker //
1295*9880d681SAndroid Build Coastguard Worker selectIntv(IntvIn);
1296*9880d681SAndroid Build Coastguard Worker SlotIndex Idx = leaveIntvAtTop(*MBB);
1297*9880d681SAndroid Build Coastguard Worker assert((!LeaveBefore || Idx <= LeaveBefore) && "Interference");
1298*9880d681SAndroid Build Coastguard Worker (void)Idx;
1299*9880d681SAndroid Build Coastguard Worker return;
1300*9880d681SAndroid Build Coastguard Worker }
1301*9880d681SAndroid Build Coastguard Worker
1302*9880d681SAndroid Build Coastguard Worker if (!IntvIn) {
1303*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << ", reload on exit.\n");
1304*9880d681SAndroid Build Coastguard Worker //
1305*9880d681SAndroid Build Coastguard Worker // >>>>>>> Possible EnterAfter interference.
1306*9880d681SAndroid Build Coastguard Worker // |-----------| Live through.
1307*9880d681SAndroid Build Coastguard Worker // ___________-- Reload on exit.
1308*9880d681SAndroid Build Coastguard Worker //
1309*9880d681SAndroid Build Coastguard Worker selectIntv(IntvOut);
1310*9880d681SAndroid Build Coastguard Worker SlotIndex Idx = enterIntvAtEnd(*MBB);
1311*9880d681SAndroid Build Coastguard Worker assert((!EnterAfter || Idx >= EnterAfter) && "Interference");
1312*9880d681SAndroid Build Coastguard Worker (void)Idx;
1313*9880d681SAndroid Build Coastguard Worker return;
1314*9880d681SAndroid Build Coastguard Worker }
1315*9880d681SAndroid Build Coastguard Worker
1316*9880d681SAndroid Build Coastguard Worker if (IntvIn == IntvOut && !LeaveBefore && !EnterAfter) {
1317*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << ", straight through.\n");
1318*9880d681SAndroid Build Coastguard Worker //
1319*9880d681SAndroid Build Coastguard Worker // |-----------| Live through.
1320*9880d681SAndroid Build Coastguard Worker // ------------- Straight through, same intv, no interference.
1321*9880d681SAndroid Build Coastguard Worker //
1322*9880d681SAndroid Build Coastguard Worker selectIntv(IntvOut);
1323*9880d681SAndroid Build Coastguard Worker useIntv(Start, Stop);
1324*9880d681SAndroid Build Coastguard Worker return;
1325*9880d681SAndroid Build Coastguard Worker }
1326*9880d681SAndroid Build Coastguard Worker
1327*9880d681SAndroid Build Coastguard Worker // We cannot legally insert splits after LSP.
1328*9880d681SAndroid Build Coastguard Worker SlotIndex LSP = SA.getLastSplitPoint(MBBNum);
1329*9880d681SAndroid Build Coastguard Worker assert((!IntvOut || !EnterAfter || EnterAfter < LSP) && "Impossible intf");
1330*9880d681SAndroid Build Coastguard Worker
1331*9880d681SAndroid Build Coastguard Worker if (IntvIn != IntvOut && (!LeaveBefore || !EnterAfter ||
1332*9880d681SAndroid Build Coastguard Worker LeaveBefore.getBaseIndex() > EnterAfter.getBoundaryIndex())) {
1333*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << ", switch avoiding interference.\n");
1334*9880d681SAndroid Build Coastguard Worker //
1335*9880d681SAndroid Build Coastguard Worker // >>>> <<<< Non-overlapping EnterAfter/LeaveBefore interference.
1336*9880d681SAndroid Build Coastguard Worker // |-----------| Live through.
1337*9880d681SAndroid Build Coastguard Worker // ------======= Switch intervals between interference.
1338*9880d681SAndroid Build Coastguard Worker //
1339*9880d681SAndroid Build Coastguard Worker selectIntv(IntvOut);
1340*9880d681SAndroid Build Coastguard Worker SlotIndex Idx;
1341*9880d681SAndroid Build Coastguard Worker if (LeaveBefore && LeaveBefore < LSP) {
1342*9880d681SAndroid Build Coastguard Worker Idx = enterIntvBefore(LeaveBefore);
1343*9880d681SAndroid Build Coastguard Worker useIntv(Idx, Stop);
1344*9880d681SAndroid Build Coastguard Worker } else {
1345*9880d681SAndroid Build Coastguard Worker Idx = enterIntvAtEnd(*MBB);
1346*9880d681SAndroid Build Coastguard Worker }
1347*9880d681SAndroid Build Coastguard Worker selectIntv(IntvIn);
1348*9880d681SAndroid Build Coastguard Worker useIntv(Start, Idx);
1349*9880d681SAndroid Build Coastguard Worker assert((!LeaveBefore || Idx <= LeaveBefore) && "Interference");
1350*9880d681SAndroid Build Coastguard Worker assert((!EnterAfter || Idx >= EnterAfter) && "Interference");
1351*9880d681SAndroid Build Coastguard Worker return;
1352*9880d681SAndroid Build Coastguard Worker }
1353*9880d681SAndroid Build Coastguard Worker
1354*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << ", create local intv for interference.\n");
1355*9880d681SAndroid Build Coastguard Worker //
1356*9880d681SAndroid Build Coastguard Worker // >>><><><><<<< Overlapping EnterAfter/LeaveBefore interference.
1357*9880d681SAndroid Build Coastguard Worker // |-----------| Live through.
1358*9880d681SAndroid Build Coastguard Worker // ==---------== Switch intervals before/after interference.
1359*9880d681SAndroid Build Coastguard Worker //
1360*9880d681SAndroid Build Coastguard Worker assert(LeaveBefore <= EnterAfter && "Missed case");
1361*9880d681SAndroid Build Coastguard Worker
1362*9880d681SAndroid Build Coastguard Worker selectIntv(IntvOut);
1363*9880d681SAndroid Build Coastguard Worker SlotIndex Idx = enterIntvAfter(EnterAfter);
1364*9880d681SAndroid Build Coastguard Worker useIntv(Idx, Stop);
1365*9880d681SAndroid Build Coastguard Worker assert((!EnterAfter || Idx >= EnterAfter) && "Interference");
1366*9880d681SAndroid Build Coastguard Worker
1367*9880d681SAndroid Build Coastguard Worker selectIntv(IntvIn);
1368*9880d681SAndroid Build Coastguard Worker Idx = leaveIntvBefore(LeaveBefore);
1369*9880d681SAndroid Build Coastguard Worker useIntv(Start, Idx);
1370*9880d681SAndroid Build Coastguard Worker assert((!LeaveBefore || Idx <= LeaveBefore) && "Interference");
1371*9880d681SAndroid Build Coastguard Worker }
1372*9880d681SAndroid Build Coastguard Worker
1373*9880d681SAndroid Build Coastguard Worker
splitRegInBlock(const SplitAnalysis::BlockInfo & BI,unsigned IntvIn,SlotIndex LeaveBefore)1374*9880d681SAndroid Build Coastguard Worker void SplitEditor::splitRegInBlock(const SplitAnalysis::BlockInfo &BI,
1375*9880d681SAndroid Build Coastguard Worker unsigned IntvIn, SlotIndex LeaveBefore) {
1376*9880d681SAndroid Build Coastguard Worker SlotIndex Start, Stop;
1377*9880d681SAndroid Build Coastguard Worker std::tie(Start, Stop) = LIS.getSlotIndexes()->getMBBRange(BI.MBB);
1378*9880d681SAndroid Build Coastguard Worker
1379*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << "BB#" << BI.MBB->getNumber() << " [" << Start << ';' << Stop
1380*9880d681SAndroid Build Coastguard Worker << "), uses " << BI.FirstInstr << '-' << BI.LastInstr
1381*9880d681SAndroid Build Coastguard Worker << ", reg-in " << IntvIn << ", leave before " << LeaveBefore
1382*9880d681SAndroid Build Coastguard Worker << (BI.LiveOut ? ", stack-out" : ", killed in block"));
1383*9880d681SAndroid Build Coastguard Worker
1384*9880d681SAndroid Build Coastguard Worker assert(IntvIn && "Must have register in");
1385*9880d681SAndroid Build Coastguard Worker assert(BI.LiveIn && "Must be live-in");
1386*9880d681SAndroid Build Coastguard Worker assert((!LeaveBefore || LeaveBefore > Start) && "Bad interference");
1387*9880d681SAndroid Build Coastguard Worker
1388*9880d681SAndroid Build Coastguard Worker if (!BI.LiveOut && (!LeaveBefore || LeaveBefore >= BI.LastInstr)) {
1389*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << " before interference.\n");
1390*9880d681SAndroid Build Coastguard Worker //
1391*9880d681SAndroid Build Coastguard Worker // <<< Interference after kill.
1392*9880d681SAndroid Build Coastguard Worker // |---o---x | Killed in block.
1393*9880d681SAndroid Build Coastguard Worker // ========= Use IntvIn everywhere.
1394*9880d681SAndroid Build Coastguard Worker //
1395*9880d681SAndroid Build Coastguard Worker selectIntv(IntvIn);
1396*9880d681SAndroid Build Coastguard Worker useIntv(Start, BI.LastInstr);
1397*9880d681SAndroid Build Coastguard Worker return;
1398*9880d681SAndroid Build Coastguard Worker }
1399*9880d681SAndroid Build Coastguard Worker
1400*9880d681SAndroid Build Coastguard Worker SlotIndex LSP = SA.getLastSplitPoint(BI.MBB->getNumber());
1401*9880d681SAndroid Build Coastguard Worker
1402*9880d681SAndroid Build Coastguard Worker if (!LeaveBefore || LeaveBefore > BI.LastInstr.getBoundaryIndex()) {
1403*9880d681SAndroid Build Coastguard Worker //
1404*9880d681SAndroid Build Coastguard Worker // <<< Possible interference after last use.
1405*9880d681SAndroid Build Coastguard Worker // |---o---o---| Live-out on stack.
1406*9880d681SAndroid Build Coastguard Worker // =========____ Leave IntvIn after last use.
1407*9880d681SAndroid Build Coastguard Worker //
1408*9880d681SAndroid Build Coastguard Worker // < Interference after last use.
1409*9880d681SAndroid Build Coastguard Worker // |---o---o--o| Live-out on stack, late last use.
1410*9880d681SAndroid Build Coastguard Worker // ============ Copy to stack after LSP, overlap IntvIn.
1411*9880d681SAndroid Build Coastguard Worker // \_____ Stack interval is live-out.
1412*9880d681SAndroid Build Coastguard Worker //
1413*9880d681SAndroid Build Coastguard Worker if (BI.LastInstr < LSP) {
1414*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << ", spill after last use before interference.\n");
1415*9880d681SAndroid Build Coastguard Worker selectIntv(IntvIn);
1416*9880d681SAndroid Build Coastguard Worker SlotIndex Idx = leaveIntvAfter(BI.LastInstr);
1417*9880d681SAndroid Build Coastguard Worker useIntv(Start, Idx);
1418*9880d681SAndroid Build Coastguard Worker assert((!LeaveBefore || Idx <= LeaveBefore) && "Interference");
1419*9880d681SAndroid Build Coastguard Worker } else {
1420*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << ", spill before last split point.\n");
1421*9880d681SAndroid Build Coastguard Worker selectIntv(IntvIn);
1422*9880d681SAndroid Build Coastguard Worker SlotIndex Idx = leaveIntvBefore(LSP);
1423*9880d681SAndroid Build Coastguard Worker overlapIntv(Idx, BI.LastInstr);
1424*9880d681SAndroid Build Coastguard Worker useIntv(Start, Idx);
1425*9880d681SAndroid Build Coastguard Worker assert((!LeaveBefore || Idx <= LeaveBefore) && "Interference");
1426*9880d681SAndroid Build Coastguard Worker }
1427*9880d681SAndroid Build Coastguard Worker return;
1428*9880d681SAndroid Build Coastguard Worker }
1429*9880d681SAndroid Build Coastguard Worker
1430*9880d681SAndroid Build Coastguard Worker // The interference is overlapping somewhere we wanted to use IntvIn. That
1431*9880d681SAndroid Build Coastguard Worker // means we need to create a local interval that can be allocated a
1432*9880d681SAndroid Build Coastguard Worker // different register.
1433*9880d681SAndroid Build Coastguard Worker unsigned LocalIntv = openIntv();
1434*9880d681SAndroid Build Coastguard Worker (void)LocalIntv;
1435*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << ", creating local interval " << LocalIntv << ".\n");
1436*9880d681SAndroid Build Coastguard Worker
1437*9880d681SAndroid Build Coastguard Worker if (!BI.LiveOut || BI.LastInstr < LSP) {
1438*9880d681SAndroid Build Coastguard Worker //
1439*9880d681SAndroid Build Coastguard Worker // <<<<<<< Interference overlapping uses.
1440*9880d681SAndroid Build Coastguard Worker // |---o---o---| Live-out on stack.
1441*9880d681SAndroid Build Coastguard Worker // =====----____ Leave IntvIn before interference, then spill.
1442*9880d681SAndroid Build Coastguard Worker //
1443*9880d681SAndroid Build Coastguard Worker SlotIndex To = leaveIntvAfter(BI.LastInstr);
1444*9880d681SAndroid Build Coastguard Worker SlotIndex From = enterIntvBefore(LeaveBefore);
1445*9880d681SAndroid Build Coastguard Worker useIntv(From, To);
1446*9880d681SAndroid Build Coastguard Worker selectIntv(IntvIn);
1447*9880d681SAndroid Build Coastguard Worker useIntv(Start, From);
1448*9880d681SAndroid Build Coastguard Worker assert((!LeaveBefore || From <= LeaveBefore) && "Interference");
1449*9880d681SAndroid Build Coastguard Worker return;
1450*9880d681SAndroid Build Coastguard Worker }
1451*9880d681SAndroid Build Coastguard Worker
1452*9880d681SAndroid Build Coastguard Worker // <<<<<<< Interference overlapping uses.
1453*9880d681SAndroid Build Coastguard Worker // |---o---o--o| Live-out on stack, late last use.
1454*9880d681SAndroid Build Coastguard Worker // =====------- Copy to stack before LSP, overlap LocalIntv.
1455*9880d681SAndroid Build Coastguard Worker // \_____ Stack interval is live-out.
1456*9880d681SAndroid Build Coastguard Worker //
1457*9880d681SAndroid Build Coastguard Worker SlotIndex To = leaveIntvBefore(LSP);
1458*9880d681SAndroid Build Coastguard Worker overlapIntv(To, BI.LastInstr);
1459*9880d681SAndroid Build Coastguard Worker SlotIndex From = enterIntvBefore(std::min(To, LeaveBefore));
1460*9880d681SAndroid Build Coastguard Worker useIntv(From, To);
1461*9880d681SAndroid Build Coastguard Worker selectIntv(IntvIn);
1462*9880d681SAndroid Build Coastguard Worker useIntv(Start, From);
1463*9880d681SAndroid Build Coastguard Worker assert((!LeaveBefore || From <= LeaveBefore) && "Interference");
1464*9880d681SAndroid Build Coastguard Worker }
1465*9880d681SAndroid Build Coastguard Worker
splitRegOutBlock(const SplitAnalysis::BlockInfo & BI,unsigned IntvOut,SlotIndex EnterAfter)1466*9880d681SAndroid Build Coastguard Worker void SplitEditor::splitRegOutBlock(const SplitAnalysis::BlockInfo &BI,
1467*9880d681SAndroid Build Coastguard Worker unsigned IntvOut, SlotIndex EnterAfter) {
1468*9880d681SAndroid Build Coastguard Worker SlotIndex Start, Stop;
1469*9880d681SAndroid Build Coastguard Worker std::tie(Start, Stop) = LIS.getSlotIndexes()->getMBBRange(BI.MBB);
1470*9880d681SAndroid Build Coastguard Worker
1471*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << "BB#" << BI.MBB->getNumber() << " [" << Start << ';' << Stop
1472*9880d681SAndroid Build Coastguard Worker << "), uses " << BI.FirstInstr << '-' << BI.LastInstr
1473*9880d681SAndroid Build Coastguard Worker << ", reg-out " << IntvOut << ", enter after " << EnterAfter
1474*9880d681SAndroid Build Coastguard Worker << (BI.LiveIn ? ", stack-in" : ", defined in block"));
1475*9880d681SAndroid Build Coastguard Worker
1476*9880d681SAndroid Build Coastguard Worker SlotIndex LSP = SA.getLastSplitPoint(BI.MBB->getNumber());
1477*9880d681SAndroid Build Coastguard Worker
1478*9880d681SAndroid Build Coastguard Worker assert(IntvOut && "Must have register out");
1479*9880d681SAndroid Build Coastguard Worker assert(BI.LiveOut && "Must be live-out");
1480*9880d681SAndroid Build Coastguard Worker assert((!EnterAfter || EnterAfter < LSP) && "Bad interference");
1481*9880d681SAndroid Build Coastguard Worker
1482*9880d681SAndroid Build Coastguard Worker if (!BI.LiveIn && (!EnterAfter || EnterAfter <= BI.FirstInstr)) {
1483*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << " after interference.\n");
1484*9880d681SAndroid Build Coastguard Worker //
1485*9880d681SAndroid Build Coastguard Worker // >>>> Interference before def.
1486*9880d681SAndroid Build Coastguard Worker // | o---o---| Defined in block.
1487*9880d681SAndroid Build Coastguard Worker // ========= Use IntvOut everywhere.
1488*9880d681SAndroid Build Coastguard Worker //
1489*9880d681SAndroid Build Coastguard Worker selectIntv(IntvOut);
1490*9880d681SAndroid Build Coastguard Worker useIntv(BI.FirstInstr, Stop);
1491*9880d681SAndroid Build Coastguard Worker return;
1492*9880d681SAndroid Build Coastguard Worker }
1493*9880d681SAndroid Build Coastguard Worker
1494*9880d681SAndroid Build Coastguard Worker if (!EnterAfter || EnterAfter < BI.FirstInstr.getBaseIndex()) {
1495*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << ", reload after interference.\n");
1496*9880d681SAndroid Build Coastguard Worker //
1497*9880d681SAndroid Build Coastguard Worker // >>>> Interference before def.
1498*9880d681SAndroid Build Coastguard Worker // |---o---o---| Live-through, stack-in.
1499*9880d681SAndroid Build Coastguard Worker // ____========= Enter IntvOut before first use.
1500*9880d681SAndroid Build Coastguard Worker //
1501*9880d681SAndroid Build Coastguard Worker selectIntv(IntvOut);
1502*9880d681SAndroid Build Coastguard Worker SlotIndex Idx = enterIntvBefore(std::min(LSP, BI.FirstInstr));
1503*9880d681SAndroid Build Coastguard Worker useIntv(Idx, Stop);
1504*9880d681SAndroid Build Coastguard Worker assert((!EnterAfter || Idx >= EnterAfter) && "Interference");
1505*9880d681SAndroid Build Coastguard Worker return;
1506*9880d681SAndroid Build Coastguard Worker }
1507*9880d681SAndroid Build Coastguard Worker
1508*9880d681SAndroid Build Coastguard Worker // The interference is overlapping somewhere we wanted to use IntvOut. That
1509*9880d681SAndroid Build Coastguard Worker // means we need to create a local interval that can be allocated a
1510*9880d681SAndroid Build Coastguard Worker // different register.
1511*9880d681SAndroid Build Coastguard Worker DEBUG(dbgs() << ", interference overlaps uses.\n");
1512*9880d681SAndroid Build Coastguard Worker //
1513*9880d681SAndroid Build Coastguard Worker // >>>>>>> Interference overlapping uses.
1514*9880d681SAndroid Build Coastguard Worker // |---o---o---| Live-through, stack-in.
1515*9880d681SAndroid Build Coastguard Worker // ____---====== Create local interval for interference range.
1516*9880d681SAndroid Build Coastguard Worker //
1517*9880d681SAndroid Build Coastguard Worker selectIntv(IntvOut);
1518*9880d681SAndroid Build Coastguard Worker SlotIndex Idx = enterIntvAfter(EnterAfter);
1519*9880d681SAndroid Build Coastguard Worker useIntv(Idx, Stop);
1520*9880d681SAndroid Build Coastguard Worker assert((!EnterAfter || Idx >= EnterAfter) && "Interference");
1521*9880d681SAndroid Build Coastguard Worker
1522*9880d681SAndroid Build Coastguard Worker openIntv();
1523*9880d681SAndroid Build Coastguard Worker SlotIndex From = enterIntvBefore(std::min(Idx, BI.FirstInstr));
1524*9880d681SAndroid Build Coastguard Worker useIntv(From, Idx);
1525*9880d681SAndroid Build Coastguard Worker }
1526