| Jakob Stoklund Olesen | 8ae0263 | 2010-07-20 15:41:07 +0000 | [diff] [blame] | 1 | //===---------- SplitKit.cpp - Toolkit for splitting live ranges ----------===// | 
|  | 2 | // | 
|  | 3 | //                     The LLVM Compiler Infrastructure | 
|  | 4 | // | 
|  | 5 | // This file is distributed under the University of Illinois Open Source | 
|  | 6 | // License. See LICENSE.TXT for details. | 
|  | 7 | // | 
|  | 8 | //===----------------------------------------------------------------------===// | 
|  | 9 | // | 
|  | 10 | // This file contains the SplitAnalysis class as well as mutator functions for | 
|  | 11 | // live range splitting. | 
|  | 12 | // | 
|  | 13 | //===----------------------------------------------------------------------===// | 
|  | 14 |  | 
| Jakob Stoklund Olesen | 376dcbd | 2010-11-03 20:39:23 +0000 | [diff] [blame] | 15 | #define DEBUG_TYPE "regalloc" | 
| Jakob Stoklund Olesen | 8ae0263 | 2010-07-20 15:41:07 +0000 | [diff] [blame] | 16 | #include "SplitKit.h" | 
| Jakob Stoklund Olesen | a17768f | 2010-10-14 23:49:52 +0000 | [diff] [blame] | 17 | #include "LiveRangeEdit.h" | 
| Jakob Stoklund Olesen | f017900 | 2010-07-26 23:44:11 +0000 | [diff] [blame] | 18 | #include "VirtRegMap.h" | 
| Jakob Stoklund Olesen | 4670353 | 2011-03-02 23:05:19 +0000 | [diff] [blame] | 19 | #include "llvm/ADT/Statistic.h" | 
| Jakob Stoklund Olesen | 08e93b1 | 2010-08-10 17:07:22 +0000 | [diff] [blame] | 20 | #include "llvm/CodeGen/CalcSpillWeights.h" | 
| Jakob Stoklund Olesen | 8ae0263 | 2010-07-20 15:41:07 +0000 | [diff] [blame] | 21 | #include "llvm/CodeGen/LiveIntervalAnalysis.h" | 
| Jakob Stoklund Olesen | d68f458 | 2010-10-28 20:34:50 +0000 | [diff] [blame] | 22 | #include "llvm/CodeGen/MachineDominators.h" | 
| Jakob Stoklund Olesen | f017900 | 2010-07-26 23:44:11 +0000 | [diff] [blame] | 23 | #include "llvm/CodeGen/MachineInstrBuilder.h" | 
| Jakob Stoklund Olesen | 8ae0263 | 2010-07-20 15:41:07 +0000 | [diff] [blame] | 24 | #include "llvm/CodeGen/MachineRegisterInfo.h" | 
| Jakob Stoklund Olesen | 6a0dc07 | 2010-07-20 21:46:58 +0000 | [diff] [blame] | 25 | #include "llvm/Support/CommandLine.h" | 
| Jakob Stoklund Olesen | 8ae0263 | 2010-07-20 15:41:07 +0000 | [diff] [blame] | 26 | #include "llvm/Support/Debug.h" | 
|  | 27 | #include "llvm/Support/raw_ostream.h" | 
| Jakob Stoklund Olesen | 6a0dc07 | 2010-07-20 21:46:58 +0000 | [diff] [blame] | 28 | #include "llvm/Target/TargetInstrInfo.h" | 
|  | 29 | #include "llvm/Target/TargetMachine.h" | 
| Jakob Stoklund Olesen | 8ae0263 | 2010-07-20 15:41:07 +0000 | [diff] [blame] | 30 |  | 
|  | 31 | using namespace llvm; | 
|  | 32 |  | 
| Jakob Stoklund Olesen | 6a0dc07 | 2010-07-20 21:46:58 +0000 | [diff] [blame] | 33 | static cl::opt<bool> | 
|  | 34 | AllowSplit("spiller-splits-edges", | 
|  | 35 | cl::desc("Allow critical edge splitting during spilling")); | 
| Jakob Stoklund Olesen | 8ae0263 | 2010-07-20 15:41:07 +0000 | [diff] [blame] | 36 |  | 
| Jakob Stoklund Olesen | 4670353 | 2011-03-02 23:05:19 +0000 | [diff] [blame] | 37 | STATISTIC(NumFinished, "Number of splits finished"); | 
|  | 38 | STATISTIC(NumSimple,   "Number of splits that were simple"); | 
|  | 39 |  | 
| Jakob Stoklund Olesen | 8ae0263 | 2010-07-20 15:41:07 +0000 | [diff] [blame] | 40 | //===----------------------------------------------------------------------===// | 
|  | 41 | //                                 Split Analysis | 
|  | 42 | //===----------------------------------------------------------------------===// | 
|  | 43 |  | 
| Jakob Stoklund Olesen | 1b847de | 2011-02-19 00:53:42 +0000 | [diff] [blame] | 44 | SplitAnalysis::SplitAnalysis(const VirtRegMap &vrm, | 
| Jakob Stoklund Olesen | f2c6e36 | 2010-07-20 23:50:15 +0000 | [diff] [blame] | 45 | const LiveIntervals &lis, | 
|  | 46 | const MachineLoopInfo &mli) | 
| Jakob Stoklund Olesen | 1b847de | 2011-02-19 00:53:42 +0000 | [diff] [blame] | 47 | : MF(vrm.getMachineFunction()), | 
|  | 48 | VRM(vrm), | 
| Jakob Stoklund Olesen | 0786284 | 2011-01-26 00:50:53 +0000 | [diff] [blame] | 49 | LIS(lis), | 
|  | 50 | Loops(mli), | 
| Jakob Stoklund Olesen | 1b847de | 2011-02-19 00:53:42 +0000 | [diff] [blame] | 51 | TII(*MF.getTarget().getInstrInfo()), | 
| Jakob Stoklund Olesen | 0786284 | 2011-01-26 00:50:53 +0000 | [diff] [blame] | 52 | CurLI(0) {} | 
| Jakob Stoklund Olesen | 8ae0263 | 2010-07-20 15:41:07 +0000 | [diff] [blame] | 53 |  | 
|  | 54 | void SplitAnalysis::clear() { | 
| Jakob Stoklund Olesen | b5fa933 | 2011-01-18 21:13:27 +0000 | [diff] [blame] | 55 | UseSlots.clear(); | 
| Jakob Stoklund Olesen | 0786284 | 2011-01-26 00:50:53 +0000 | [diff] [blame] | 56 | UsingInstrs.clear(); | 
|  | 57 | UsingBlocks.clear(); | 
| Jakob Stoklund Olesen | f0ac26c | 2011-02-09 22:50:26 +0000 | [diff] [blame] | 58 | LiveBlocks.clear(); | 
| Jakob Stoklund Olesen | 0786284 | 2011-01-26 00:50:53 +0000 | [diff] [blame] | 59 | CurLI = 0; | 
| Jakob Stoklund Olesen | 8ae0263 | 2010-07-20 15:41:07 +0000 | [diff] [blame] | 60 | } | 
|  | 61 |  | 
| Jakob Stoklund Olesen | 6a0dc07 | 2010-07-20 21:46:58 +0000 | [diff] [blame] | 62 | bool SplitAnalysis::canAnalyzeBranch(const MachineBasicBlock *MBB) { | 
|  | 63 | MachineBasicBlock *T, *F; | 
|  | 64 | SmallVector<MachineOperand, 4> Cond; | 
| Jakob Stoklund Olesen | 0786284 | 2011-01-26 00:50:53 +0000 | [diff] [blame] | 65 | return !TII.AnalyzeBranch(const_cast<MachineBasicBlock&>(*MBB), T, F, Cond); | 
| Jakob Stoklund Olesen | 6a0dc07 | 2010-07-20 21:46:58 +0000 | [diff] [blame] | 66 | } | 
|  | 67 |  | 
| Jakob Stoklund Olesen | 0786284 | 2011-01-26 00:50:53 +0000 | [diff] [blame] | 68 | /// analyzeUses - Count instructions, basic blocks, and loops using CurLI. | 
| Jakob Stoklund Olesen | abff280 | 2010-07-20 16:12:37 +0000 | [diff] [blame] | 69 | void SplitAnalysis::analyzeUses() { | 
| Jakob Stoklund Olesen | 0786284 | 2011-01-26 00:50:53 +0000 | [diff] [blame] | 70 | const MachineRegisterInfo &MRI = MF.getRegInfo(); | 
| Jakob Stoklund Olesen | a372d16 | 2011-02-09 21:52:09 +0000 | [diff] [blame] | 71 | for (MachineRegisterInfo::reg_iterator I = MRI.reg_begin(CurLI->reg), | 
|  | 72 | E = MRI.reg_end(); I != E; ++I) { | 
|  | 73 | MachineOperand &MO = I.getOperand(); | 
|  | 74 | if (MO.isUse() && MO.isUndef()) | 
|  | 75 | continue; | 
|  | 76 | MachineInstr *MI = MO.getParent(); | 
| Jakob Stoklund Olesen | 0786284 | 2011-01-26 00:50:53 +0000 | [diff] [blame] | 77 | if (MI->isDebugValue() || !UsingInstrs.insert(MI)) | 
| Jakob Stoklund Olesen | 8ae0263 | 2010-07-20 15:41:07 +0000 | [diff] [blame] | 78 | continue; | 
| Jakob Stoklund Olesen | 0786284 | 2011-01-26 00:50:53 +0000 | [diff] [blame] | 79 | UseSlots.push_back(LIS.getInstructionIndex(MI).getDefIndex()); | 
| Jakob Stoklund Olesen | 8ae0263 | 2010-07-20 15:41:07 +0000 | [diff] [blame] | 80 | MachineBasicBlock *MBB = MI->getParent(); | 
| Jakob Stoklund Olesen | 4f5c9d2 | 2011-02-09 23:56:18 +0000 | [diff] [blame] | 81 | UsingBlocks[MBB]++; | 
| Jakob Stoklund Olesen | 8ae0263 | 2010-07-20 15:41:07 +0000 | [diff] [blame] | 82 | } | 
| Jakob Stoklund Olesen | b5fa933 | 2011-01-18 21:13:27 +0000 | [diff] [blame] | 83 | array_pod_sort(UseSlots.begin(), UseSlots.end()); | 
| Jakob Stoklund Olesen | f0ac26c | 2011-02-09 22:50:26 +0000 | [diff] [blame] | 84 | calcLiveBlockInfo(); | 
| Jakob Stoklund Olesen | e1f543f | 2010-08-12 18:50:55 +0000 | [diff] [blame] | 85 | DEBUG(dbgs() << "  counted " | 
| Jakob Stoklund Olesen | 0786284 | 2011-01-26 00:50:53 +0000 | [diff] [blame] | 86 | << UsingInstrs.size() << " instrs, " | 
| Jakob Stoklund Olesen | 4f5c9d2 | 2011-02-09 23:56:18 +0000 | [diff] [blame] | 87 | << UsingBlocks.size() << " blocks.\n"); | 
| Jakob Stoklund Olesen | 8ae0263 | 2010-07-20 15:41:07 +0000 | [diff] [blame] | 88 | } | 
|  | 89 |  | 
| Jakob Stoklund Olesen | f0ac26c | 2011-02-09 22:50:26 +0000 | [diff] [blame] | 90 | /// calcLiveBlockInfo - Fill the LiveBlocks array with information about blocks | 
|  | 91 | /// where CurLI is live. | 
|  | 92 | void SplitAnalysis::calcLiveBlockInfo() { | 
|  | 93 | if (CurLI->empty()) | 
|  | 94 | return; | 
|  | 95 |  | 
|  | 96 | LiveInterval::const_iterator LVI = CurLI->begin(); | 
|  | 97 | LiveInterval::const_iterator LVE = CurLI->end(); | 
|  | 98 |  | 
|  | 99 | SmallVectorImpl<SlotIndex>::const_iterator UseI, UseE; | 
|  | 100 | UseI = UseSlots.begin(); | 
|  | 101 | UseE = UseSlots.end(); | 
|  | 102 |  | 
|  | 103 | // Loop over basic blocks where CurLI is live. | 
|  | 104 | MachineFunction::iterator MFI = LIS.getMBBFromIndex(LVI->start); | 
|  | 105 | for (;;) { | 
|  | 106 | BlockInfo BI; | 
|  | 107 | BI.MBB = MFI; | 
| Jakob Stoklund Olesen | 36d6186 | 2011-03-03 03:41:29 +0000 | [diff] [blame] | 108 | tie(BI.Start, BI.Stop) = LIS.getSlotIndexes()->getMBBRange(BI.MBB); | 
| Jakob Stoklund Olesen | f0ac26c | 2011-02-09 22:50:26 +0000 | [diff] [blame] | 109 |  | 
|  | 110 | // The last split point is the latest possible insertion point that dominates | 
|  | 111 | // all successor blocks. If interference reaches LastSplitPoint, it is not | 
|  | 112 | // possible to insert a split or reload that makes CurLI live in the | 
|  | 113 | // outgoing bundle. | 
|  | 114 | MachineBasicBlock::iterator LSP = LIS.getLastSplitPoint(*CurLI, BI.MBB); | 
|  | 115 | if (LSP == BI.MBB->end()) | 
| Jakob Stoklund Olesen | 36d6186 | 2011-03-03 03:41:29 +0000 | [diff] [blame] | 116 | BI.LastSplitPoint = BI.Stop; | 
| Jakob Stoklund Olesen | f0ac26c | 2011-02-09 22:50:26 +0000 | [diff] [blame] | 117 | else | 
|  | 118 | BI.LastSplitPoint = LIS.getInstructionIndex(LSP); | 
|  | 119 |  | 
|  | 120 | // LVI is the first live segment overlapping MBB. | 
| Jakob Stoklund Olesen | 36d6186 | 2011-03-03 03:41:29 +0000 | [diff] [blame] | 121 | BI.LiveIn = LVI->start <= BI.Start; | 
| Jakob Stoklund Olesen | f0ac26c | 2011-02-09 22:50:26 +0000 | [diff] [blame] | 122 | if (!BI.LiveIn) | 
|  | 123 | BI.Def = LVI->start; | 
|  | 124 |  | 
|  | 125 | // Find the first and last uses in the block. | 
|  | 126 | BI.Uses = hasUses(MFI); | 
|  | 127 | if (BI.Uses && UseI != UseE) { | 
|  | 128 | BI.FirstUse = *UseI; | 
| Jakob Stoklund Olesen | 36d6186 | 2011-03-03 03:41:29 +0000 | [diff] [blame] | 129 | assert(BI.FirstUse >= BI.Start); | 
| Jakob Stoklund Olesen | f0ac26c | 2011-02-09 22:50:26 +0000 | [diff] [blame] | 130 | do ++UseI; | 
| Jakob Stoklund Olesen | 36d6186 | 2011-03-03 03:41:29 +0000 | [diff] [blame] | 131 | while (UseI != UseE && *UseI < BI.Stop); | 
| Jakob Stoklund Olesen | f0ac26c | 2011-02-09 22:50:26 +0000 | [diff] [blame] | 132 | BI.LastUse = UseI[-1]; | 
| Jakob Stoklund Olesen | 36d6186 | 2011-03-03 03:41:29 +0000 | [diff] [blame] | 133 | assert(BI.LastUse < BI.Stop); | 
| Jakob Stoklund Olesen | f0ac26c | 2011-02-09 22:50:26 +0000 | [diff] [blame] | 134 | } | 
|  | 135 |  | 
|  | 136 | // Look for gaps in the live range. | 
|  | 137 | bool hasGap = false; | 
|  | 138 | BI.LiveOut = true; | 
| Jakob Stoklund Olesen | 36d6186 | 2011-03-03 03:41:29 +0000 | [diff] [blame] | 139 | while (LVI->end < BI.Stop) { | 
| Jakob Stoklund Olesen | f0ac26c | 2011-02-09 22:50:26 +0000 | [diff] [blame] | 140 | SlotIndex LastStop = LVI->end; | 
| Jakob Stoklund Olesen | 36d6186 | 2011-03-03 03:41:29 +0000 | [diff] [blame] | 141 | if (++LVI == LVE || LVI->start >= BI.Stop) { | 
| Jakob Stoklund Olesen | f0ac26c | 2011-02-09 22:50:26 +0000 | [diff] [blame] | 142 | BI.Kill = LastStop; | 
|  | 143 | BI.LiveOut = false; | 
|  | 144 | break; | 
|  | 145 | } | 
|  | 146 | if (LastStop < LVI->start) { | 
|  | 147 | hasGap = true; | 
|  | 148 | BI.Kill = LastStop; | 
|  | 149 | BI.Def = LVI->start; | 
|  | 150 | } | 
|  | 151 | } | 
|  | 152 |  | 
|  | 153 | // Don't set LiveThrough when the block has a gap. | 
|  | 154 | BI.LiveThrough = !hasGap && BI.LiveIn && BI.LiveOut; | 
|  | 155 | LiveBlocks.push_back(BI); | 
|  | 156 |  | 
|  | 157 | // LVI is now at LVE or LVI->end >= Stop. | 
|  | 158 | if (LVI == LVE) | 
|  | 159 | break; | 
|  | 160 |  | 
|  | 161 | // Live segment ends exactly at Stop. Move to the next segment. | 
| Jakob Stoklund Olesen | 36d6186 | 2011-03-03 03:41:29 +0000 | [diff] [blame] | 162 | if (LVI->end == BI.Stop && ++LVI == LVE) | 
| Jakob Stoklund Olesen | f0ac26c | 2011-02-09 22:50:26 +0000 | [diff] [blame] | 163 | break; | 
|  | 164 |  | 
|  | 165 | // Pick the next basic block. | 
| Jakob Stoklund Olesen | 36d6186 | 2011-03-03 03:41:29 +0000 | [diff] [blame] | 166 | if (LVI->start < BI.Stop) | 
| Jakob Stoklund Olesen | f0ac26c | 2011-02-09 22:50:26 +0000 | [diff] [blame] | 167 | ++MFI; | 
|  | 168 | else | 
|  | 169 | MFI = LIS.getMBBFromIndex(LVI->start); | 
|  | 170 | } | 
|  | 171 | } | 
|  | 172 |  | 
| Jakob Stoklund Olesen | 06c0f25 | 2011-02-21 23:09:46 +0000 | [diff] [blame] | 173 | bool SplitAnalysis::isOriginalEndpoint(SlotIndex Idx) const { | 
|  | 174 | unsigned OrigReg = VRM.getOriginal(CurLI->reg); | 
|  | 175 | const LiveInterval &Orig = LIS.getInterval(OrigReg); | 
|  | 176 | assert(!Orig.empty() && "Splitting empty interval?"); | 
|  | 177 | LiveInterval::const_iterator I = Orig.find(Idx); | 
|  | 178 |  | 
|  | 179 | // Range containing Idx should begin at Idx. | 
|  | 180 | if (I != Orig.end() && I->start <= Idx) | 
|  | 181 | return I->start == Idx; | 
|  | 182 |  | 
|  | 183 | // Range does not contain Idx, previous must end at Idx. | 
|  | 184 | return I != Orig.begin() && (--I)->end == Idx; | 
|  | 185 | } | 
|  | 186 |  | 
| Jakob Stoklund Olesen | 532de3d | 2010-10-22 20:28:21 +0000 | [diff] [blame] | 187 | void SplitAnalysis::print(const BlockPtrSet &B, raw_ostream &OS) const { | 
|  | 188 | for (BlockPtrSet::const_iterator I = B.begin(), E = B.end(); I != E; ++I) { | 
| Jakob Stoklund Olesen | 0786284 | 2011-01-26 00:50:53 +0000 | [diff] [blame] | 189 | unsigned count = UsingBlocks.lookup(*I); | 
| Jakob Stoklund Olesen | 532de3d | 2010-10-22 20:28:21 +0000 | [diff] [blame] | 190 | OS << " BB#" << (*I)->getNumber(); | 
|  | 191 | if (count) | 
|  | 192 | OS << '(' << count << ')'; | 
|  | 193 | } | 
|  | 194 | } | 
|  | 195 |  | 
| Jakob Stoklund Olesen | 8ae0263 | 2010-07-20 15:41:07 +0000 | [diff] [blame] | 196 | void SplitAnalysis::analyze(const LiveInterval *li) { | 
|  | 197 | clear(); | 
| Jakob Stoklund Olesen | 0786284 | 2011-01-26 00:50:53 +0000 | [diff] [blame] | 198 | CurLI = li; | 
| Jakob Stoklund Olesen | abff280 | 2010-07-20 16:12:37 +0000 | [diff] [blame] | 199 | analyzeUses(); | 
| Jakob Stoklund Olesen | 8ae0263 | 2010-07-20 15:41:07 +0000 | [diff] [blame] | 200 | } | 
|  | 201 |  | 
| Jakob Stoklund Olesen | 697483a | 2010-12-15 17:49:52 +0000 | [diff] [blame] | 202 |  | 
| Jakob Stoklund Olesen | f017900 | 2010-07-26 23:44:11 +0000 | [diff] [blame] | 203 | //===----------------------------------------------------------------------===// | 
|  | 204 | //                               Split Editor | 
|  | 205 | //===----------------------------------------------------------------------===// | 
|  | 206 |  | 
|  | 207 | /// Create a new SplitEditor for editing the LiveInterval analyzed by SA. | 
| Jakob Stoklund Olesen | d68f458 | 2010-10-28 20:34:50 +0000 | [diff] [blame] | 208 | SplitEditor::SplitEditor(SplitAnalysis &sa, | 
|  | 209 | LiveIntervals &lis, | 
|  | 210 | VirtRegMap &vrm, | 
| Jakob Stoklund Olesen | bece06f | 2011-03-03 01:29:13 +0000 | [diff] [blame] | 211 | MachineDominatorTree &mdt) | 
| Jakob Stoklund Olesen | 0eeca44 | 2011-02-19 00:42:33 +0000 | [diff] [blame] | 212 | : SA(sa), LIS(lis), VRM(vrm), | 
| Jakob Stoklund Olesen | 0786284 | 2011-01-26 00:50:53 +0000 | [diff] [blame] | 213 | MRI(vrm.getMachineFunction().getRegInfo()), | 
| Eric Christopher | 0f43811 | 2011-02-03 06:18:29 +0000 | [diff] [blame] | 214 | MDT(mdt), | 
| Jakob Stoklund Olesen | 0786284 | 2011-01-26 00:50:53 +0000 | [diff] [blame] | 215 | TII(*vrm.getMachineFunction().getTarget().getInstrInfo()), | 
|  | 216 | TRI(*vrm.getMachineFunction().getTarget().getRegisterInfo()), | 
| Jakob Stoklund Olesen | bece06f | 2011-03-03 01:29:13 +0000 | [diff] [blame] | 217 | Edit(0), | 
| Eric Christopher | 0f43811 | 2011-02-03 06:18:29 +0000 | [diff] [blame] | 218 | OpenIdx(0), | 
|  | 219 | RegAssign(Allocator) | 
| Jakob Stoklund Olesen | bece06f | 2011-03-03 01:29:13 +0000 | [diff] [blame] | 220 | {} | 
|  | 221 |  | 
|  | 222 | void SplitEditor::reset(LiveRangeEdit &lre) { | 
|  | 223 | Edit = &lre; | 
|  | 224 | OpenIdx = 0; | 
|  | 225 | RegAssign.clear(); | 
|  | 226 | Values.clear(); | 
| Jakob Stoklund Olesen | 13ba2da | 2011-03-04 00:15:36 +0000 | [diff] [blame] | 227 |  | 
|  | 228 | // We don't need to clear LiveOutCache, only LiveOutSeen entries are read. | 
|  | 229 | LiveOutSeen.clear(); | 
| Jakob Stoklund Olesen | bece06f | 2011-03-03 01:29:13 +0000 | [diff] [blame] | 230 |  | 
| Jakob Stoklund Olesen | cfa7134 | 2010-11-10 19:31:50 +0000 | [diff] [blame] | 231 | // We don't need an AliasAnalysis since we will only be performing | 
|  | 232 | // cheap-as-a-copy remats anyway. | 
| Jakob Stoklund Olesen | a2cae58 | 2011-03-02 23:31:50 +0000 | [diff] [blame] | 233 | Edit->anyRematerializable(LIS, TII, 0); | 
| Jakob Stoklund Olesen | f017900 | 2010-07-26 23:44:11 +0000 | [diff] [blame] | 234 | } | 
|  | 235 |  | 
| Eric Christopher | 0f43811 | 2011-02-03 06:18:29 +0000 | [diff] [blame] | 236 | void SplitEditor::dump() const { | 
|  | 237 | if (RegAssign.empty()) { | 
|  | 238 | dbgs() << " empty\n"; | 
|  | 239 | return; | 
|  | 240 | } | 
|  | 241 |  | 
|  | 242 | for (RegAssignMap::const_iterator I = RegAssign.begin(); I.valid(); ++I) | 
|  | 243 | dbgs() << " [" << I.start() << ';' << I.stop() << "):" << I.value(); | 
|  | 244 | dbgs() << '\n'; | 
| Jakob Stoklund Olesen | 5fa42a4 | 2010-09-21 22:32:21 +0000 | [diff] [blame] | 245 | } | 
|  | 246 |  | 
| Jakob Stoklund Olesen | 670ccd1 | 2011-03-01 23:14:53 +0000 | [diff] [blame] | 247 | VNInfo *SplitEditor::defValue(unsigned RegIdx, | 
|  | 248 | const VNInfo *ParentVNI, | 
|  | 249 | SlotIndex Idx) { | 
|  | 250 | assert(ParentVNI && "Mapping  NULL value"); | 
|  | 251 | assert(Idx.isValid() && "Invalid SlotIndex"); | 
| Jakob Stoklund Olesen | a2cae58 | 2011-03-02 23:31:50 +0000 | [diff] [blame] | 252 | assert(Edit->getParent().getVNInfoAt(Idx) == ParentVNI && "Bad Parent VNI"); | 
|  | 253 | LiveInterval *LI = Edit->get(RegIdx); | 
| Jakob Stoklund Olesen | 670ccd1 | 2011-03-01 23:14:53 +0000 | [diff] [blame] | 254 |  | 
|  | 255 | // Create a new value. | 
|  | 256 | VNInfo *VNI = LI->getNextValue(Idx, 0, LIS.getVNInfoAllocator()); | 
|  | 257 |  | 
|  | 258 | // Preserve the PHIDef bit. | 
|  | 259 | if (ParentVNI->isPHIDef() && Idx == ParentVNI->def) | 
|  | 260 | VNI->setIsPHIDef(true); | 
|  | 261 |  | 
|  | 262 | // Use insert for lookup, so we can add missing values with a second lookup. | 
|  | 263 | std::pair<ValueMap::iterator, bool> InsP = | 
|  | 264 | Values.insert(std::make_pair(std::make_pair(RegIdx, ParentVNI->id), VNI)); | 
|  | 265 |  | 
|  | 266 | // This was the first time (RegIdx, ParentVNI) was mapped. | 
|  | 267 | // Keep it as a simple def without any liveness. | 
|  | 268 | if (InsP.second) | 
|  | 269 | return VNI; | 
|  | 270 |  | 
|  | 271 | // If the previous value was a simple mapping, add liveness for it now. | 
|  | 272 | if (VNInfo *OldVNI = InsP.first->second) { | 
|  | 273 | SlotIndex Def = OldVNI->def; | 
|  | 274 | LI->addRange(LiveRange(Def, Def.getNextSlot(), OldVNI)); | 
|  | 275 | // No longer a simple mapping. | 
|  | 276 | InsP.first->second = 0; | 
|  | 277 | } | 
|  | 278 |  | 
|  | 279 | // This is a complex mapping, add liveness for VNI | 
|  | 280 | SlotIndex Def = VNI->def; | 
|  | 281 | LI->addRange(LiveRange(Def, Def.getNextSlot(), VNI)); | 
|  | 282 |  | 
|  | 283 | return VNI; | 
|  | 284 | } | 
|  | 285 |  | 
|  | 286 | void SplitEditor::markComplexMapped(unsigned RegIdx, const VNInfo *ParentVNI) { | 
|  | 287 | assert(ParentVNI && "Mapping  NULL value"); | 
|  | 288 | VNInfo *&VNI = Values[std::make_pair(RegIdx, ParentVNI->id)]; | 
|  | 289 |  | 
|  | 290 | // ParentVNI was either unmapped or already complex mapped. Either way. | 
|  | 291 | if (!VNI) | 
|  | 292 | return; | 
|  | 293 |  | 
|  | 294 | // This was previously a single mapping. Make sure the old def is represented | 
|  | 295 | // by a trivial live range. | 
|  | 296 | SlotIndex Def = VNI->def; | 
| Jakob Stoklund Olesen | a2cae58 | 2011-03-02 23:31:50 +0000 | [diff] [blame] | 297 | Edit->get(RegIdx)->addRange(LiveRange(Def, Def.getNextSlot(), VNI)); | 
| Jakob Stoklund Olesen | 670ccd1 | 2011-03-01 23:14:53 +0000 | [diff] [blame] | 298 | VNI = 0; | 
|  | 299 | } | 
|  | 300 |  | 
| Jakob Stoklund Olesen | 1c38ba6 | 2011-03-02 01:59:34 +0000 | [diff] [blame] | 301 | // extendRange - Extend the live range to reach Idx. | 
|  | 302 | // Potentially create phi-def values. | 
|  | 303 | void SplitEditor::extendRange(unsigned RegIdx, SlotIndex Idx) { | 
|  | 304 | assert(Idx.isValid() && "Invalid SlotIndex"); | 
|  | 305 | MachineBasicBlock *IdxMBB = LIS.getMBBFromIndex(Idx); | 
|  | 306 | assert(IdxMBB && "No MBB at Idx"); | 
| Jakob Stoklund Olesen | a2cae58 | 2011-03-02 23:31:50 +0000 | [diff] [blame] | 307 | LiveInterval *LI = Edit->get(RegIdx); | 
| Jakob Stoklund Olesen | 1c38ba6 | 2011-03-02 01:59:34 +0000 | [diff] [blame] | 308 |  | 
|  | 309 | // Is there a def in the same MBB we can extend? | 
|  | 310 | if (LI->extendInBlock(LIS.getMBBStartIdx(IdxMBB), Idx)) | 
|  | 311 | return; | 
|  | 312 |  | 
|  | 313 | // Now for the fun part. We know that ParentVNI potentially has multiple defs, | 
|  | 314 | // and we may need to create even more phi-defs to preserve VNInfo SSA form. | 
|  | 315 | // Perform a search for all predecessor blocks where we know the dominating | 
|  | 316 | // VNInfo. Insert phi-def VNInfos along the path back to IdxMBB. | 
| Jakob Stoklund Olesen | 1c38ba6 | 2011-03-02 01:59:34 +0000 | [diff] [blame] | 317 |  | 
| Jakob Stoklund Olesen | 13ba2da | 2011-03-04 00:15:36 +0000 | [diff] [blame] | 318 | // Initialize the live-out cache the first time it is needed. | 
|  | 319 | if (LiveOutSeen.empty()) { | 
|  | 320 | unsigned N = VRM.getMachineFunction().getNumBlockIDs(); | 
|  | 321 | LiveOutSeen.resize(N); | 
|  | 322 | LiveOutCache.resize(N); | 
|  | 323 | } | 
|  | 324 |  | 
| Jakob Stoklund Olesen | 1c38ba6 | 2011-03-02 01:59:34 +0000 | [diff] [blame] | 325 | // Blocks where LI should be live-in. | 
|  | 326 | SmallVector<MachineDomTreeNode*, 16> LiveIn; | 
|  | 327 | LiveIn.push_back(MDT[IdxMBB]); | 
|  | 328 |  | 
| Jakob Stoklund Olesen | 8701768 | 2011-03-03 01:29:10 +0000 | [diff] [blame] | 329 | // Remember if we have seen more than one value. | 
|  | 330 | bool UniqueVNI = true; | 
|  | 331 | VNInfo *IdxVNI = 0; | 
|  | 332 |  | 
| Jakob Stoklund Olesen | 1c38ba6 | 2011-03-02 01:59:34 +0000 | [diff] [blame] | 333 | // Using LiveOutCache as a visited set, perform a BFS for all reaching defs. | 
|  | 334 | for (unsigned i = 0; i != LiveIn.size(); ++i) { | 
|  | 335 | MachineBasicBlock *MBB = LiveIn[i]->getBlock(); | 
|  | 336 | for (MachineBasicBlock::pred_iterator PI = MBB->pred_begin(), | 
|  | 337 | PE = MBB->pred_end(); PI != PE; ++PI) { | 
|  | 338 | MachineBasicBlock *Pred = *PI; | 
| Jakob Stoklund Olesen | 13ba2da | 2011-03-04 00:15:36 +0000 | [diff] [blame] | 339 | LiveOutPair &LOP = LiveOutCache[Pred]; | 
|  | 340 |  | 
| Jakob Stoklund Olesen | 1c38ba6 | 2011-03-02 01:59:34 +0000 | [diff] [blame] | 341 | // Is this a known live-out block? | 
| Jakob Stoklund Olesen | 13ba2da | 2011-03-04 00:15:36 +0000 | [diff] [blame] | 342 | if (LiveOutSeen.test(Pred->getNumber())) { | 
|  | 343 | if (VNInfo *VNI = LOP.first) { | 
| Jakob Stoklund Olesen | 8701768 | 2011-03-03 01:29:10 +0000 | [diff] [blame] | 344 | if (IdxVNI && IdxVNI != VNI) | 
|  | 345 | UniqueVNI = false; | 
|  | 346 | IdxVNI = VNI; | 
|  | 347 | } | 
| Jakob Stoklund Olesen | 1c38ba6 | 2011-03-02 01:59:34 +0000 | [diff] [blame] | 348 | continue; | 
| Jakob Stoklund Olesen | 8701768 | 2011-03-03 01:29:10 +0000 | [diff] [blame] | 349 | } | 
| Jakob Stoklund Olesen | 13ba2da | 2011-03-04 00:15:36 +0000 | [diff] [blame] | 350 |  | 
|  | 351 | // First time. LOP is garbage and must be cleared below. | 
|  | 352 | LiveOutSeen.set(Pred->getNumber()); | 
|  | 353 |  | 
| Jakob Stoklund Olesen | 1c38ba6 | 2011-03-02 01:59:34 +0000 | [diff] [blame] | 354 | // Does Pred provide a live-out value? | 
|  | 355 | SlotIndex Start, Last; | 
|  | 356 | tie(Start, Last) = LIS.getSlotIndexes()->getMBBRange(Pred); | 
|  | 357 | Last = Last.getPrevSlot(); | 
| Jakob Stoklund Olesen | 13ba2da | 2011-03-04 00:15:36 +0000 | [diff] [blame] | 358 | VNInfo *VNI = LI->extendInBlock(Start, Last); | 
|  | 359 | LOP.first = VNI; | 
|  | 360 | if (VNI) { | 
|  | 361 | LOP.second = MDT[LIS.getMBBFromIndex(VNI->def)]; | 
| Jakob Stoklund Olesen | 8701768 | 2011-03-03 01:29:10 +0000 | [diff] [blame] | 362 | if (IdxVNI && IdxVNI != VNI) | 
|  | 363 | UniqueVNI = false; | 
|  | 364 | IdxVNI = VNI; | 
| Jakob Stoklund Olesen | 1c38ba6 | 2011-03-02 01:59:34 +0000 | [diff] [blame] | 365 | continue; | 
|  | 366 | } | 
| Jakob Stoklund Olesen | 13ba2da | 2011-03-04 00:15:36 +0000 | [diff] [blame] | 367 | LOP.second = 0; | 
|  | 368 |  | 
| Jakob Stoklund Olesen | 1c38ba6 | 2011-03-02 01:59:34 +0000 | [diff] [blame] | 369 | // No, we need a live-in value for Pred as well | 
|  | 370 | if (Pred != IdxMBB) | 
|  | 371 | LiveIn.push_back(MDT[Pred]); | 
| Jakob Stoklund Olesen | 8701768 | 2011-03-03 01:29:10 +0000 | [diff] [blame] | 372 | else | 
|  | 373 | UniqueVNI = false; // Loopback to IdxMBB, ask updateSSA() for help. | 
| Jakob Stoklund Olesen | 1c38ba6 | 2011-03-02 01:59:34 +0000 | [diff] [blame] | 374 | } | 
|  | 375 | } | 
|  | 376 |  | 
|  | 377 | // We may need to add phi-def values to preserve the SSA form. | 
| Jakob Stoklund Olesen | 8701768 | 2011-03-03 01:29:10 +0000 | [diff] [blame] | 378 | if (UniqueVNI) { | 
|  | 379 | LiveOutPair LOP(IdxVNI, MDT[LIS.getMBBFromIndex(IdxVNI->def)]); | 
|  | 380 | // Update LiveOutCache, but skip IdxMBB at LiveIn[0]. | 
|  | 381 | for (unsigned i = 1, e = LiveIn.size(); i != e; ++i) | 
|  | 382 | LiveOutCache[LiveIn[i]->getBlock()] = LOP; | 
|  | 383 | } else | 
|  | 384 | IdxVNI = updateSSA(RegIdx, LiveIn, Idx, IdxMBB); | 
| Jakob Stoklund Olesen | 1c38ba6 | 2011-03-02 01:59:34 +0000 | [diff] [blame] | 385 |  | 
| Jakob Stoklund Olesen | 1c38ba6 | 2011-03-02 01:59:34 +0000 | [diff] [blame] | 386 | // Since we went through the trouble of a full BFS visiting all reaching defs, | 
|  | 387 | // the values in LiveIn are now accurate. No more phi-defs are needed | 
|  | 388 | // for these blocks, so we can color the live ranges. | 
|  | 389 | for (unsigned i = 0, e = LiveIn.size(); i != e; ++i) { | 
|  | 390 | MachineBasicBlock *MBB = LiveIn[i]->getBlock(); | 
|  | 391 | SlotIndex Start = LIS.getMBBStartIdx(MBB); | 
| Jakob Stoklund Olesen | 13ba2da | 2011-03-04 00:15:36 +0000 | [diff] [blame] | 392 | VNInfo *VNI = LiveOutCache[MBB].first; | 
| Jakob Stoklund Olesen | 1c38ba6 | 2011-03-02 01:59:34 +0000 | [diff] [blame] | 393 |  | 
|  | 394 | // Anything in LiveIn other than IdxMBB is live-through. | 
|  | 395 | // In IdxMBB, we should stop at Idx unless the same value is live-out. | 
|  | 396 | if (MBB == IdxMBB && IdxVNI != VNI) | 
|  | 397 | LI->addRange(LiveRange(Start, Idx.getNextSlot(), IdxVNI)); | 
|  | 398 | else | 
|  | 399 | LI->addRange(LiveRange(Start, LIS.getMBBEndIdx(MBB), VNI)); | 
|  | 400 | } | 
|  | 401 | } | 
|  | 402 |  | 
|  | 403 | VNInfo *SplitEditor::updateSSA(unsigned RegIdx, | 
|  | 404 | SmallVectorImpl<MachineDomTreeNode*> &LiveIn, | 
|  | 405 | SlotIndex Idx, | 
|  | 406 | const MachineBasicBlock *IdxMBB) { | 
|  | 407 | // This is essentially the same iterative algorithm that SSAUpdater uses, | 
|  | 408 | // except we already have a dominator tree, so we don't have to recompute it. | 
| Jakob Stoklund Olesen | a2cae58 | 2011-03-02 23:31:50 +0000 | [diff] [blame] | 409 | LiveInterval *LI = Edit->get(RegIdx); | 
| Jakob Stoklund Olesen | 1c38ba6 | 2011-03-02 01:59:34 +0000 | [diff] [blame] | 410 | VNInfo *IdxVNI = 0; | 
|  | 411 | unsigned Changes; | 
|  | 412 | do { | 
|  | 413 | Changes = 0; | 
| Jakob Stoklund Olesen | 1c38ba6 | 2011-03-02 01:59:34 +0000 | [diff] [blame] | 414 | // Propagate live-out values down the dominator tree, inserting phi-defs | 
|  | 415 | // when necessary. Since LiveIn was created by a BFS, going backwards makes | 
|  | 416 | // it more likely for us to visit immediate dominators before their | 
|  | 417 | // children. | 
|  | 418 | for (unsigned i = LiveIn.size(); i; --i) { | 
|  | 419 | MachineDomTreeNode *Node = LiveIn[i-1]; | 
|  | 420 | MachineBasicBlock *MBB = Node->getBlock(); | 
|  | 421 | MachineDomTreeNode *IDom = Node->getIDom(); | 
|  | 422 | LiveOutPair IDomValue; | 
| Jakob Stoklund Olesen | 13ba2da | 2011-03-04 00:15:36 +0000 | [diff] [blame] | 423 |  | 
| Jakob Stoklund Olesen | 1c38ba6 | 2011-03-02 01:59:34 +0000 | [diff] [blame] | 424 | // We need a live-in value to a block with no immediate dominator? | 
|  | 425 | // This is probably an unreachable block that has survived somehow. | 
| Jakob Stoklund Olesen | 13ba2da | 2011-03-04 00:15:36 +0000 | [diff] [blame] | 426 | bool needPHI = !IDom || !LiveOutSeen.test(IDom->getBlock()->getNumber()); | 
| Jakob Stoklund Olesen | 1c38ba6 | 2011-03-02 01:59:34 +0000 | [diff] [blame] | 427 |  | 
|  | 428 | // IDom dominates all of our predecessors, but it may not be the immediate | 
|  | 429 | // dominator. Check if any of them have live-out values that are properly | 
|  | 430 | // dominated by IDom. If so, we need a phi-def here. | 
|  | 431 | if (!needPHI) { | 
| Jakob Stoklund Olesen | 13ba2da | 2011-03-04 00:15:36 +0000 | [diff] [blame] | 432 | IDomValue = LiveOutCache[IDom->getBlock()]; | 
| Jakob Stoklund Olesen | 1c38ba6 | 2011-03-02 01:59:34 +0000 | [diff] [blame] | 433 | for (MachineBasicBlock::pred_iterator PI = MBB->pred_begin(), | 
|  | 434 | PE = MBB->pred_end(); PI != PE; ++PI) { | 
|  | 435 | LiveOutPair Value = LiveOutCache[*PI]; | 
|  | 436 | if (!Value.first || Value.first == IDomValue.first) | 
|  | 437 | continue; | 
|  | 438 | // This predecessor is carrying something other than IDomValue. | 
|  | 439 | // It could be because IDomValue hasn't propagated yet, or it could be | 
|  | 440 | // because MBB is in the dominance frontier of that value. | 
|  | 441 | if (MDT.dominates(IDom, Value.second)) { | 
|  | 442 | needPHI = true; | 
|  | 443 | break; | 
|  | 444 | } | 
|  | 445 | } | 
|  | 446 | } | 
|  | 447 |  | 
|  | 448 | // Create a phi-def if required. | 
|  | 449 | if (needPHI) { | 
|  | 450 | ++Changes; | 
|  | 451 | SlotIndex Start = LIS.getMBBStartIdx(MBB); | 
|  | 452 | VNInfo *VNI = LI->getNextValue(Start, 0, LIS.getVNInfoAllocator()); | 
|  | 453 | VNI->setIsPHIDef(true); | 
| Jakob Stoklund Olesen | 1c38ba6 | 2011-03-02 01:59:34 +0000 | [diff] [blame] | 454 | // We no longer need LI to be live-in. | 
|  | 455 | LiveIn.erase(LiveIn.begin()+(i-1)); | 
|  | 456 | // Blocks in LiveIn are either IdxMBB, or have a value live-through. | 
|  | 457 | if (MBB == IdxMBB) | 
|  | 458 | IdxVNI = VNI; | 
|  | 459 | // Check if we need to update live-out info. | 
| Jakob Stoklund Olesen | 13ba2da | 2011-03-04 00:15:36 +0000 | [diff] [blame] | 460 | LiveOutPair &LOP = LiveOutCache[MBB]; | 
|  | 461 | if (LOP.second == Node || !LiveOutSeen.test(MBB->getNumber())) { | 
| Jakob Stoklund Olesen | 1c38ba6 | 2011-03-02 01:59:34 +0000 | [diff] [blame] | 462 | // We already have a live-out defined in MBB, so this must be IdxMBB. | 
|  | 463 | assert(MBB == IdxMBB && "Adding phi-def to known live-out"); | 
|  | 464 | LI->addRange(LiveRange(Start, Idx.getNextSlot(), VNI)); | 
|  | 465 | } else { | 
|  | 466 | // This phi-def is also live-out, so color the whole block. | 
|  | 467 | LI->addRange(LiveRange(Start, LIS.getMBBEndIdx(MBB), VNI)); | 
| Jakob Stoklund Olesen | 13ba2da | 2011-03-04 00:15:36 +0000 | [diff] [blame] | 468 | LOP = LiveOutPair(VNI, Node); | 
| Jakob Stoklund Olesen | 1c38ba6 | 2011-03-02 01:59:34 +0000 | [diff] [blame] | 469 | } | 
|  | 470 | } else if (IDomValue.first) { | 
|  | 471 | // No phi-def here. Remember incoming value for IdxMBB. | 
| Jakob Stoklund Olesen | 13ba2da | 2011-03-04 00:15:36 +0000 | [diff] [blame] | 472 | if (MBB == IdxMBB) { | 
| Jakob Stoklund Olesen | 1c38ba6 | 2011-03-02 01:59:34 +0000 | [diff] [blame] | 473 | IdxVNI = IDomValue.first; | 
| Jakob Stoklund Olesen | 13ba2da | 2011-03-04 00:15:36 +0000 | [diff] [blame] | 474 | // IdxMBB need not be live-out. | 
|  | 475 | if (!LiveOutSeen.test(MBB->getNumber())) | 
|  | 476 | continue; | 
|  | 477 | } | 
|  | 478 | assert(LiveOutSeen.test(MBB->getNumber()) && "Expected live-out block"); | 
| Jakob Stoklund Olesen | 1c38ba6 | 2011-03-02 01:59:34 +0000 | [diff] [blame] | 479 | // Propagate IDomValue if needed: | 
|  | 480 | // MBB is live-out and doesn't define its own value. | 
| Jakob Stoklund Olesen | 13ba2da | 2011-03-04 00:15:36 +0000 | [diff] [blame] | 481 | LiveOutPair &LOP = LiveOutCache[MBB]; | 
|  | 482 | if (LOP.second != Node && LOP.first != IDomValue.first) { | 
| Jakob Stoklund Olesen | 1c38ba6 | 2011-03-02 01:59:34 +0000 | [diff] [blame] | 483 | ++Changes; | 
| Jakob Stoklund Olesen | 13ba2da | 2011-03-04 00:15:36 +0000 | [diff] [blame] | 484 | LOP = IDomValue; | 
| Jakob Stoklund Olesen | 1c38ba6 | 2011-03-02 01:59:34 +0000 | [diff] [blame] | 485 | } | 
|  | 486 | } | 
|  | 487 | } | 
| Jakob Stoklund Olesen | 1c38ba6 | 2011-03-02 01:59:34 +0000 | [diff] [blame] | 488 | } while (Changes); | 
|  | 489 |  | 
|  | 490 | assert(IdxVNI && "Didn't find value for Idx"); | 
|  | 491 | return IdxVNI; | 
|  | 492 | } | 
|  | 493 |  | 
| Eric Christopher | 0f43811 | 2011-02-03 06:18:29 +0000 | [diff] [blame] | 494 | VNInfo *SplitEditor::defFromParent(unsigned RegIdx, | 
| Jakob Stoklund Olesen | cfa7134 | 2010-11-10 19:31:50 +0000 | [diff] [blame] | 495 | VNInfo *ParentVNI, | 
|  | 496 | SlotIndex UseIdx, | 
|  | 497 | MachineBasicBlock &MBB, | 
|  | 498 | MachineBasicBlock::iterator I) { | 
| Jakob Stoklund Olesen | cfa7134 | 2010-11-10 19:31:50 +0000 | [diff] [blame] | 499 | MachineInstr *CopyMI = 0; | 
|  | 500 | SlotIndex Def; | 
| Jakob Stoklund Olesen | a2cae58 | 2011-03-02 23:31:50 +0000 | [diff] [blame] | 501 | LiveInterval *LI = Edit->get(RegIdx); | 
| Jakob Stoklund Olesen | cfa7134 | 2010-11-10 19:31:50 +0000 | [diff] [blame] | 502 |  | 
|  | 503 | // Attempt cheap-as-a-copy rematerialization. | 
|  | 504 | LiveRangeEdit::Remat RM(ParentVNI); | 
| Jakob Stoklund Olesen | a2cae58 | 2011-03-02 23:31:50 +0000 | [diff] [blame] | 505 | if (Edit->canRematerializeAt(RM, UseIdx, true, LIS)) { | 
|  | 506 | Def = Edit->rematerializeAt(MBB, I, LI->reg, RM, LIS, TII, TRI); | 
| Jakob Stoklund Olesen | cfa7134 | 2010-11-10 19:31:50 +0000 | [diff] [blame] | 507 | } else { | 
|  | 508 | // Can't remat, just insert a copy from parent. | 
| Eric Christopher | 0f43811 | 2011-02-03 06:18:29 +0000 | [diff] [blame] | 509 | CopyMI = BuildMI(MBB, I, DebugLoc(), TII.get(TargetOpcode::COPY), LI->reg) | 
| Jakob Stoklund Olesen | a2cae58 | 2011-03-02 23:31:50 +0000 | [diff] [blame] | 510 | .addReg(Edit->getReg()); | 
| Jakob Stoklund Olesen | 0786284 | 2011-01-26 00:50:53 +0000 | [diff] [blame] | 511 | Def = LIS.InsertMachineInstrInMaps(CopyMI).getDefIndex(); | 
| Jakob Stoklund Olesen | cfa7134 | 2010-11-10 19:31:50 +0000 | [diff] [blame] | 512 | } | 
|  | 513 |  | 
| Jakob Stoklund Olesen | 670ccd1 | 2011-03-01 23:14:53 +0000 | [diff] [blame] | 514 | // Define the value in Reg. | 
|  | 515 | VNInfo *VNI = defValue(RegIdx, ParentVNI, Def); | 
|  | 516 | VNI->setCopy(CopyMI); | 
| Jakob Stoklund Olesen | cfa7134 | 2010-11-10 19:31:50 +0000 | [diff] [blame] | 517 | return VNI; | 
|  | 518 | } | 
|  | 519 |  | 
| Jakob Stoklund Olesen | 7536f72 | 2010-08-04 22:08:39 +0000 | [diff] [blame] | 520 | /// Create a new virtual register and live interval. | 
|  | 521 | void SplitEditor::openIntv() { | 
| Eric Christopher | 0f43811 | 2011-02-03 06:18:29 +0000 | [diff] [blame] | 522 | assert(!OpenIdx && "Previous LI not closed before openIntv"); | 
| Jakob Stoklund Olesen | f6a129a | 2010-09-16 00:01:36 +0000 | [diff] [blame] | 523 |  | 
| Eric Christopher | 0f43811 | 2011-02-03 06:18:29 +0000 | [diff] [blame] | 524 | // Create the complement as index 0. | 
| Jakob Stoklund Olesen | a2cae58 | 2011-03-02 23:31:50 +0000 | [diff] [blame] | 525 | if (Edit->empty()) | 
|  | 526 | Edit->create(MRI, LIS, VRM); | 
| Eric Christopher | 0f43811 | 2011-02-03 06:18:29 +0000 | [diff] [blame] | 527 |  | 
|  | 528 | // Create the open interval. | 
| Jakob Stoklund Olesen | a2cae58 | 2011-03-02 23:31:50 +0000 | [diff] [blame] | 529 | OpenIdx = Edit->size(); | 
|  | 530 | Edit->create(MRI, LIS, VRM); | 
| Jakob Stoklund Olesen | 7536f72 | 2010-08-04 22:08:39 +0000 | [diff] [blame] | 531 | } | 
|  | 532 |  | 
| Jakob Stoklund Olesen | 207c868 | 2011-02-03 17:04:16 +0000 | [diff] [blame] | 533 | SlotIndex SplitEditor::enterIntvBefore(SlotIndex Idx) { | 
| Eric Christopher | 0f43811 | 2011-02-03 06:18:29 +0000 | [diff] [blame] | 534 | assert(OpenIdx && "openIntv not called before enterIntvBefore"); | 
| Jakob Stoklund Olesen | 9b24afe | 2010-10-07 17:56:35 +0000 | [diff] [blame] | 535 | DEBUG(dbgs() << "    enterIntvBefore " << Idx); | 
| Jakob Stoklund Olesen | 207c868 | 2011-02-03 17:04:16 +0000 | [diff] [blame] | 536 | Idx = Idx.getBaseIndex(); | 
| Jakob Stoklund Olesen | a2cae58 | 2011-03-02 23:31:50 +0000 | [diff] [blame] | 537 | VNInfo *ParentVNI = Edit->getParent().getVNInfoAt(Idx); | 
| Jakob Stoklund Olesen | f6a129a | 2010-09-16 00:01:36 +0000 | [diff] [blame] | 538 | if (!ParentVNI) { | 
| Jakob Stoklund Olesen | 9b24afe | 2010-10-07 17:56:35 +0000 | [diff] [blame] | 539 | DEBUG(dbgs() << ": not live\n"); | 
| Jakob Stoklund Olesen | 207c868 | 2011-02-03 17:04:16 +0000 | [diff] [blame] | 540 | return Idx; | 
| Jakob Stoklund Olesen | f1b05f2 | 2010-08-12 17:07:14 +0000 | [diff] [blame] | 541 | } | 
| Jakob Stoklund Olesen | 207c868 | 2011-02-03 17:04:16 +0000 | [diff] [blame] | 542 | DEBUG(dbgs() << ": valno " << ParentVNI->id << '\n'); | 
| Jakob Stoklund Olesen | 0786284 | 2011-01-26 00:50:53 +0000 | [diff] [blame] | 543 | MachineInstr *MI = LIS.getInstructionFromIndex(Idx); | 
| Jakob Stoklund Olesen | f6a129a | 2010-09-16 00:01:36 +0000 | [diff] [blame] | 544 | assert(MI && "enterIntvBefore called with invalid index"); | 
| Jakob Stoklund Olesen | cfa7134 | 2010-11-10 19:31:50 +0000 | [diff] [blame] | 545 |  | 
| Jakob Stoklund Olesen | 207c868 | 2011-02-03 17:04:16 +0000 | [diff] [blame] | 546 | VNInfo *VNI = defFromParent(OpenIdx, ParentVNI, Idx, *MI->getParent(), MI); | 
|  | 547 | return VNI->def; | 
| Jakob Stoklund Olesen | f1b05f2 | 2010-08-12 17:07:14 +0000 | [diff] [blame] | 548 | } | 
|  | 549 |  | 
| Jakob Stoklund Olesen | 207c868 | 2011-02-03 17:04:16 +0000 | [diff] [blame] | 550 | SlotIndex SplitEditor::enterIntvAtEnd(MachineBasicBlock &MBB) { | 
| Eric Christopher | 0f43811 | 2011-02-03 06:18:29 +0000 | [diff] [blame] | 551 | assert(OpenIdx && "openIntv not called before enterIntvAtEnd"); | 
| Jakob Stoklund Olesen | 207c868 | 2011-02-03 17:04:16 +0000 | [diff] [blame] | 552 | SlotIndex End = LIS.getMBBEndIdx(&MBB); | 
|  | 553 | SlotIndex Last = End.getPrevSlot(); | 
|  | 554 | DEBUG(dbgs() << "    enterIntvAtEnd BB#" << MBB.getNumber() << ", " << Last); | 
| Jakob Stoklund Olesen | a2cae58 | 2011-03-02 23:31:50 +0000 | [diff] [blame] | 555 | VNInfo *ParentVNI = Edit->getParent().getVNInfoAt(Last); | 
| Jakob Stoklund Olesen | f6a129a | 2010-09-16 00:01:36 +0000 | [diff] [blame] | 556 | if (!ParentVNI) { | 
| Jakob Stoklund Olesen | 9b24afe | 2010-10-07 17:56:35 +0000 | [diff] [blame] | 557 | DEBUG(dbgs() << ": not live\n"); | 
| Jakob Stoklund Olesen | 207c868 | 2011-02-03 17:04:16 +0000 | [diff] [blame] | 558 | return End; | 
| Jakob Stoklund Olesen | f017900 | 2010-07-26 23:44:11 +0000 | [diff] [blame] | 559 | } | 
| Jakob Stoklund Olesen | 9b24afe | 2010-10-07 17:56:35 +0000 | [diff] [blame] | 560 | DEBUG(dbgs() << ": valno " << ParentVNI->id); | 
| Jakob Stoklund Olesen | 207c868 | 2011-02-03 17:04:16 +0000 | [diff] [blame] | 561 | VNInfo *VNI = defFromParent(OpenIdx, ParentVNI, Last, MBB, | 
| Jakob Stoklund Olesen | a2cae58 | 2011-03-02 23:31:50 +0000 | [diff] [blame] | 562 | LIS.getLastSplitPoint(Edit->getParent(), &MBB)); | 
| Jakob Stoklund Olesen | 207c868 | 2011-02-03 17:04:16 +0000 | [diff] [blame] | 563 | RegAssign.insert(VNI->def, End, OpenIdx); | 
| Eric Christopher | 0f43811 | 2011-02-03 06:18:29 +0000 | [diff] [blame] | 564 | DEBUG(dump()); | 
| Jakob Stoklund Olesen | 207c868 | 2011-02-03 17:04:16 +0000 | [diff] [blame] | 565 | return VNI->def; | 
| Jakob Stoklund Olesen | f017900 | 2010-07-26 23:44:11 +0000 | [diff] [blame] | 566 | } | 
|  | 567 |  | 
| Jakob Stoklund Olesen | 0786284 | 2011-01-26 00:50:53 +0000 | [diff] [blame] | 568 | /// useIntv - indicate that all instructions in MBB should use OpenLI. | 
| Jakob Stoklund Olesen | 7536f72 | 2010-08-04 22:08:39 +0000 | [diff] [blame] | 569 | void SplitEditor::useIntv(const MachineBasicBlock &MBB) { | 
| Jakob Stoklund Olesen | 0786284 | 2011-01-26 00:50:53 +0000 | [diff] [blame] | 570 | useIntv(LIS.getMBBStartIdx(&MBB), LIS.getMBBEndIdx(&MBB)); | 
| Jakob Stoklund Olesen | f017900 | 2010-07-26 23:44:11 +0000 | [diff] [blame] | 571 | } | 
|  | 572 |  | 
| Jakob Stoklund Olesen | 7536f72 | 2010-08-04 22:08:39 +0000 | [diff] [blame] | 573 | void SplitEditor::useIntv(SlotIndex Start, SlotIndex End) { | 
| Eric Christopher | 0f43811 | 2011-02-03 06:18:29 +0000 | [diff] [blame] | 574 | assert(OpenIdx && "openIntv not called before useIntv"); | 
|  | 575 | DEBUG(dbgs() << "    useIntv [" << Start << ';' << End << "):"); | 
|  | 576 | RegAssign.insert(Start, End, OpenIdx); | 
|  | 577 | DEBUG(dump()); | 
| Jakob Stoklund Olesen | f017900 | 2010-07-26 23:44:11 +0000 | [diff] [blame] | 578 | } | 
|  | 579 |  | 
| Jakob Stoklund Olesen | 207c868 | 2011-02-03 17:04:16 +0000 | [diff] [blame] | 580 | SlotIndex SplitEditor::leaveIntvAfter(SlotIndex Idx) { | 
| Eric Christopher | 0f43811 | 2011-02-03 06:18:29 +0000 | [diff] [blame] | 581 | assert(OpenIdx && "openIntv not called before leaveIntvAfter"); | 
| Jakob Stoklund Olesen | 9b24afe | 2010-10-07 17:56:35 +0000 | [diff] [blame] | 582 | DEBUG(dbgs() << "    leaveIntvAfter " << Idx); | 
| Jakob Stoklund Olesen | f1b05f2 | 2010-08-12 17:07:14 +0000 | [diff] [blame] | 583 |  | 
| Jakob Stoklund Olesen | f6a129a | 2010-09-16 00:01:36 +0000 | [diff] [blame] | 584 | // The interval must be live beyond the instruction at Idx. | 
| Jakob Stoklund Olesen | cfa7134 | 2010-11-10 19:31:50 +0000 | [diff] [blame] | 585 | Idx = Idx.getBoundaryIndex(); | 
| Jakob Stoklund Olesen | a2cae58 | 2011-03-02 23:31:50 +0000 | [diff] [blame] | 586 | VNInfo *ParentVNI = Edit->getParent().getVNInfoAt(Idx); | 
| Jakob Stoklund Olesen | f6a129a | 2010-09-16 00:01:36 +0000 | [diff] [blame] | 587 | if (!ParentVNI) { | 
| Jakob Stoklund Olesen | 9b24afe | 2010-10-07 17:56:35 +0000 | [diff] [blame] | 588 | DEBUG(dbgs() << ": not live\n"); | 
| Jakob Stoklund Olesen | 207c868 | 2011-02-03 17:04:16 +0000 | [diff] [blame] | 589 | return Idx.getNextSlot(); | 
| Jakob Stoklund Olesen | f1b05f2 | 2010-08-12 17:07:14 +0000 | [diff] [blame] | 590 | } | 
| Jakob Stoklund Olesen | 207c868 | 2011-02-03 17:04:16 +0000 | [diff] [blame] | 591 | DEBUG(dbgs() << ": valno " << ParentVNI->id << '\n'); | 
| Jakob Stoklund Olesen | f1b05f2 | 2010-08-12 17:07:14 +0000 | [diff] [blame] | 592 |  | 
| Jakob Stoklund Olesen | 01cb34b | 2011-02-08 18:50:18 +0000 | [diff] [blame] | 593 | MachineInstr *MI = LIS.getInstructionFromIndex(Idx); | 
|  | 594 | assert(MI && "No instruction at index"); | 
|  | 595 | VNInfo *VNI = defFromParent(0, ParentVNI, Idx, *MI->getParent(), | 
|  | 596 | llvm::next(MachineBasicBlock::iterator(MI))); | 
| Jakob Stoklund Olesen | 207c868 | 2011-02-03 17:04:16 +0000 | [diff] [blame] | 597 | return VNI->def; | 
| Jakob Stoklund Olesen | f1b05f2 | 2010-08-12 17:07:14 +0000 | [diff] [blame] | 598 | } | 
|  | 599 |  | 
| Jakob Stoklund Olesen | 9b05777 | 2011-02-09 23:30:25 +0000 | [diff] [blame] | 600 | SlotIndex SplitEditor::leaveIntvBefore(SlotIndex Idx) { | 
|  | 601 | assert(OpenIdx && "openIntv not called before leaveIntvBefore"); | 
|  | 602 | DEBUG(dbgs() << "    leaveIntvBefore " << Idx); | 
|  | 603 |  | 
|  | 604 | // The interval must be live into the instruction at Idx. | 
|  | 605 | Idx = Idx.getBoundaryIndex(); | 
| Jakob Stoklund Olesen | a2cae58 | 2011-03-02 23:31:50 +0000 | [diff] [blame] | 606 | VNInfo *ParentVNI = Edit->getParent().getVNInfoAt(Idx); | 
| Jakob Stoklund Olesen | 9b05777 | 2011-02-09 23:30:25 +0000 | [diff] [blame] | 607 | if (!ParentVNI) { | 
|  | 608 | DEBUG(dbgs() << ": not live\n"); | 
|  | 609 | return Idx.getNextSlot(); | 
|  | 610 | } | 
|  | 611 | DEBUG(dbgs() << ": valno " << ParentVNI->id << '\n'); | 
|  | 612 |  | 
|  | 613 | MachineInstr *MI = LIS.getInstructionFromIndex(Idx); | 
|  | 614 | assert(MI && "No instruction at index"); | 
|  | 615 | VNInfo *VNI = defFromParent(0, ParentVNI, Idx, *MI->getParent(), MI); | 
|  | 616 | return VNI->def; | 
|  | 617 | } | 
|  | 618 |  | 
| Jakob Stoklund Olesen | 207c868 | 2011-02-03 17:04:16 +0000 | [diff] [blame] | 619 | SlotIndex SplitEditor::leaveIntvAtTop(MachineBasicBlock &MBB) { | 
| Eric Christopher | 0f43811 | 2011-02-03 06:18:29 +0000 | [diff] [blame] | 620 | assert(OpenIdx && "openIntv not called before leaveIntvAtTop"); | 
| Jakob Stoklund Olesen | 0786284 | 2011-01-26 00:50:53 +0000 | [diff] [blame] | 621 | SlotIndex Start = LIS.getMBBStartIdx(&MBB); | 
| Jakob Stoklund Olesen | 9b24afe | 2010-10-07 17:56:35 +0000 | [diff] [blame] | 622 | DEBUG(dbgs() << "    leaveIntvAtTop BB#" << MBB.getNumber() << ", " << Start); | 
| Jakob Stoklund Olesen | 7536f72 | 2010-08-04 22:08:39 +0000 | [diff] [blame] | 623 |  | 
| Jakob Stoklund Olesen | a2cae58 | 2011-03-02 23:31:50 +0000 | [diff] [blame] | 624 | VNInfo *ParentVNI = Edit->getParent().getVNInfoAt(Start); | 
| Jakob Stoklund Olesen | f6a129a | 2010-09-16 00:01:36 +0000 | [diff] [blame] | 625 | if (!ParentVNI) { | 
| Jakob Stoklund Olesen | 9b24afe | 2010-10-07 17:56:35 +0000 | [diff] [blame] | 626 | DEBUG(dbgs() << ": not live\n"); | 
| Jakob Stoklund Olesen | 207c868 | 2011-02-03 17:04:16 +0000 | [diff] [blame] | 627 | return Start; | 
| Jakob Stoklund Olesen | 7536f72 | 2010-08-04 22:08:39 +0000 | [diff] [blame] | 628 | } | 
|  | 629 |  | 
| Eric Christopher | 0f43811 | 2011-02-03 06:18:29 +0000 | [diff] [blame] | 630 | VNInfo *VNI = defFromParent(0, ParentVNI, Start, MBB, | 
| Jakob Stoklund Olesen | cfa7134 | 2010-11-10 19:31:50 +0000 | [diff] [blame] | 631 | MBB.SkipPHIsAndLabels(MBB.begin())); | 
| Eric Christopher | 0f43811 | 2011-02-03 06:18:29 +0000 | [diff] [blame] | 632 | RegAssign.insert(Start, VNI->def, OpenIdx); | 
|  | 633 | DEBUG(dump()); | 
| Jakob Stoklund Olesen | 207c868 | 2011-02-03 17:04:16 +0000 | [diff] [blame] | 634 | return VNI->def; | 
| Jakob Stoklund Olesen | f017900 | 2010-07-26 23:44:11 +0000 | [diff] [blame] | 635 | } | 
|  | 636 |  | 
| Jakob Stoklund Olesen | 5c716bd | 2011-02-08 18:50:21 +0000 | [diff] [blame] | 637 | void SplitEditor::overlapIntv(SlotIndex Start, SlotIndex End) { | 
|  | 638 | assert(OpenIdx && "openIntv not called before overlapIntv"); | 
| Jakob Stoklund Olesen | a2cae58 | 2011-03-02 23:31:50 +0000 | [diff] [blame] | 639 | const VNInfo *ParentVNI = Edit->getParent().getVNInfoAt(Start); | 
|  | 640 | assert(ParentVNI == Edit->getParent().getVNInfoAt(End.getPrevSlot()) && | 
| Jakob Stoklund Olesen | 5c716bd | 2011-02-08 18:50:21 +0000 | [diff] [blame] | 641 | "Parent changes value in extended range"); | 
| Jakob Stoklund Olesen | 5c716bd | 2011-02-08 18:50:21 +0000 | [diff] [blame] | 642 | assert(LIS.getMBBFromIndex(Start) == LIS.getMBBFromIndex(End) && | 
|  | 643 | "Range cannot span basic blocks"); | 
|  | 644 |  | 
| Jakob Stoklund Olesen | d3fdaeb | 2011-03-02 00:49:28 +0000 | [diff] [blame] | 645 | // The complement interval will be extended as needed by extendRange(). | 
| Jakob Stoklund Olesen | 4670353 | 2011-03-02 23:05:19 +0000 | [diff] [blame] | 646 | markComplexMapped(0, ParentVNI); | 
| Jakob Stoklund Olesen | 5c716bd | 2011-02-08 18:50:21 +0000 | [diff] [blame] | 647 | DEBUG(dbgs() << "    overlapIntv [" << Start << ';' << End << "):"); | 
|  | 648 | RegAssign.insert(Start, End, OpenIdx); | 
|  | 649 | DEBUG(dump()); | 
|  | 650 | } | 
|  | 651 |  | 
| Jakob Stoklund Olesen | 7536f72 | 2010-08-04 22:08:39 +0000 | [diff] [blame] | 652 | /// closeIntv - Indicate that we are done editing the currently open | 
| Jakob Stoklund Olesen | f017900 | 2010-07-26 23:44:11 +0000 | [diff] [blame] | 653 | /// LiveInterval, and ranges can be trimmed. | 
| Jakob Stoklund Olesen | 7536f72 | 2010-08-04 22:08:39 +0000 | [diff] [blame] | 654 | void SplitEditor::closeIntv() { | 
| Eric Christopher | 0f43811 | 2011-02-03 06:18:29 +0000 | [diff] [blame] | 655 | assert(OpenIdx && "openIntv not called before closeIntv"); | 
|  | 656 | OpenIdx = 0; | 
| Jakob Stoklund Olesen | f017900 | 2010-07-26 23:44:11 +0000 | [diff] [blame] | 657 | } | 
|  | 658 |  | 
| Jakob Stoklund Olesen | 4670353 | 2011-03-02 23:05:19 +0000 | [diff] [blame] | 659 | /// transferSimpleValues - Transfer all simply defined values to the new live | 
|  | 660 | /// ranges. | 
|  | 661 | /// Values that were rematerialized or that have multiple defs are left alone. | 
|  | 662 | bool SplitEditor::transferSimpleValues() { | 
|  | 663 | bool Skipped = false; | 
|  | 664 | RegAssignMap::const_iterator AssignI = RegAssign.begin(); | 
| Jakob Stoklund Olesen | a2cae58 | 2011-03-02 23:31:50 +0000 | [diff] [blame] | 665 | for (LiveInterval::const_iterator ParentI = Edit->getParent().begin(), | 
|  | 666 | ParentE = Edit->getParent().end(); ParentI != ParentE; ++ParentI) { | 
| Jakob Stoklund Olesen | 4670353 | 2011-03-02 23:05:19 +0000 | [diff] [blame] | 667 | DEBUG(dbgs() << "  blit " << *ParentI << ':'); | 
|  | 668 | VNInfo *ParentVNI = ParentI->valno; | 
|  | 669 | // RegAssign has holes where RegIdx 0 should be used. | 
|  | 670 | SlotIndex Start = ParentI->start; | 
|  | 671 | AssignI.advanceTo(Start); | 
|  | 672 | do { | 
|  | 673 | unsigned RegIdx; | 
|  | 674 | SlotIndex End = ParentI->end; | 
|  | 675 | if (!AssignI.valid()) { | 
|  | 676 | RegIdx = 0; | 
|  | 677 | } else if (AssignI.start() <= Start) { | 
|  | 678 | RegIdx = AssignI.value(); | 
|  | 679 | if (AssignI.stop() < End) { | 
|  | 680 | End = AssignI.stop(); | 
|  | 681 | ++AssignI; | 
|  | 682 | } | 
|  | 683 | } else { | 
|  | 684 | RegIdx = 0; | 
|  | 685 | End = std::min(End, AssignI.start()); | 
|  | 686 | } | 
|  | 687 | DEBUG(dbgs() << " [" << Start << ';' << End << ")=" << RegIdx); | 
|  | 688 | if (VNInfo *VNI = Values.lookup(std::make_pair(RegIdx, ParentVNI->id))) { | 
|  | 689 | DEBUG(dbgs() << ':' << VNI->id); | 
| Jakob Stoklund Olesen | a2cae58 | 2011-03-02 23:31:50 +0000 | [diff] [blame] | 690 | Edit->get(RegIdx)->addRange(LiveRange(Start, End, VNI)); | 
| Jakob Stoklund Olesen | 4670353 | 2011-03-02 23:05:19 +0000 | [diff] [blame] | 691 | } else | 
|  | 692 | Skipped = true; | 
|  | 693 | Start = End; | 
|  | 694 | } while (Start != ParentI->end); | 
|  | 695 | DEBUG(dbgs() << '\n'); | 
|  | 696 | } | 
|  | 697 | return Skipped; | 
|  | 698 | } | 
|  | 699 |  | 
| Jakob Stoklund Olesen | e2dc0c9 | 2011-03-02 23:05:16 +0000 | [diff] [blame] | 700 | void SplitEditor::extendPHIKillRanges() { | 
|  | 701 | // Extend live ranges to be live-out for successor PHI values. | 
| Jakob Stoklund Olesen | a2cae58 | 2011-03-02 23:31:50 +0000 | [diff] [blame] | 702 | for (LiveInterval::const_vni_iterator I = Edit->getParent().vni_begin(), | 
|  | 703 | E = Edit->getParent().vni_end(); I != E; ++I) { | 
| Jakob Stoklund Olesen | e2dc0c9 | 2011-03-02 23:05:16 +0000 | [diff] [blame] | 704 | const VNInfo *PHIVNI = *I; | 
|  | 705 | if (PHIVNI->isUnused() || !PHIVNI->isPHIDef()) | 
|  | 706 | continue; | 
|  | 707 | unsigned RegIdx = RegAssign.lookup(PHIVNI->def); | 
|  | 708 | MachineBasicBlock *MBB = LIS.getMBBFromIndex(PHIVNI->def); | 
|  | 709 | for (MachineBasicBlock::pred_iterator PI = MBB->pred_begin(), | 
|  | 710 | PE = MBB->pred_end(); PI != PE; ++PI) { | 
|  | 711 | SlotIndex End = LIS.getMBBEndIdx(*PI).getPrevSlot(); | 
|  | 712 | // The predecessor may not have a live-out value. That is OK, like an | 
|  | 713 | // undef PHI operand. | 
| Jakob Stoklund Olesen | a2cae58 | 2011-03-02 23:31:50 +0000 | [diff] [blame] | 714 | if (Edit->getParent().liveAt(End)) { | 
| Jakob Stoklund Olesen | e2dc0c9 | 2011-03-02 23:05:16 +0000 | [diff] [blame] | 715 | assert(RegAssign.lookup(End) == RegIdx && | 
|  | 716 | "Different register assignment in phi predecessor"); | 
|  | 717 | extendRange(RegIdx, End); | 
|  | 718 | } | 
|  | 719 | } | 
|  | 720 | } | 
|  | 721 | } | 
|  | 722 |  | 
| Jakob Stoklund Olesen | a2cae58 | 2011-03-02 23:31:50 +0000 | [diff] [blame] | 723 | /// rewriteAssigned - Rewrite all uses of Edit->getReg(). | 
| Jakob Stoklund Olesen | 4670353 | 2011-03-02 23:05:19 +0000 | [diff] [blame] | 724 | void SplitEditor::rewriteAssigned(bool ExtendRanges) { | 
| Jakob Stoklund Olesen | a2cae58 | 2011-03-02 23:31:50 +0000 | [diff] [blame] | 725 | for (MachineRegisterInfo::reg_iterator RI = MRI.reg_begin(Edit->getReg()), | 
| Jakob Stoklund Olesen | 0786284 | 2011-01-26 00:50:53 +0000 | [diff] [blame] | 726 | RE = MRI.reg_end(); RI != RE;) { | 
| Jakob Stoklund Olesen | 7466927 | 2010-10-08 23:42:21 +0000 | [diff] [blame] | 727 | MachineOperand &MO = RI.getOperand(); | 
|  | 728 | MachineInstr *MI = MO.getParent(); | 
|  | 729 | ++RI; | 
| Eric Christopher | 0f43811 | 2011-02-03 06:18:29 +0000 | [diff] [blame] | 730 | // LiveDebugVariables should have handled all DBG_VALUE instructions. | 
| Jakob Stoklund Olesen | 7466927 | 2010-10-08 23:42:21 +0000 | [diff] [blame] | 731 | if (MI->isDebugValue()) { | 
|  | 732 | DEBUG(dbgs() << "Zapping " << *MI); | 
| Jakob Stoklund Olesen | 7466927 | 2010-10-08 23:42:21 +0000 | [diff] [blame] | 733 | MO.setReg(0); | 
|  | 734 | continue; | 
|  | 735 | } | 
| Jakob Stoklund Olesen | a372d16 | 2011-02-09 21:52:09 +0000 | [diff] [blame] | 736 |  | 
|  | 737 | // <undef> operands don't really read the register, so just assign them to | 
|  | 738 | // the complement. | 
|  | 739 | if (MO.isUse() && MO.isUndef()) { | 
| Jakob Stoklund Olesen | a2cae58 | 2011-03-02 23:31:50 +0000 | [diff] [blame] | 740 | MO.setReg(Edit->get(0)->reg); | 
| Jakob Stoklund Olesen | a372d16 | 2011-02-09 21:52:09 +0000 | [diff] [blame] | 741 | continue; | 
|  | 742 | } | 
|  | 743 |  | 
| Jakob Stoklund Olesen | 0786284 | 2011-01-26 00:50:53 +0000 | [diff] [blame] | 744 | SlotIndex Idx = LIS.getInstructionIndex(MI); | 
| Jakob Stoklund Olesen | 7466927 | 2010-10-08 23:42:21 +0000 | [diff] [blame] | 745 | Idx = MO.isUse() ? Idx.getUseIndex() : Idx.getDefIndex(); | 
| Eric Christopher | 0f43811 | 2011-02-03 06:18:29 +0000 | [diff] [blame] | 746 |  | 
|  | 747 | // Rewrite to the mapped register at Idx. | 
|  | 748 | unsigned RegIdx = RegAssign.lookup(Idx); | 
| Jakob Stoklund Olesen | a2cae58 | 2011-03-02 23:31:50 +0000 | [diff] [blame] | 749 | MO.setReg(Edit->get(RegIdx)->reg); | 
| Eric Christopher | 0f43811 | 2011-02-03 06:18:29 +0000 | [diff] [blame] | 750 | DEBUG(dbgs() << "  rewr BB#" << MI->getParent()->getNumber() << '\t' | 
|  | 751 | << Idx << ':' << RegIdx << '\t' << *MI); | 
|  | 752 |  | 
|  | 753 | // Extend liveness to Idx. | 
| Jakob Stoklund Olesen | 4670353 | 2011-03-02 23:05:19 +0000 | [diff] [blame] | 754 | if (ExtendRanges) | 
|  | 755 | extendRange(RegIdx, Idx); | 
| Jakob Stoklund Olesen | 7466927 | 2010-10-08 23:42:21 +0000 | [diff] [blame] | 756 | } | 
|  | 757 | } | 
|  | 758 |  | 
| Eric Christopher | 0f43811 | 2011-02-03 06:18:29 +0000 | [diff] [blame] | 759 | /// rewriteSplit - Rewrite uses of Intvs[0] according to the ConEQ mapping. | 
|  | 760 | void SplitEditor::rewriteComponents(const SmallVectorImpl<LiveInterval*> &Intvs, | 
|  | 761 | const ConnectedVNInfoEqClasses &ConEq) { | 
|  | 762 | for (MachineRegisterInfo::reg_iterator RI = MRI.reg_begin(Intvs[0]->reg), | 
|  | 763 | RE = MRI.reg_end(); RI != RE;) { | 
|  | 764 | MachineOperand &MO = RI.getOperand(); | 
|  | 765 | MachineInstr *MI = MO.getParent(); | 
|  | 766 | ++RI; | 
|  | 767 | if (MO.isUse() && MO.isUndef()) | 
| Jakob Stoklund Olesen | 9d99977 | 2010-10-21 18:47:08 +0000 | [diff] [blame] | 768 | continue; | 
| Eric Christopher | 0f43811 | 2011-02-03 06:18:29 +0000 | [diff] [blame] | 769 | // DBG_VALUE instructions should have been eliminated earlier. | 
|  | 770 | SlotIndex Idx = LIS.getInstructionIndex(MI); | 
|  | 771 | Idx = MO.isUse() ? Idx.getUseIndex() : Idx.getDefIndex(); | 
|  | 772 | DEBUG(dbgs() << "  rewr BB#" << MI->getParent()->getNumber() << '\t' | 
|  | 773 | << Idx << ':'); | 
|  | 774 | const VNInfo *VNI = Intvs[0]->getVNInfoAt(Idx); | 
|  | 775 | assert(VNI && "Interval not live at use."); | 
|  | 776 | MO.setReg(Intvs[ConEq.getEqClass(VNI)]->reg); | 
|  | 777 | DEBUG(dbgs() << VNI->id << '\t' << *MI); | 
| Eric Christopher | 463a297 | 2011-02-03 05:40:54 +0000 | [diff] [blame] | 778 | } | 
| Eric Christopher | 463a297 | 2011-02-03 05:40:54 +0000 | [diff] [blame] | 779 | } | 
| Jakob Stoklund Olesen | 2cd2111 | 2011-02-03 00:54:23 +0000 | [diff] [blame] | 780 |  | 
| Eric Christopher | 463a297 | 2011-02-03 05:40:54 +0000 | [diff] [blame] | 781 | void SplitEditor::finish() { | 
| Eric Christopher | 0f43811 | 2011-02-03 06:18:29 +0000 | [diff] [blame] | 782 | assert(OpenIdx == 0 && "Previous LI not closed before rewrite"); | 
| Jakob Stoklund Olesen | 4670353 | 2011-03-02 23:05:19 +0000 | [diff] [blame] | 783 | ++NumFinished; | 
| Eric Christopher | 463a297 | 2011-02-03 05:40:54 +0000 | [diff] [blame] | 784 |  | 
| Eric Christopher | 0f43811 | 2011-02-03 06:18:29 +0000 | [diff] [blame] | 785 | // At this point, the live intervals in Edit contain VNInfos corresponding to | 
|  | 786 | // the inserted copies. | 
|  | 787 |  | 
|  | 788 | // Add the original defs from the parent interval. | 
| Jakob Stoklund Olesen | a2cae58 | 2011-03-02 23:31:50 +0000 | [diff] [blame] | 789 | for (LiveInterval::const_vni_iterator I = Edit->getParent().vni_begin(), | 
|  | 790 | E = Edit->getParent().vni_end(); I != E; ++I) { | 
| Eric Christopher | 0f43811 | 2011-02-03 06:18:29 +0000 | [diff] [blame] | 791 | const VNInfo *ParentVNI = *I; | 
| Jakob Stoklund Olesen | 9ecd1e7 | 2011-02-04 00:59:23 +0000 | [diff] [blame] | 792 | if (ParentVNI->isUnused()) | 
|  | 793 | continue; | 
| Jakob Stoklund Olesen | 670ccd1 | 2011-03-01 23:14:53 +0000 | [diff] [blame] | 794 | unsigned RegIdx = RegAssign.lookup(ParentVNI->def); | 
| Jakob Stoklund Olesen | 670ccd1 | 2011-03-01 23:14:53 +0000 | [diff] [blame] | 795 | defValue(RegIdx, ParentVNI, ParentVNI->def); | 
| Jakob Stoklund Olesen | 4670353 | 2011-03-02 23:05:19 +0000 | [diff] [blame] | 796 | // Mark rematted values as complex everywhere to force liveness computation. | 
|  | 797 | // The new live ranges may be truncated. | 
| Jakob Stoklund Olesen | a2cae58 | 2011-03-02 23:31:50 +0000 | [diff] [blame] | 798 | if (Edit->didRematerialize(ParentVNI)) | 
|  | 799 | for (unsigned i = 0, e = Edit->size(); i != e; ++i) | 
| Jakob Stoklund Olesen | 4670353 | 2011-03-02 23:05:19 +0000 | [diff] [blame] | 800 | markComplexMapped(i, ParentVNI); | 
| Eric Christopher | 0f43811 | 2011-02-03 06:18:29 +0000 | [diff] [blame] | 801 | } | 
|  | 802 |  | 
|  | 803 | #ifndef NDEBUG | 
|  | 804 | // Every new interval must have a def by now, otherwise the split is bogus. | 
| Jakob Stoklund Olesen | a2cae58 | 2011-03-02 23:31:50 +0000 | [diff] [blame] | 805 | for (LiveRangeEdit::iterator I = Edit->begin(), E = Edit->end(); I != E; ++I) | 
| Eric Christopher | 0f43811 | 2011-02-03 06:18:29 +0000 | [diff] [blame] | 806 | assert((*I)->hasAtLeastOneValue() && "Split interval has no value"); | 
|  | 807 | #endif | 
|  | 808 |  | 
| Jakob Stoklund Olesen | 4670353 | 2011-03-02 23:05:19 +0000 | [diff] [blame] | 809 | // Transfer the simply mapped values, check if any are complex. | 
|  | 810 | bool Complex = transferSimpleValues(); | 
|  | 811 | if (Complex) | 
|  | 812 | extendPHIKillRanges(); | 
|  | 813 | else | 
|  | 814 | ++NumSimple; | 
| Eric Christopher | 0f43811 | 2011-02-03 06:18:29 +0000 | [diff] [blame] | 815 |  | 
| Jakob Stoklund Olesen | 4670353 | 2011-03-02 23:05:19 +0000 | [diff] [blame] | 816 | // Rewrite virtual registers, possibly extending ranges. | 
|  | 817 | rewriteAssigned(Complex); | 
| Eric Christopher | 0f43811 | 2011-02-03 06:18:29 +0000 | [diff] [blame] | 818 |  | 
|  | 819 | // FIXME: Delete defs that were rematted everywhere. | 
| Jakob Stoklund Olesen | 5fa42a4 | 2010-09-21 22:32:21 +0000 | [diff] [blame] | 820 |  | 
| Jakob Stoklund Olesen | 0253df9 | 2010-10-07 23:34:34 +0000 | [diff] [blame] | 821 | // Get rid of unused values and set phi-kill flags. | 
| Jakob Stoklund Olesen | a2cae58 | 2011-03-02 23:31:50 +0000 | [diff] [blame] | 822 | for (LiveRangeEdit::iterator I = Edit->begin(), E = Edit->end(); I != E; ++I) | 
| Jakob Stoklund Olesen | 0786284 | 2011-01-26 00:50:53 +0000 | [diff] [blame] | 823 | (*I)->RenumberValues(LIS); | 
| Jakob Stoklund Olesen | 5fa42a4 | 2010-09-21 22:32:21 +0000 | [diff] [blame] | 824 |  | 
| Jakob Stoklund Olesen | 3a0e071 | 2010-10-26 22:36:09 +0000 | [diff] [blame] | 825 | // Now check if any registers were separated into multiple components. | 
| Jakob Stoklund Olesen | 0786284 | 2011-01-26 00:50:53 +0000 | [diff] [blame] | 826 | ConnectedVNInfoEqClasses ConEQ(LIS); | 
| Jakob Stoklund Olesen | a2cae58 | 2011-03-02 23:31:50 +0000 | [diff] [blame] | 827 | for (unsigned i = 0, e = Edit->size(); i != e; ++i) { | 
| Jakob Stoklund Olesen | 3a0e071 | 2010-10-26 22:36:09 +0000 | [diff] [blame] | 828 | // Don't use iterators, they are invalidated by create() below. | 
| Jakob Stoklund Olesen | a2cae58 | 2011-03-02 23:31:50 +0000 | [diff] [blame] | 829 | LiveInterval *li = Edit->get(i); | 
| Jakob Stoklund Olesen | 3a0e071 | 2010-10-26 22:36:09 +0000 | [diff] [blame] | 830 | unsigned NumComp = ConEQ.Classify(li); | 
|  | 831 | if (NumComp <= 1) | 
|  | 832 | continue; | 
|  | 833 | DEBUG(dbgs() << "  " << NumComp << " components: " << *li << '\n'); | 
|  | 834 | SmallVector<LiveInterval*, 8> dups; | 
|  | 835 | dups.push_back(li); | 
|  | 836 | for (unsigned i = 1; i != NumComp; ++i) | 
| Jakob Stoklund Olesen | a2cae58 | 2011-03-02 23:31:50 +0000 | [diff] [blame] | 837 | dups.push_back(&Edit->create(MRI, LIS, VRM)); | 
| Eric Christopher | 0f43811 | 2011-02-03 06:18:29 +0000 | [diff] [blame] | 838 | rewriteComponents(dups, ConEQ); | 
| Jakob Stoklund Olesen | 3a0e071 | 2010-10-26 22:36:09 +0000 | [diff] [blame] | 839 | ConEQ.Distribute(&dups[0]); | 
| Jakob Stoklund Olesen | 3a0e071 | 2010-10-26 22:36:09 +0000 | [diff] [blame] | 840 | } | 
|  | 841 |  | 
| Jakob Stoklund Olesen | 08e93b1 | 2010-08-10 17:07:22 +0000 | [diff] [blame] | 842 | // Calculate spill weight and allocation hints for new intervals. | 
| Jakob Stoklund Olesen | 0eeca44 | 2011-02-19 00:42:33 +0000 | [diff] [blame] | 843 | VirtRegAuxInfo vrai(VRM.getMachineFunction(), LIS, SA.Loops); | 
| Jakob Stoklund Olesen | a2cae58 | 2011-03-02 23:31:50 +0000 | [diff] [blame] | 844 | for (LiveRangeEdit::iterator I = Edit->begin(), E = Edit->end(); I != E; ++I){ | 
| Jakob Stoklund Olesen | a17768f | 2010-10-14 23:49:52 +0000 | [diff] [blame] | 845 | LiveInterval &li = **I; | 
| Jakob Stoklund Olesen | 9db3ea4 | 2010-08-10 18:37:40 +0000 | [diff] [blame] | 846 | vrai.CalculateRegClass(li.reg); | 
| Jakob Stoklund Olesen | 08e93b1 | 2010-08-10 17:07:22 +0000 | [diff] [blame] | 847 | vrai.CalculateWeightAndHint(li); | 
| Jakob Stoklund Olesen | 0786284 | 2011-01-26 00:50:53 +0000 | [diff] [blame] | 848 | DEBUG(dbgs() << "  new interval " << MRI.getRegClass(li.reg)->getName() | 
| Jakob Stoklund Olesen | e1f543f | 2010-08-12 18:50:55 +0000 | [diff] [blame] | 849 | << ":" << li << '\n'); | 
| Jakob Stoklund Olesen | 08e93b1 | 2010-08-10 17:07:22 +0000 | [diff] [blame] | 850 | } | 
| Jakob Stoklund Olesen | f017900 | 2010-07-26 23:44:11 +0000 | [diff] [blame] | 851 | } | 
|  | 852 |  | 
|  | 853 |  | 
| Jakob Stoklund Olesen | 8ae0263 | 2010-07-20 15:41:07 +0000 | [diff] [blame] | 854 | //===----------------------------------------------------------------------===// | 
| Jakob Stoklund Olesen | f1b05f2 | 2010-08-12 17:07:14 +0000 | [diff] [blame] | 855 | //                            Single Block Splitting | 
|  | 856 | //===----------------------------------------------------------------------===// | 
|  | 857 |  | 
| Jakob Stoklund Olesen | 0786284 | 2011-01-26 00:50:53 +0000 | [diff] [blame] | 858 | /// getMultiUseBlocks - if CurLI has more than one use in a basic block, it | 
|  | 859 | /// may be an advantage to split CurLI for the duration of the block. | 
| Jakob Stoklund Olesen | 2bfb324 | 2010-10-22 22:48:56 +0000 | [diff] [blame] | 860 | bool SplitAnalysis::getMultiUseBlocks(BlockPtrSet &Blocks) { | 
| Jakob Stoklund Olesen | 0786284 | 2011-01-26 00:50:53 +0000 | [diff] [blame] | 861 | // If CurLI is local to one block, there is no point to splitting it. | 
| Jakob Stoklund Olesen | 9b05777 | 2011-02-09 23:30:25 +0000 | [diff] [blame] | 862 | if (LiveBlocks.size() <= 1) | 
| Jakob Stoklund Olesen | 2bfb324 | 2010-10-22 22:48:56 +0000 | [diff] [blame] | 863 | return false; | 
|  | 864 | // Add blocks with multiple uses. | 
| Jakob Stoklund Olesen | 9b05777 | 2011-02-09 23:30:25 +0000 | [diff] [blame] | 865 | for (unsigned i = 0, e = LiveBlocks.size(); i != e; ++i) { | 
|  | 866 | const BlockInfo &BI = LiveBlocks[i]; | 
|  | 867 | if (!BI.Uses) | 
| Jakob Stoklund Olesen | 2bfb324 | 2010-10-22 22:48:56 +0000 | [diff] [blame] | 868 | continue; | 
| Jakob Stoklund Olesen | 9b05777 | 2011-02-09 23:30:25 +0000 | [diff] [blame] | 869 | unsigned Instrs = UsingBlocks.lookup(BI.MBB); | 
|  | 870 | if (Instrs <= 1) | 
|  | 871 | continue; | 
|  | 872 | if (Instrs == 2 && BI.LiveIn && BI.LiveOut && !BI.LiveThrough) | 
|  | 873 | continue; | 
|  | 874 | Blocks.insert(BI.MBB); | 
|  | 875 | } | 
| Jakob Stoklund Olesen | 2bfb324 | 2010-10-22 22:48:56 +0000 | [diff] [blame] | 876 | return !Blocks.empty(); | 
|  | 877 | } | 
|  | 878 |  | 
| Jakob Stoklund Olesen | 0786284 | 2011-01-26 00:50:53 +0000 | [diff] [blame] | 879 | /// splitSingleBlocks - Split CurLI into a separate live interval inside each | 
| Jakob Stoklund Olesen | 57d0f2d | 2010-10-05 22:19:33 +0000 | [diff] [blame] | 880 | /// basic block in Blocks. | 
|  | 881 | void SplitEditor::splitSingleBlocks(const SplitAnalysis::BlockPtrSet &Blocks) { | 
| Jakob Stoklund Olesen | e1f543f | 2010-08-12 18:50:55 +0000 | [diff] [blame] | 882 | DEBUG(dbgs() << "  splitSingleBlocks for " << Blocks.size() << " blocks.\n"); | 
| Jakob Stoklund Olesen | f1b05f2 | 2010-08-12 17:07:14 +0000 | [diff] [blame] | 883 |  | 
| Jakob Stoklund Olesen | 0eeca44 | 2011-02-19 00:42:33 +0000 | [diff] [blame] | 884 | for (unsigned i = 0, e = SA.LiveBlocks.size(); i != e; ++i) { | 
|  | 885 | const SplitAnalysis::BlockInfo &BI = SA.LiveBlocks[i]; | 
| Jakob Stoklund Olesen | 9b05777 | 2011-02-09 23:30:25 +0000 | [diff] [blame] | 886 | if (!BI.Uses || !Blocks.count(BI.MBB)) | 
|  | 887 | continue; | 
| Jakob Stoklund Olesen | f1b05f2 | 2010-08-12 17:07:14 +0000 | [diff] [blame] | 888 |  | 
|  | 889 | openIntv(); | 
| Jakob Stoklund Olesen | 9b05777 | 2011-02-09 23:30:25 +0000 | [diff] [blame] | 890 | SlotIndex SegStart = enterIntvBefore(BI.FirstUse); | 
| Jakob Stoklund Olesen | c70f687 | 2011-02-23 18:26:31 +0000 | [diff] [blame] | 891 | if (!BI.LiveOut || BI.LastUse < BI.LastSplitPoint) { | 
| Jakob Stoklund Olesen | 9b05777 | 2011-02-09 23:30:25 +0000 | [diff] [blame] | 892 | useIntv(SegStart, leaveIntvAfter(BI.LastUse)); | 
|  | 893 | } else { | 
| Jakob Stoklund Olesen | c70f687 | 2011-02-23 18:26:31 +0000 | [diff] [blame] | 894 | // The last use is after the last valid split point. | 
| Jakob Stoklund Olesen | 9b05777 | 2011-02-09 23:30:25 +0000 | [diff] [blame] | 895 | SlotIndex SegStop = leaveIntvBefore(BI.LastSplitPoint); | 
|  | 896 | useIntv(SegStart, SegStop); | 
|  | 897 | overlapIntv(SegStop, BI.LastUse); | 
|  | 898 | } | 
| Jakob Stoklund Olesen | f1b05f2 | 2010-08-12 17:07:14 +0000 | [diff] [blame] | 899 | closeIntv(); | 
|  | 900 | } | 
| Jakob Stoklund Olesen | 7466927 | 2010-10-08 23:42:21 +0000 | [diff] [blame] | 901 | finish(); | 
| Jakob Stoklund Olesen | f1b05f2 | 2010-08-12 17:07:14 +0000 | [diff] [blame] | 902 | } |