blob: 8ae852c8abd70482714b4911ee69864355efc5f5 [file] [log] [blame]
Jim Stichnothd97c7df2014-06-04 11:57:08 -07001//===- subzero/src/IceRegAlloc.cpp - Linear-scan implementation -----------===//
2//
3// The Subzero Code Generator
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
Andrew Scull9612d322015-07-06 14:53:25 -07009///
10/// \file
Jim Stichnoth92a6e5b2015-12-02 16:52:44 -080011/// \brief Implements the LinearScan class, which performs the linear-scan
Andrew Sculld24cfda2015-08-25 10:31:15 -070012/// register allocation after liveness analysis has been performed.
Andrew Scull9612d322015-07-06 14:53:25 -070013///
Jim Stichnothd97c7df2014-06-04 11:57:08 -070014//===----------------------------------------------------------------------===//
15
John Porto67f8de92015-06-25 10:14:17 -070016#include "IceRegAlloc.h"
17
John Portoe82b5602016-02-24 15:58:55 -080018#include "IceBitVector.h"
Jim Stichnothd97c7df2014-06-04 11:57:08 -070019#include "IceCfg.h"
Jim Stichnoth87ff3a12014-11-14 10:27:29 -080020#include "IceCfgNode.h"
Jim Stichnothd97c7df2014-06-04 11:57:08 -070021#include "IceInst.h"
John Portoec3f5652015-08-31 15:07:09 -070022#include "IceInstVarIter.h"
Jim Stichnothd97c7df2014-06-04 11:57:08 -070023#include "IceOperand.h"
Jim Stichnothd97c7df2014-06-04 11:57:08 -070024#include "IceTargetLowering.h"
25
26namespace Ice {
27
Jim Stichnothad403532014-09-25 12:44:17 -070028namespace {
29
30// Returns true if Var has any definitions within Item's live range.
Andrew Sculld24cfda2015-08-25 10:31:15 -070031// TODO(stichnot): Consider trimming the Definitions list similar to how the
32// live ranges are trimmed, since all the overlapsDefs() tests are whether some
33// variable's definitions overlap Cur, and trimming is with respect Cur.start.
34// Initial tests show no measurable performance difference, so we'll keep the
35// code simple for now.
Jim Stichnoth5ce0abb2014-10-15 10:16:54 -070036bool overlapsDefs(const Cfg *Func, const Variable *Item, const Variable *Var) {
Jim Stichnotha3f57b92015-07-30 12:46:04 -070037 constexpr bool UseTrimmed = true;
Jim Stichnoth037fa1d2014-10-07 11:09:33 -070038 VariablesMetadata *VMetadata = Func->getVMetadata();
Jim Stichnoth877b04e2014-10-15 15:13:06 -070039 if (const Inst *FirstDef = VMetadata->getFirstDefinition(Var))
40 if (Item->getLiveRange().overlapsInst(FirstDef->getNumber(), UseTrimmed))
41 return true;
Jim Stichnoth48e3ae52015-10-01 13:33:35 -070042 for (const Inst *Def : VMetadata->getLatterDefinitions(Var)) {
43 if (Item->getLiveRange().overlapsInst(Def->getNumber(), UseTrimmed))
Jim Stichnothad403532014-09-25 12:44:17 -070044 return true;
45 }
46 return false;
47}
48
49void dumpDisableOverlap(const Cfg *Func, const Variable *Var,
50 const char *Reason) {
Jim Stichnoth20b71f52015-06-24 15:52:24 -070051 if (!BuildDefs::dump())
Karl Schimpfb6c96af2014-11-17 10:58:39 -080052 return;
Jim Stichnotha1da6ff2015-11-16 15:59:39 -080053 if (!Func->isVerbose(IceV_LinearScan))
54 return;
55
56 VariablesMetadata *VMetadata = Func->getVMetadata();
57 Ostream &Str = Func->getContext()->getStrDump();
58 Str << "Disabling Overlap due to " << Reason << " " << *Var
59 << " LIVE=" << Var->getLiveRange() << " Defs=";
60 if (const Inst *FirstDef = VMetadata->getFirstDefinition(Var))
61 Str << FirstDef->getNumber();
62 const InstDefList &Defs = VMetadata->getLatterDefinitions(Var);
63 for (size_t i = 0; i < Defs.size(); ++i) {
64 Str << "," << Defs[i]->getNumber();
Jim Stichnothad403532014-09-25 12:44:17 -070065 }
Jim Stichnotha1da6ff2015-11-16 15:59:39 -080066 Str << "\n";
Jim Stichnothad403532014-09-25 12:44:17 -070067}
68
Jim Stichnoth5ce0abb2014-10-15 10:16:54 -070069void dumpLiveRange(const Variable *Var, const Cfg *Func) {
Jim Stichnoth20b71f52015-06-24 15:52:24 -070070 if (!BuildDefs::dump())
Karl Schimpfb6c96af2014-11-17 10:58:39 -080071 return;
Jim Stichnoth5ce0abb2014-10-15 10:16:54 -070072 Ostream &Str = Func->getContext()->getStrDump();
Jim Stichnotha3f57b92015-07-30 12:46:04 -070073 char buf[30];
Jim Stichnoth8aa39662016-02-10 11:20:30 -080074 snprintf(buf, llvm::array_lengthof(buf), "%2u",
75 unsigned(Var->getRegNumTmp()));
Jim Stichnoth5ce0abb2014-10-15 10:16:54 -070076 Str << "R=" << buf << " V=";
77 Var->dump(Func);
78 Str << " Range=" << Var->getLiveRange();
Jim Stichnothe22f8232014-10-13 16:20:59 -070079}
80
Jim Stichnothb40595a2016-01-29 06:14:31 -080081int32_t findMinWeightIndex(
John Portoe82b5602016-02-24 15:58:55 -080082 const SmallBitVector &RegMask,
Jim Stichnothb40595a2016-01-29 06:14:31 -080083 const llvm::SmallVector<RegWeight, LinearScan::REGS_SIZE> &Weights) {
Jim Stichnoth8aa39662016-02-10 11:20:30 -080084 int MinWeightIndex = -1;
85 for (RegNumT i : RegNumBVIter(RegMask)) {
86 if (MinWeightIndex < 0 || Weights[i] < Weights[MinWeightIndex])
Jim Stichnothb40595a2016-01-29 06:14:31 -080087 MinWeightIndex = i;
88 }
Jim Stichnoth8aa39662016-02-10 11:20:30 -080089 assert(MinWeightIndex >= 0);
Jim Stichnothb40595a2016-01-29 06:14:31 -080090 return MinWeightIndex;
91}
92
Jim Stichnothad403532014-09-25 12:44:17 -070093} // end of anonymous namespace
94
Andrew Sculld24cfda2015-08-25 10:31:15 -070095LinearScan::LinearScan(Cfg *Func)
John Portobb0a5fe2015-09-04 11:23:41 -070096 : Func(Func), Ctx(Func->getContext()), Target(Func->getTarget()),
Jim Stichnothb40595a2016-01-29 06:14:31 -080097 Verbose(BuildDefs::dump() && Func->isVerbose(IceV_LinearScan)),
98 UseReserve(Ctx->getFlags().getRegAllocReserve()) {}
Andrew Sculld24cfda2015-08-25 10:31:15 -070099
Andrew Scull57e12682015-09-16 11:30:19 -0700100// Prepare for full register allocation of all variables. We depend on liveness
101// analysis to have calculated live ranges.
Jim Stichnoth70d0a052014-11-14 15:53:46 -0800102void LinearScan::initForGlobal() {
Jim Stichnoth87ff3a12014-11-14 10:27:29 -0800103 TimerMarker T(TimerStack::TT_initUnhandled, Func);
Jim Stichnoth70d0a052014-11-14 15:53:46 -0800104 FindPreference = true;
Jim Stichnotha3f57b92015-07-30 12:46:04 -0700105 // For full register allocation, normally we want to enable FindOverlap
106 // (meaning we look for opportunities for two overlapping live ranges to
Andrew Scull57e12682015-09-16 11:30:19 -0700107 // safely share the same register). However, we disable it for phi-lowering
Jim Stichnotha3f57b92015-07-30 12:46:04 -0700108 // register allocation since no overlap opportunities should be available and
109 // it's more expensive to look for opportunities.
110 FindOverlap = (Kind != RAK_Phi);
Jim Stichnoth87ff3a12014-11-14 10:27:29 -0800111 const VarList &Vars = Func->getVariables();
112 Unhandled.reserve(Vars.size());
Jim Stichnoth4ead35a2014-12-03 20:30:34 -0800113 UnhandledPrecolored.reserve(Vars.size());
Andrew Sculld24cfda2015-08-25 10:31:15 -0700114 // Gather the live ranges of all variables and add them to the Unhandled set.
Jim Stichnoth87ff3a12014-11-14 10:27:29 -0800115 for (Variable *Var : Vars) {
Jim Stichnoth4c5c5712015-11-16 17:17:48 -0800116 // Don't consider rematerializable variables.
117 if (Var->isRematerializable())
118 continue;
Andrew Sculld24cfda2015-08-25 10:31:15 -0700119 // Explicitly don't consider zero-weight variables, which are meant to be
120 // spill slots.
Andrew Scull11c9a322015-08-28 14:24:14 -0700121 if (Var->mustNotHaveReg())
Jim Stichnoth87ff3a12014-11-14 10:27:29 -0800122 continue;
Andrew Sculld24cfda2015-08-25 10:31:15 -0700123 // Don't bother if the variable has a null live range, which means it was
124 // never referenced.
Jim Stichnoth87ff3a12014-11-14 10:27:29 -0800125 if (Var->getLiveRange().isEmpty())
126 continue;
127 Var->untrimLiveRange();
128 Unhandled.push_back(Var);
129 if (Var->hasReg()) {
130 Var->setRegNumTmp(Var->getRegNum());
Andrew Scull11c9a322015-08-28 14:24:14 -0700131 Var->setMustHaveReg();
Jim Stichnoth87ff3a12014-11-14 10:27:29 -0800132 UnhandledPrecolored.push_back(Var);
133 }
134 }
Jim Stichnoth70d0a052014-11-14 15:53:46 -0800135
136 // Build the (ordered) list of FakeKill instruction numbers.
137 Kills.clear();
Jim Stichnotha3f57b92015-07-30 12:46:04 -0700138 // Phi lowering should not be creating new call instructions, so there should
139 // be no infinite-weight not-yet-colored live ranges that span a call
140 // instruction, hence no need to construct the Kills list.
141 if (Kind == RAK_Phi)
142 return;
Jim Stichnoth70d0a052014-11-14 15:53:46 -0800143 for (CfgNode *Node : Func->getNodes()) {
Jim Stichnoth29841e82014-12-23 12:26:24 -0800144 for (Inst &I : Node->getInsts()) {
Jim Stichnoth5bff61c2015-10-28 09:26:00 -0700145 if (auto *Kill = llvm::dyn_cast<InstFakeKill>(&I)) {
Jim Stichnoth70d0a052014-11-14 15:53:46 -0800146 if (!Kill->isDeleted() && !Kill->getLinked()->isDeleted())
Jim Stichnoth29841e82014-12-23 12:26:24 -0800147 Kills.push_back(I.getNumber());
Jim Stichnoth70d0a052014-11-14 15:53:46 -0800148 }
149 }
150 }
151}
152
Jim Stichnoth230d4102015-09-25 17:40:32 -0700153// Validate the integrity of the live ranges. If there are any errors, it
154// prints details and returns false. On success, it returns true.
155bool LinearScan::livenessValidateIntervals(
156 const DefUseErrorList &DefsWithoutUses,
157 const DefUseErrorList &UsesBeforeDefs,
158 const CfgVector<InstNumberT> &LRBegin,
Jim Stichnoth318f4cd2015-10-01 21:02:37 -0700159 const CfgVector<InstNumberT> &LREnd) const {
Jim Stichnoth230d4102015-09-25 17:40:32 -0700160 if (DefsWithoutUses.empty() && UsesBeforeDefs.empty())
161 return true;
162
163 if (!BuildDefs::dump())
164 return false;
165
166 const VarList &Vars = Func->getVariables();
167 OstreamLocker L(Ctx);
168 Ostream &Str = Ctx->getStrDump();
169 for (SizeT VarNum : DefsWithoutUses) {
170 Variable *Var = Vars[VarNum];
171 Str << "LR def without use, instruction " << LRBegin[VarNum]
172 << ", variable " << Var->getName(Func) << "\n";
173 }
174 for (SizeT VarNum : UsesBeforeDefs) {
175 Variable *Var = Vars[VarNum];
176 Str << "LR use before def, instruction " << LREnd[VarNum] << ", variable "
177 << Var->getName(Func) << "\n";
178 }
179 return false;
180}
181
Jim Stichnotha1da6ff2015-11-16 15:59:39 -0800182// Prepare for very simple register allocation of only infinite-weight Variables
183// while respecting pre-colored Variables. Some properties we take advantage of:
Jim Stichnoth70d0a052014-11-14 15:53:46 -0800184//
185// * Live ranges of interest consist of a single segment.
186//
187// * Live ranges of interest never span a call instruction.
188//
Andrew Sculld24cfda2015-08-25 10:31:15 -0700189// * Phi instructions are not considered because either phis have already been
190// lowered, or they don't contain any pre-colored or infinite-weight
191// Variables.
Jim Stichnoth70d0a052014-11-14 15:53:46 -0800192//
Jim Stichnotha1da6ff2015-11-16 15:59:39 -0800193// * We don't need to renumber instructions before computing live ranges because
194// all the high-level ICE instructions are deleted prior to lowering, and the
195// low-level instructions are added in monotonically increasing order.
Jim Stichnoth70d0a052014-11-14 15:53:46 -0800196//
Andrew Sculld24cfda2015-08-25 10:31:15 -0700197// * There are no opportunities for register preference or allowing overlap.
Jim Stichnoth70d0a052014-11-14 15:53:46 -0800198//
199// Some properties we aren't (yet) taking advantage of:
200//
Andrew Sculld24cfda2015-08-25 10:31:15 -0700201// * Because live ranges are a single segment, the Inactive set will always be
202// empty, and the live range trimming operation is unnecessary.
Jim Stichnoth70d0a052014-11-14 15:53:46 -0800203//
Jim Stichnotha1da6ff2015-11-16 15:59:39 -0800204// * Calculating overlap of single-segment live ranges could be optimized a bit.
Jim Stichnoth70d0a052014-11-14 15:53:46 -0800205void LinearScan::initForInfOnly() {
206 TimerMarker T(TimerStack::TT_initUnhandled, Func);
207 FindPreference = false;
208 FindOverlap = false;
209 SizeT NumVars = 0;
210 const VarList &Vars = Func->getVariables();
211
Andrew Sculld24cfda2015-08-25 10:31:15 -0700212 // Iterate across all instructions and record the begin and end of the live
213 // range for each variable that is pre-colored or infinite weight.
Andrew Scull00741a02015-09-16 19:04:09 -0700214 CfgVector<InstNumberT> LRBegin(Vars.size(), Inst::NumberSentinel);
215 CfgVector<InstNumberT> LREnd(Vars.size(), Inst::NumberSentinel);
Jim Stichnoth230d4102015-09-25 17:40:32 -0700216 DefUseErrorList DefsWithoutUses, UsesBeforeDefs;
Jim Stichnoth70d0a052014-11-14 15:53:46 -0800217 for (CfgNode *Node : Func->getNodes()) {
Jim Stichnoth8cfeb692016-02-05 09:50:02 -0800218 for (Inst &Instr : Node->getInsts()) {
219 if (Instr.isDeleted())
Jim Stichnoth70d0a052014-11-14 15:53:46 -0800220 continue;
Jim Stichnoth8cfeb692016-02-05 09:50:02 -0800221 FOREACH_VAR_IN_INST(Var, Instr) {
Jim Stichnoth4c5c5712015-11-16 17:17:48 -0800222 if (Var->isRematerializable())
223 continue;
Jim Stichnoth230d4102015-09-25 17:40:32 -0700224 if (Var->getIgnoreLiveness())
225 continue;
226 if (Var->hasReg() || Var->mustHaveReg()) {
227 SizeT VarNum = Var->getIndex();
Jim Stichnoth8cfeb692016-02-05 09:50:02 -0800228 LREnd[VarNum] = Instr.getNumber();
Jim Stichnoth230d4102015-09-25 17:40:32 -0700229 if (!Var->getIsArg() && LRBegin[VarNum] == Inst::NumberSentinel)
230 UsesBeforeDefs.push_back(VarNum);
231 }
232 }
Jim Stichnoth8cfeb692016-02-05 09:50:02 -0800233 if (const Variable *Var = Instr.getDest()) {
Jim Stichnoth4c5c5712015-11-16 17:17:48 -0800234 if (!Var->isRematerializable() && !Var->getIgnoreLiveness() &&
Andrew Scull11c9a322015-08-28 14:24:14 -0700235 (Var->hasReg() || Var->mustHaveReg())) {
Jim Stichnoth70d0a052014-11-14 15:53:46 -0800236 if (LRBegin[Var->getIndex()] == Inst::NumberSentinel) {
Jim Stichnoth8cfeb692016-02-05 09:50:02 -0800237 LRBegin[Var->getIndex()] = Instr.getNumber();
Jim Stichnoth70d0a052014-11-14 15:53:46 -0800238 ++NumVars;
239 }
240 }
241 }
Jim Stichnoth70d0a052014-11-14 15:53:46 -0800242 }
243 }
244
245 Unhandled.reserve(NumVars);
Jim Stichnoth4ead35a2014-12-03 20:30:34 -0800246 UnhandledPrecolored.reserve(NumVars);
Jim Stichnoth70d0a052014-11-14 15:53:46 -0800247 for (SizeT i = 0; i < Vars.size(); ++i) {
248 Variable *Var = Vars[i];
Jim Stichnoth4c5c5712015-11-16 17:17:48 -0800249 if (Var->isRematerializable())
250 continue;
Jim Stichnoth70d0a052014-11-14 15:53:46 -0800251 if (LRBegin[i] != Inst::NumberSentinel) {
Jim Stichnoth230d4102015-09-25 17:40:32 -0700252 if (LREnd[i] == Inst::NumberSentinel) {
253 DefsWithoutUses.push_back(i);
254 continue;
255 }
Jim Stichnoth70d0a052014-11-14 15:53:46 -0800256 Unhandled.push_back(Var);
257 Var->resetLiveRange();
Andrew Scull11c9a322015-08-28 14:24:14 -0700258 Var->addLiveRange(LRBegin[i], LREnd[i]);
Jim Stichnoth70d0a052014-11-14 15:53:46 -0800259 Var->untrimLiveRange();
260 if (Var->hasReg()) {
261 Var->setRegNumTmp(Var->getRegNum());
Andrew Scull11c9a322015-08-28 14:24:14 -0700262 Var->setMustHaveReg();
Jim Stichnoth70d0a052014-11-14 15:53:46 -0800263 UnhandledPrecolored.push_back(Var);
264 }
265 --NumVars;
266 }
267 }
Jim Stichnoth230d4102015-09-25 17:40:32 -0700268
269 if (!livenessValidateIntervals(DefsWithoutUses, UsesBeforeDefs, LRBegin,
270 LREnd)) {
271 llvm::report_fatal_error("initForInfOnly: Liveness error");
272 return;
273 }
274
275 if (!DefsWithoutUses.empty() || !UsesBeforeDefs.empty()) {
276 if (BuildDefs::dump()) {
277 OstreamLocker L(Ctx);
278 Ostream &Str = Ctx->getStrDump();
279 for (SizeT VarNum : DefsWithoutUses) {
280 Variable *Var = Vars[VarNum];
281 Str << "LR def without use, instruction " << LRBegin[VarNum]
282 << ", variable " << Var->getName(Func) << "\n";
283 }
284 for (SizeT VarNum : UsesBeforeDefs) {
285 Variable *Var = Vars[VarNum];
286 Str << "LR use before def, instruction " << LREnd[VarNum]
287 << ", variable " << Var->getName(Func) << "\n";
288 }
289 }
290 llvm::report_fatal_error("initForInfOnly: Liveness error");
291 }
Andrew Sculld24cfda2015-08-25 10:31:15 -0700292 // This isn't actually a fatal condition, but it would be nice to know if we
293 // somehow pre-calculated Unhandled's size wrong.
Jim Stichnoth70d0a052014-11-14 15:53:46 -0800294 assert(NumVars == 0);
295
Andrew Sculld24cfda2015-08-25 10:31:15 -0700296 // Don't build up the list of Kills because we know that no infinite-weight
297 // Variable has a live range spanning a call.
Jim Stichnoth70d0a052014-11-14 15:53:46 -0800298 Kills.clear();
299}
300
Jim Stichnoth4001c932015-10-09 14:33:26 -0700301void LinearScan::initForSecondChance() {
302 TimerMarker T(TimerStack::TT_initUnhandled, Func);
303 FindPreference = true;
304 FindOverlap = true;
305 const VarList &Vars = Func->getVariables();
306 Unhandled.reserve(Vars.size());
307 UnhandledPrecolored.reserve(Vars.size());
308 for (Variable *Var : Vars) {
Jim Stichnoth4c5c5712015-11-16 17:17:48 -0800309 if (Var->isRematerializable())
310 continue;
Jim Stichnoth4001c932015-10-09 14:33:26 -0700311 if (Var->hasReg()) {
312 Var->untrimLiveRange();
313 Var->setRegNumTmp(Var->getRegNum());
314 Var->setMustHaveReg();
315 UnhandledPrecolored.push_back(Var);
316 Unhandled.push_back(Var);
317 }
318 }
319 for (Variable *Var : Evicted) {
320 Var->untrimLiveRange();
321 Unhandled.push_back(Var);
322 }
323}
324
Jim Stichnoth70d0a052014-11-14 15:53:46 -0800325void LinearScan::init(RegAllocKind Kind) {
Jim Stichnotha3f57b92015-07-30 12:46:04 -0700326 this->Kind = Kind;
Jim Stichnoth70d0a052014-11-14 15:53:46 -0800327 Unhandled.clear();
328 UnhandledPrecolored.clear();
329 Handled.clear();
330 Inactive.clear();
331 Active.clear();
332
John Portobb0a5fe2015-09-04 11:23:41 -0700333 SizeT NumRegs = Target->getNumRegisters();
334 RegAliases.resize(NumRegs);
335 for (SizeT Reg = 0; Reg < NumRegs; ++Reg) {
Jim Stichnoth8aa39662016-02-10 11:20:30 -0800336 RegAliases[Reg] = &Target->getAliasesForRegister(RegNumT::fromInt(Reg));
John Portobb0a5fe2015-09-04 11:23:41 -0700337 }
338
Jim Stichnoth70d0a052014-11-14 15:53:46 -0800339 switch (Kind) {
Jim Stichnotha3f57b92015-07-30 12:46:04 -0700340 case RAK_Unknown:
341 llvm::report_fatal_error("Invalid RAK_Unknown");
342 break;
Jim Stichnoth70d0a052014-11-14 15:53:46 -0800343 case RAK_Global:
Jim Stichnotha3f57b92015-07-30 12:46:04 -0700344 case RAK_Phi:
Jim Stichnoth70d0a052014-11-14 15:53:46 -0800345 initForGlobal();
346 break;
347 case RAK_InfOnly:
348 initForInfOnly();
349 break;
Jim Stichnoth4001c932015-10-09 14:33:26 -0700350 case RAK_SecondChance:
351 initForSecondChance();
352 break;
Jim Stichnoth70d0a052014-11-14 15:53:46 -0800353 }
354
Jim Stichnoth4001c932015-10-09 14:33:26 -0700355 Evicted.clear();
356
Jim Stichnoth992f91d2015-08-10 11:18:38 -0700357 auto CompareRanges = [](const Variable *L, const Variable *R) {
Qining Luaee5fa82015-08-20 14:59:03 -0700358 InstNumberT Lstart = L->getLiveRange().getStart();
359 InstNumberT Rstart = R->getLiveRange().getStart();
360 if (Lstart == Rstart)
361 return L->getIndex() < R->getIndex();
362 return Lstart < Rstart;
Jim Stichnoth87ff3a12014-11-14 10:27:29 -0800363 };
364 // Do a reverse sort so that erasing elements (from the end) is fast.
Jim Stichnoth992f91d2015-08-10 11:18:38 -0700365 std::sort(Unhandled.rbegin(), Unhandled.rend(), CompareRanges);
Jim Stichnoth87ff3a12014-11-14 10:27:29 -0800366 std::sort(UnhandledPrecolored.rbegin(), UnhandledPrecolored.rend(),
Jim Stichnoth992f91d2015-08-10 11:18:38 -0700367 CompareRanges);
Jim Stichnoth4ead35a2014-12-03 20:30:34 -0800368
369 Handled.reserve(Unhandled.size());
370 Inactive.reserve(Unhandled.size());
371 Active.reserve(Unhandled.size());
Jim Stichnoth4001c932015-10-09 14:33:26 -0700372 Evicted.reserve(Unhandled.size());
Jim Stichnoth87ff3a12014-11-14 10:27:29 -0800373}
374
Jim Stichnotha3f57b92015-07-30 12:46:04 -0700375// This is called when Cur must be allocated a register but no registers are
Jim Stichnotha1da6ff2015-11-16 15:59:39 -0800376// available across Cur's live range. To handle this, we find a register that is
377// not explicitly used during Cur's live range, spill that register to a stack
378// location right before Cur's live range begins, and fill (reload) the register
379// from the stack location right after Cur's live range ends.
Andrew Sculld24cfda2015-08-25 10:31:15 -0700380void LinearScan::addSpillFill(IterationState &Iter) {
381 // Identify the actual instructions that begin and end Iter.Cur's live range.
382 // Iterate through Iter.Cur's node's instruction list until we find the actual
383 // instructions with instruction numbers corresponding to Iter.Cur's recorded
384 // live range endpoints. This sounds inefficient but shouldn't be a problem
385 // in practice because:
Jim Stichnotha3f57b92015-07-30 12:46:04 -0700386 // (1) This function is almost never called in practice.
387 // (2) Since this register over-subscription problem happens only for
388 // phi-lowered instructions, the number of instructions in the node is
389 // proportional to the number of phi instructions in the original node,
390 // which is never very large in practice.
Andrew Sculld24cfda2015-08-25 10:31:15 -0700391 // (3) We still have to iterate through all instructions of Iter.Cur's live
392 // range to find all explicitly used registers (though the live range is
393 // usually only 2-3 instructions), so the main cost that could be avoided
394 // would be finding the instruction that begin's Iter.Cur's live range.
395 assert(!Iter.Cur->getLiveRange().isEmpty());
396 InstNumberT Start = Iter.Cur->getLiveRange().getStart();
397 InstNumberT End = Iter.Cur->getLiveRange().getEnd();
398 CfgNode *Node = Func->getVMetadata()->getLocalUseNode(Iter.Cur);
Jim Stichnotha3f57b92015-07-30 12:46:04 -0700399 assert(Node);
400 InstList &Insts = Node->getInsts();
401 InstList::iterator SpillPoint = Insts.end();
402 InstList::iterator FillPoint = Insts.end();
403 // Stop searching after we have found both the SpillPoint and the FillPoint.
404 for (auto I = Insts.begin(), E = Insts.end();
405 I != E && (SpillPoint == E || FillPoint == E); ++I) {
406 if (I->getNumber() == Start)
407 SpillPoint = I;
408 if (I->getNumber() == End)
409 FillPoint = I;
410 if (SpillPoint != E) {
Jim Stichnotha1da6ff2015-11-16 15:59:39 -0800411 // Remove from RegMask any physical registers referenced during Cur's live
412 // range. Start looking after SpillPoint gets set, i.e. once Cur's live
413 // range begins.
John Portoec3f5652015-08-31 15:07:09 -0700414 FOREACH_VAR_IN_INST(Var, *I) {
John Portobb0a5fe2015-09-04 11:23:41 -0700415 if (!Var->hasRegTmp())
416 continue;
John Portoe82b5602016-02-24 15:58:55 -0800417 const auto &Aliases = *RegAliases[Var->getRegNumTmp()];
Jim Stichnoth8aa39662016-02-10 11:20:30 -0800418 for (RegNumT RegAlias : RegNumBVIter(Aliases)) {
John Portobb0a5fe2015-09-04 11:23:41 -0700419 Iter.RegMask[RegAlias] = false;
420 }
Jim Stichnotha3f57b92015-07-30 12:46:04 -0700421 }
422 }
423 }
424 assert(SpillPoint != Insts.end());
425 assert(FillPoint != Insts.end());
426 ++FillPoint;
Jim Stichnoth8aa39662016-02-10 11:20:30 -0800427 // TODO(stichnot): Randomize instead of *.begin() which maps to find_first().
428 const RegNumT RegNum = *RegNumBVIter(Iter.RegMask).begin();
Andrew Sculld24cfda2015-08-25 10:31:15 -0700429 Iter.Cur->setRegNumTmp(RegNum);
Andrew Sculld24cfda2015-08-25 10:31:15 -0700430 Variable *Preg = Target->getPhysicalRegister(RegNum, Iter.Cur->getType());
Jim Stichnotha1da6ff2015-11-16 15:59:39 -0800431 // TODO(stichnot): Add SpillLoc to VariablesMetadata tracking so that SpillLoc
432 // is correctly identified as !isMultiBlock(), reducing stack frame size.
Andrew Sculld24cfda2015-08-25 10:31:15 -0700433 Variable *SpillLoc = Func->makeVariable(Iter.Cur->getType());
Jim Stichnotha3f57b92015-07-30 12:46:04 -0700434 // Add "reg=FakeDef;spill=reg" before SpillPoint
435 Target->lowerInst(Node, SpillPoint, InstFakeDef::create(Func, Preg));
436 Target->lowerInst(Node, SpillPoint, InstAssign::create(Func, SpillLoc, Preg));
437 // add "reg=spill;FakeUse(reg)" before FillPoint
438 Target->lowerInst(Node, FillPoint, InstAssign::create(Func, Preg, SpillLoc));
439 Target->lowerInst(Node, FillPoint, InstFakeUse::create(Func, Preg));
440}
441
Andrew Sculld24cfda2015-08-25 10:31:15 -0700442void LinearScan::handleActiveRangeExpiredOrInactive(const Variable *Cur) {
443 for (SizeT I = Active.size(); I > 0; --I) {
444 const SizeT Index = I - 1;
445 Variable *Item = Active[Index];
446 Item->trimLiveRange(Cur->getLiveRange().getStart());
447 bool Moved = false;
448 if (Item->rangeEndsBefore(Cur)) {
449 // Move Item from Active to Handled list.
Jim Stichnoth69660552015-09-18 06:41:02 -0700450 dumpLiveRangeTrace("Expiring ", Item);
Andrew Sculld24cfda2015-08-25 10:31:15 -0700451 moveItem(Active, Index, Handled);
452 Moved = true;
453 } else if (!Item->rangeOverlapsStart(Cur)) {
454 // Move Item from Active to Inactive list.
Jim Stichnoth69660552015-09-18 06:41:02 -0700455 dumpLiveRangeTrace("Inactivating ", Item);
Andrew Sculld24cfda2015-08-25 10:31:15 -0700456 moveItem(Active, Index, Inactive);
457 Moved = true;
458 }
459 if (Moved) {
460 // Decrement Item from RegUses[].
461 assert(Item->hasRegTmp());
John Portoe82b5602016-02-24 15:58:55 -0800462 const auto &Aliases = *RegAliases[Item->getRegNumTmp()];
Jim Stichnoth8aa39662016-02-10 11:20:30 -0800463 for (RegNumT RegAlias : RegNumBVIter(Aliases)) {
John Portobb0a5fe2015-09-04 11:23:41 -0700464 --RegUses[RegAlias];
465 assert(RegUses[RegAlias] >= 0);
466 }
Jim Stichnothe6d24782014-12-19 05:42:24 -0800467 }
468 }
Andrew Sculld24cfda2015-08-25 10:31:15 -0700469}
Jim Stichnothd97c7df2014-06-04 11:57:08 -0700470
Andrew Sculld24cfda2015-08-25 10:31:15 -0700471void LinearScan::handleInactiveRangeExpiredOrReactivated(const Variable *Cur) {
472 for (SizeT I = Inactive.size(); I > 0; --I) {
473 const SizeT Index = I - 1;
474 Variable *Item = Inactive[Index];
475 Item->trimLiveRange(Cur->getLiveRange().getStart());
476 if (Item->rangeEndsBefore(Cur)) {
477 // Move Item from Inactive to Handled list.
Jim Stichnoth69660552015-09-18 06:41:02 -0700478 dumpLiveRangeTrace("Expiring ", Item);
Andrew Sculld24cfda2015-08-25 10:31:15 -0700479 moveItem(Inactive, Index, Handled);
480 } else if (Item->rangeOverlapsStart(Cur)) {
481 // Move Item from Inactive to Active list.
Jim Stichnoth69660552015-09-18 06:41:02 -0700482 dumpLiveRangeTrace("Reactivating ", Item);
Andrew Sculld24cfda2015-08-25 10:31:15 -0700483 moveItem(Inactive, Index, Active);
484 // Increment Item in RegUses[].
485 assert(Item->hasRegTmp());
John Portoe82b5602016-02-24 15:58:55 -0800486 const auto &Aliases = *RegAliases[Item->getRegNumTmp()];
Jim Stichnoth8aa39662016-02-10 11:20:30 -0800487 for (RegNumT RegAlias : RegNumBVIter(Aliases)) {
John Portobb0a5fe2015-09-04 11:23:41 -0700488 assert(RegUses[RegAlias] >= 0);
489 ++RegUses[RegAlias];
490 }
Jim Stichnothd97c7df2014-06-04 11:57:08 -0700491 }
Andrew Sculld24cfda2015-08-25 10:31:15 -0700492 }
493}
Jim Stichnothd97c7df2014-06-04 11:57:08 -0700494
Andrew Sculld24cfda2015-08-25 10:31:15 -0700495// Infer register preference and allowable overlap. Only form a preference when
Jim Stichnotha1da6ff2015-11-16 15:59:39 -0800496// the current Variable has an unambiguous "first" definition. The preference is
497// some source Variable of the defining instruction that either is assigned a
498// register that is currently free, or that is assigned a register that is not
499// free but overlap is allowed. Overlap is allowed when the Variable under
500// consideration is single-definition, and its definition is a simple assignment
501// - i.e., the register gets copied/aliased but is never modified. Furthermore,
502// overlap is only allowed when preferred Variable definition instructions do
503// not appear within the current Variable's live range.
Andrew Sculld24cfda2015-08-25 10:31:15 -0700504void LinearScan::findRegisterPreference(IterationState &Iter) {
505 Iter.Prefer = nullptr;
Reed Kotler5fa0a5f2016-02-15 20:01:24 -0800506 Iter.PreferReg = RegNumT();
Andrew Sculld24cfda2015-08-25 10:31:15 -0700507 Iter.AllowOverlap = false;
508
Jim Stichnotha1da6ff2015-11-16 15:59:39 -0800509 if (!FindPreference)
510 return;
511
512 VariablesMetadata *VMetadata = Func->getVMetadata();
513 const Inst *DefInst = VMetadata->getFirstDefinitionSingleBlock(Iter.Cur);
514 if (DefInst == nullptr)
515 return;
516
517 assert(DefInst->getDest() == Iter.Cur);
518 const bool IsSingleDefAssign =
519 DefInst->isVarAssign() && !VMetadata->isMultiDef(Iter.Cur);
520 FOREACH_VAR_IN_INST(SrcVar, *DefInst) {
521 // Only consider source variables that have (so far) been assigned a
522 // register.
523 if (!SrcVar->hasRegTmp())
524 continue;
525
526 // That register must be one in the RegMask set, e.g. don't try to prefer
527 // the stack pointer as a result of the stacksave intrinsic.
John Portoe82b5602016-02-24 15:58:55 -0800528 const auto &Aliases = *RegAliases[SrcVar->getRegNumTmp()];
Jim Stichnoth8aa39662016-02-10 11:20:30 -0800529 const int SrcReg = (Iter.RegMask & Aliases).find_first();
Jim Stichnotha1da6ff2015-11-16 15:59:39 -0800530 if (SrcReg == -1)
531 continue;
532
533 if (FindOverlap && IsSingleDefAssign && !Iter.Free[SrcReg]) {
534 // Don't bother trying to enable AllowOverlap if the register is already
535 // free (hence the test on Iter.Free[SrcReg]).
536 Iter.AllowOverlap = !overlapsDefs(Func, Iter.Cur, SrcVar);
Andrew Sculld24cfda2015-08-25 10:31:15 -0700537 }
Jim Stichnotha1da6ff2015-11-16 15:59:39 -0800538 if (Iter.AllowOverlap || Iter.Free[SrcReg]) {
539 Iter.Prefer = SrcVar;
Jim Stichnoth8aa39662016-02-10 11:20:30 -0800540 Iter.PreferReg = RegNumT::fromInt(SrcReg);
Jim Stichnotha1da6ff2015-11-16 15:59:39 -0800541 // Stop looking for a preference after the first valid preference is
542 // found. One might think that we should look at all instruction
543 // variables to find the best <Prefer,AllowOverlap> combination, but note
544 // that AllowOverlap can only be true for a simple assignment statement
545 // which can have only one source operand, so it's not possible for
546 // AllowOverlap to be true beyond the first source operand.
547 FOREACH_VAR_IN_INST_BREAK;
548 }
549 }
550 if (BuildDefs::dump() && Verbose && Iter.Prefer) {
551 Ostream &Str = Ctx->getStrDump();
552 Str << "Initial Iter.Prefer=";
553 Iter.Prefer->dump(Func);
554 Str << " R=" << Iter.PreferReg << " LIVE=" << Iter.Prefer->getLiveRange()
555 << " Overlap=" << Iter.AllowOverlap << "\n";
Andrew Sculld24cfda2015-08-25 10:31:15 -0700556 }
557}
558
Jim Stichnothb40595a2016-01-29 06:14:31 -0800559// Remove registers from the Iter.Free[] list where an Inactive range overlaps
560// with the current range.
Andrew Sculld24cfda2015-08-25 10:31:15 -0700561void LinearScan::filterFreeWithInactiveRanges(IterationState &Iter) {
562 for (const Variable *Item : Inactive) {
John Portobb0a5fe2015-09-04 11:23:41 -0700563 if (!Item->rangeOverlaps(Iter.Cur))
564 continue;
John Portoe82b5602016-02-24 15:58:55 -0800565 const auto &Aliases = *RegAliases[Item->getRegNumTmp()];
Jim Stichnoth8aa39662016-02-10 11:20:30 -0800566 for (RegNumT RegAlias : RegNumBVIter(Aliases)) {
567 // Don't assert(Iter.Free[RegAlias]) because in theory (though probably
Jim Stichnothb40595a2016-01-29 06:14:31 -0800568 // never in practice) there could be two inactive variables that were
569 // marked with AllowOverlap.
John Portobb0a5fe2015-09-04 11:23:41 -0700570 Iter.Free[RegAlias] = false;
Jim Stichnothb40595a2016-01-29 06:14:31 -0800571 Iter.FreeUnfiltered[RegAlias] = false;
Andrew Sculld24cfda2015-08-25 10:31:15 -0700572 // Disable AllowOverlap if an Inactive variable, which is not Prefer,
Jim Stichnotha1da6ff2015-11-16 15:59:39 -0800573 // shares Prefer's register, and has a definition within Cur's live range.
Andrew Sculld24cfda2015-08-25 10:31:15 -0700574 if (Iter.AllowOverlap && Item != Iter.Prefer &&
John Portobb0a5fe2015-09-04 11:23:41 -0700575 RegAlias == Iter.PreferReg && overlapsDefs(Func, Iter.Cur, Item)) {
Andrew Sculld24cfda2015-08-25 10:31:15 -0700576 Iter.AllowOverlap = false;
577 dumpDisableOverlap(Func, Item, "Inactive");
578 }
579 }
580 }
581}
582
Jim Stichnothb40595a2016-01-29 06:14:31 -0800583// Remove registers from the Iter.Free[] list where an Unhandled pre-colored
584// range overlaps with the current range, and set those registers to infinite
585// weight so that they aren't candidates for eviction.
586// Cur->rangeEndsBefore(Item) is an early exit check that turns a guaranteed
587// O(N^2) algorithm into expected linear complexity.
Andrew Sculld24cfda2015-08-25 10:31:15 -0700588void LinearScan::filterFreeWithPrecoloredRanges(IterationState &Iter) {
Jim Stichnoth4c5c5712015-11-16 17:17:48 -0800589 // TODO(stichnot): Partition UnhandledPrecolored according to register class,
590 // to restrict the number of overlap comparisons needed.
Andrew Sculld24cfda2015-08-25 10:31:15 -0700591 for (Variable *Item : reverse_range(UnhandledPrecolored)) {
592 assert(Item->hasReg());
593 if (Iter.Cur->rangeEndsBefore(Item))
594 break;
Jim Stichnotha1da6ff2015-11-16 15:59:39 -0800595 if (!Item->rangeOverlaps(Iter.Cur))
596 continue;
John Portoe82b5602016-02-24 15:58:55 -0800597 const auto &Aliases =
Jim Stichnotha1da6ff2015-11-16 15:59:39 -0800598 *RegAliases[Item->getRegNum()]; // Note: not getRegNumTmp()
Jim Stichnoth8aa39662016-02-10 11:20:30 -0800599 for (RegNumT RegAlias : RegNumBVIter(Aliases)) {
Jim Stichnotha1da6ff2015-11-16 15:59:39 -0800600 Iter.Weights[RegAlias].setWeight(RegWeight::Inf);
601 Iter.Free[RegAlias] = false;
Jim Stichnothb40595a2016-01-29 06:14:31 -0800602 Iter.FreeUnfiltered[RegAlias] = false;
Jim Stichnotha1da6ff2015-11-16 15:59:39 -0800603 Iter.PrecoloredUnhandledMask[RegAlias] = true;
604 // Disable Iter.AllowOverlap if the preferred register is one of these
605 // pre-colored unhandled overlapping ranges.
606 if (Iter.AllowOverlap && RegAlias == Iter.PreferReg) {
607 Iter.AllowOverlap = false;
608 dumpDisableOverlap(Func, Item, "PrecoloredUnhandled");
Andrew Sculld24cfda2015-08-25 10:31:15 -0700609 }
610 }
611 }
612}
613
614void LinearScan::allocatePrecoloredRegister(Variable *Cur) {
Jim Stichnoth8aa39662016-02-10 11:20:30 -0800615 const auto RegNum = Cur->getRegNum();
Andrew Sculld24cfda2015-08-25 10:31:15 -0700616 // RegNumTmp should have already been set above.
617 assert(Cur->getRegNumTmp() == RegNum);
618 dumpLiveRangeTrace("Precoloring ", Cur);
619 Active.push_back(Cur);
John Portoe82b5602016-02-24 15:58:55 -0800620 const auto &Aliases = *RegAliases[RegNum];
Jim Stichnoth8aa39662016-02-10 11:20:30 -0800621 for (RegNumT RegAlias : RegNumBVIter(Aliases)) {
John Portobb0a5fe2015-09-04 11:23:41 -0700622 assert(RegUses[RegAlias] >= 0);
623 ++RegUses[RegAlias];
624 }
Andrew Sculld24cfda2015-08-25 10:31:15 -0700625 assert(!UnhandledPrecolored.empty());
626 assert(UnhandledPrecolored.back() == Cur);
627 UnhandledPrecolored.pop_back();
628}
629
630void LinearScan::allocatePreferredRegister(IterationState &Iter) {
631 Iter.Cur->setRegNumTmp(Iter.PreferReg);
632 dumpLiveRangeTrace("Preferring ", Iter.Cur);
John Portoe82b5602016-02-24 15:58:55 -0800633 const auto &Aliases = *RegAliases[Iter.PreferReg];
Jim Stichnoth8aa39662016-02-10 11:20:30 -0800634 for (RegNumT RegAlias : RegNumBVIter(Aliases)) {
John Portobb0a5fe2015-09-04 11:23:41 -0700635 assert(RegUses[RegAlias] >= 0);
636 ++RegUses[RegAlias];
637 }
Andrew Sculld24cfda2015-08-25 10:31:15 -0700638 Active.push_back(Iter.Cur);
639}
640
Jim Stichnothb40595a2016-01-29 06:14:31 -0800641void LinearScan::allocateFreeRegister(IterationState &Iter, bool Filtered) {
Jim Stichnoth8aa39662016-02-10 11:20:30 -0800642 const RegNumT RegNum =
643 *RegNumBVIter(Filtered ? Iter.Free : Iter.FreeUnfiltered).begin();
Andrew Sculld24cfda2015-08-25 10:31:15 -0700644 Iter.Cur->setRegNumTmp(RegNum);
Jim Stichnothb40595a2016-01-29 06:14:31 -0800645 if (Filtered)
John Porto4b6e4b42016-02-17 05:00:59 -0800646 dumpLiveRangeTrace("Allocating Y ", Iter.Cur);
Jim Stichnothb40595a2016-01-29 06:14:31 -0800647 else
648 dumpLiveRangeTrace("Allocating X ", Iter.Cur);
John Portoe82b5602016-02-24 15:58:55 -0800649 const auto &Aliases = *RegAliases[RegNum];
Jim Stichnoth8aa39662016-02-10 11:20:30 -0800650 for (RegNumT RegAlias : RegNumBVIter(Aliases)) {
John Portobb0a5fe2015-09-04 11:23:41 -0700651 assert(RegUses[RegAlias] >= 0);
652 ++RegUses[RegAlias];
653 }
Andrew Sculld24cfda2015-08-25 10:31:15 -0700654 Active.push_back(Iter.Cur);
655}
656
657void LinearScan::handleNoFreeRegisters(IterationState &Iter) {
658 // Check Active ranges.
659 for (const Variable *Item : Active) {
660 assert(Item->rangeOverlaps(Iter.Cur));
Andrew Sculld24cfda2015-08-25 10:31:15 -0700661 assert(Item->hasRegTmp());
John Portoe82b5602016-02-24 15:58:55 -0800662 const auto &Aliases = *RegAliases[Item->getRegNumTmp()];
John Portobb0a5fe2015-09-04 11:23:41 -0700663 // We add the Item's weight to each alias/subregister to represent that,
664 // should we decide to pick any of them, then we would incur that many
665 // memory accesses.
666 RegWeight W = Item->getWeight(Func);
Jim Stichnoth8aa39662016-02-10 11:20:30 -0800667 for (RegNumT RegAlias : RegNumBVIter(Aliases)) {
John Portobb0a5fe2015-09-04 11:23:41 -0700668 Iter.Weights[RegAlias].addWeight(W);
669 }
Andrew Sculld24cfda2015-08-25 10:31:15 -0700670 }
671 // Same as above, but check Inactive ranges instead of Active.
672 for (const Variable *Item : Inactive) {
John Portobb0a5fe2015-09-04 11:23:41 -0700673 if (!Item->rangeOverlaps(Iter.Cur))
674 continue;
Andrew Sculld24cfda2015-08-25 10:31:15 -0700675 assert(Item->hasRegTmp());
John Portoe82b5602016-02-24 15:58:55 -0800676 const auto &Aliases = *RegAliases[Item->getRegNumTmp()];
John Portobb0a5fe2015-09-04 11:23:41 -0700677 RegWeight W = Item->getWeight(Func);
Jim Stichnoth8aa39662016-02-10 11:20:30 -0800678 for (RegNumT RegAlias : RegNumBVIter(Aliases)) {
John Portobb0a5fe2015-09-04 11:23:41 -0700679 Iter.Weights[RegAlias].addWeight(W);
680 }
Andrew Sculld24cfda2015-08-25 10:31:15 -0700681 }
682
Jim Stichnotha1da6ff2015-11-16 15:59:39 -0800683 // All the weights are now calculated. Find the register with smallest weight.
Jim Stichnothb40595a2016-01-29 06:14:31 -0800684 int32_t MinWeightIndex = findMinWeightIndex(Iter.RegMask, Iter.Weights);
Andrew Sculld24cfda2015-08-25 10:31:15 -0700685
Andrew Scull11c9a322015-08-28 14:24:14 -0700686 if (Iter.Cur->getWeight(Func) <= Iter.Weights[MinWeightIndex]) {
Jim Stichnothb40595a2016-01-29 06:14:31 -0800687 if (!Iter.Cur->mustHaveReg()) {
688 // Iter.Cur doesn't have priority over any other live ranges, so don't
689 // allocate any register to it, and move it to the Handled state.
690 Handled.push_back(Iter.Cur);
691 return;
692 }
693 if (Kind == RAK_Phi) {
694 // Iter.Cur is infinite-weight but all physical registers are already
695 // taken, so we need to force one to be temporarily available.
696 addSpillFill(Iter);
697 Handled.push_back(Iter.Cur);
698 return;
699 }
700 // The remaining portion of the enclosing "if" block should only be
701 // reachable if we are manually limiting physical registers for testing.
702 if (UseReserve) {
703 if (Iter.FreeUnfiltered.any()) {
704 // There is some available physical register held in reserve, so use it.
705 constexpr bool NotFiltered = false;
706 allocateFreeRegister(Iter, NotFiltered);
707 // Iter.Cur is now on the Active list.
708 return;
Jim Stichnoth2544d4d2016-01-22 13:07:46 -0800709 }
Jim Stichnothb40595a2016-01-29 06:14:31 -0800710 // At this point, we need to find some reserve register that is already
711 // assigned to a non-infinite-weight variable. This could happen if some
712 // variable was previously assigned an alias of such a register.
713 MinWeightIndex = findMinWeightIndex(Iter.RegMaskUnfiltered, Iter.Weights);
Andrew Sculld24cfda2015-08-25 10:31:15 -0700714 }
Jim Stichnothb40595a2016-01-29 06:14:31 -0800715 if (Iter.Cur->getWeight(Func) <= Iter.Weights[MinWeightIndex]) {
716 dumpLiveRangeTrace("Failing ", Iter.Cur);
717 Func->setError("Unable to find a physical register for an "
718 "infinite-weight live range "
719 "(consider using -reg-reserve): " +
720 Iter.Cur->getName(Func));
721 Handled.push_back(Iter.Cur);
722 return;
Jim Stichnothd97c7df2014-06-04 11:57:08 -0700723 }
Jim Stichnothb40595a2016-01-29 06:14:31 -0800724 // At this point, MinWeightIndex points to a valid reserve register to
725 // reallocate to Iter.Cur, so drop into the eviction code.
Jim Stichnothd97c7df2014-06-04 11:57:08 -0700726 }
Jim Stichnothb40595a2016-01-29 06:14:31 -0800727
728 // Evict all live ranges in Active that register number MinWeightIndex is
729 // assigned to.
John Portoe82b5602016-02-24 15:58:55 -0800730 const auto &Aliases = *RegAliases[MinWeightIndex];
Jim Stichnothb40595a2016-01-29 06:14:31 -0800731 for (SizeT I = Active.size(); I > 0; --I) {
732 const SizeT Index = I - 1;
733 Variable *Item = Active[Index];
Jim Stichnoth8aa39662016-02-10 11:20:30 -0800734 const auto RegNum = Item->getRegNumTmp();
Jim Stichnothb40595a2016-01-29 06:14:31 -0800735 if (Aliases[RegNum]) {
736 dumpLiveRangeTrace("Evicting A ", Item);
John Portoe82b5602016-02-24 15:58:55 -0800737 const auto &Aliases = *RegAliases[RegNum];
Jim Stichnoth8aa39662016-02-10 11:20:30 -0800738 for (RegNumT RegAlias : RegNumBVIter(Aliases)) {
Jim Stichnothb40595a2016-01-29 06:14:31 -0800739 --RegUses[RegAlias];
740 assert(RegUses[RegAlias] >= 0);
741 }
Reed Kotler5fa0a5f2016-02-15 20:01:24 -0800742 Item->setRegNumTmp(RegNumT());
Jim Stichnothb40595a2016-01-29 06:14:31 -0800743 moveItem(Active, Index, Handled);
744 Evicted.push_back(Item);
745 }
746 }
747 // Do the same for Inactive.
748 for (SizeT I = Inactive.size(); I > 0; --I) {
749 const SizeT Index = I - 1;
750 Variable *Item = Inactive[Index];
751 // Note: The Item->rangeOverlaps(Cur) clause is not part of the description
752 // of AssignMemLoc() in the original paper. But there doesn't seem to be any
753 // need to evict an inactive live range that doesn't overlap with the live
754 // range currently being considered. It's especially bad if we would end up
755 // evicting an infinite-weight but currently-inactive live range. The most
756 // common situation for this would be a scratch register kill set for call
757 // instructions.
758 if (Aliases[Item->getRegNumTmp()] && Item->rangeOverlaps(Iter.Cur)) {
759 dumpLiveRangeTrace("Evicting I ", Item);
Reed Kotler5fa0a5f2016-02-15 20:01:24 -0800760 Item->setRegNumTmp(RegNumT());
Jim Stichnothb40595a2016-01-29 06:14:31 -0800761 moveItem(Inactive, Index, Handled);
762 Evicted.push_back(Item);
763 }
764 }
765 // Assign the register to Cur.
Jim Stichnoth8aa39662016-02-10 11:20:30 -0800766 Iter.Cur->setRegNumTmp(RegNumT::fromInt(MinWeightIndex));
767 for (RegNumT RegAlias : RegNumBVIter(Aliases)) {
Jim Stichnothb40595a2016-01-29 06:14:31 -0800768 assert(RegUses[RegAlias] >= 0);
769 ++RegUses[RegAlias];
770 }
771 Active.push_back(Iter.Cur);
John Porto4b6e4b42016-02-17 05:00:59 -0800772 dumpLiveRangeTrace("Allocating Z ", Iter.Cur);
Andrew Sculld24cfda2015-08-25 10:31:15 -0700773}
Jim Stichnothd97c7df2014-06-04 11:57:08 -0700774
John Portoe82b5602016-02-24 15:58:55 -0800775void LinearScan::assignFinalRegisters(const SmallBitVector &RegMaskFull,
776 const SmallBitVector &PreDefinedRegisters,
777 bool Randomized) {
Andrew Sculld24cfda2015-08-25 10:31:15 -0700778 const size_t NumRegisters = RegMaskFull.size();
Jim Stichnoth8aa39662016-02-10 11:20:30 -0800779 llvm::SmallVector<RegNumT, REGS_SIZE> Permutation(NumRegisters);
Jim Stichnothe6d24782014-12-19 05:42:24 -0800780 if (Randomized) {
Qining Luaee5fa82015-08-20 14:59:03 -0700781 // Create a random number generator for regalloc randomization. Merge
Andrew Sculld24cfda2015-08-25 10:31:15 -0700782 // function's sequence and Kind value as the Salt. Because regAlloc() is
Andrew Scull57e12682015-09-16 11:30:19 -0700783 // called twice under O2, the second time with RAK_Phi, we check Kind ==
784 // RAK_Phi to determine the lowest-order bit to make sure the Salt is
785 // different.
Qining Luaee5fa82015-08-20 14:59:03 -0700786 uint64_t Salt =
787 (Func->getSequenceNumber() << 1) ^ (Kind == RAK_Phi ? 0u : 1u);
John Portobb0a5fe2015-09-04 11:23:41 -0700788 Target->makeRandomRegisterPermutation(
Qining Luaee5fa82015-08-20 14:59:03 -0700789 Permutation, PreDefinedRegisters | ~RegMaskFull, Salt);
Jim Stichnothe6d24782014-12-19 05:42:24 -0800790 }
791
Andrew Sculld24cfda2015-08-25 10:31:15 -0700792 // Finish up by setting RegNum = RegNumTmp (or a random permutation thereof)
793 // for each Variable.
Jim Stichnoth5ce0abb2014-10-15 10:16:54 -0700794 for (Variable *Item : Handled) {
Jim Stichnoth8aa39662016-02-10 11:20:30 -0800795 const auto RegNum = Item->getRegNumTmp();
796 auto AssignedRegNum = RegNum;
Jim Stichnothe6d24782014-12-19 05:42:24 -0800797
798 if (Randomized && Item->hasRegTmp() && !Item->hasReg()) {
799 AssignedRegNum = Permutation[RegNum];
800 }
Jim Stichnotha1da6ff2015-11-16 15:59:39 -0800801 if (BuildDefs::dump() && Verbose) {
Jim Stichnothe4a8f402015-01-20 12:52:51 -0800802 Ostream &Str = Ctx->getStrDump();
Jim Stichnoth5ce0abb2014-10-15 10:16:54 -0700803 if (!Item->hasRegTmp()) {
Jim Stichnothd97c7df2014-06-04 11:57:08 -0700804 Str << "Not assigning ";
Jim Stichnoth5ce0abb2014-10-15 10:16:54 -0700805 Item->dump(Func);
Jim Stichnothd97c7df2014-06-04 11:57:08 -0700806 Str << "\n";
807 } else {
Jim Stichnothe6d24782014-12-19 05:42:24 -0800808 Str << (AssignedRegNum == Item->getRegNum() ? "Reassigning "
809 : "Assigning ")
Jim Stichnoth4a659472016-02-01 10:41:18 -0800810 << Target->getRegName(AssignedRegNum, Item->getType()) << "(r"
John Portobb0a5fe2015-09-04 11:23:41 -0700811 << AssignedRegNum << ") to ";
Jim Stichnoth5ce0abb2014-10-15 10:16:54 -0700812 Item->dump(Func);
Jim Stichnothd97c7df2014-06-04 11:57:08 -0700813 Str << "\n";
814 }
815 }
Jim Stichnothe6d24782014-12-19 05:42:24 -0800816 Item->setRegNum(AssignedRegNum);
Jim Stichnothd97c7df2014-06-04 11:57:08 -0700817 }
Andrew Sculld24cfda2015-08-25 10:31:15 -0700818}
Jim Stichnothd97c7df2014-06-04 11:57:08 -0700819
Andrew Sculld24cfda2015-08-25 10:31:15 -0700820// Implements the linear-scan algorithm. Based on "Linear Scan Register
821// Allocation in the Context of SSA Form and Register Constraints" by Hanspeter
822// Mössenböck and Michael Pfeiffer,
823// ftp://ftp.ssw.uni-linz.ac.at/pub/Papers/Moe02.PDF. This implementation is
Jim Stichnotha1da6ff2015-11-16 15:59:39 -0800824// modified to take affinity into account and allow two interfering variables to
825// share the same register in certain cases.
Andrew Sculld24cfda2015-08-25 10:31:15 -0700826//
827// Requires running Cfg::liveness(Liveness_Intervals) in preparation. Results
828// are assigned to Variable::RegNum for each Variable.
John Portoe82b5602016-02-24 15:58:55 -0800829void LinearScan::scan(const SmallBitVector &RegMaskFull, bool Randomized) {
Andrew Sculld24cfda2015-08-25 10:31:15 -0700830 TimerMarker T(TimerStack::TT_linearScan, Func);
831 assert(RegMaskFull.any()); // Sanity check
832 if (Verbose)
833 Ctx->lockStr();
834 Func->resetCurrentNode();
835 const size_t NumRegisters = RegMaskFull.size();
John Portoe82b5602016-02-24 15:58:55 -0800836 SmallBitVector PreDefinedRegisters(NumRegisters);
Andrew Sculld24cfda2015-08-25 10:31:15 -0700837 if (Randomized) {
838 for (Variable *Var : UnhandledPrecolored) {
839 PreDefinedRegisters[Var->getRegNum()] = true;
840 }
841 }
842
843 // Build a LiveRange representing the Kills list.
844 LiveRange KillsRange(Kills);
845 KillsRange.untrim();
846
Jim Stichnotha1da6ff2015-11-16 15:59:39 -0800847 // Reset the register use count.
Andrew Sculld24cfda2015-08-25 10:31:15 -0700848 RegUses.resize(NumRegisters);
849 std::fill(RegUses.begin(), RegUses.end(), 0);
850
Jim Stichnotha1da6ff2015-11-16 15:59:39 -0800851 // Unhandled is already set to all ranges in increasing order of start points.
Andrew Sculld24cfda2015-08-25 10:31:15 -0700852 assert(Active.empty());
853 assert(Inactive.empty());
854 assert(Handled.empty());
855 const TargetLowering::RegSetMask RegsInclude =
856 TargetLowering::RegSet_CallerSave;
857 const TargetLowering::RegSetMask RegsExclude = TargetLowering::RegSet_None;
John Portoe82b5602016-02-24 15:58:55 -0800858 const SmallBitVector KillsMask =
John Portobb0a5fe2015-09-04 11:23:41 -0700859 Target->getRegisterSet(RegsInclude, RegsExclude);
Andrew Sculld24cfda2015-08-25 10:31:15 -0700860
Jim Stichnotha1da6ff2015-11-16 15:59:39 -0800861 // Allocate memory once outside the loop.
Andrew Sculld24cfda2015-08-25 10:31:15 -0700862 IterationState Iter;
863 Iter.Weights.reserve(NumRegisters);
864 Iter.PrecoloredUnhandledMask.reserve(NumRegisters);
865
866 while (!Unhandled.empty()) {
867 Iter.Cur = Unhandled.back();
868 Unhandled.pop_back();
869 dumpLiveRangeTrace("\nConsidering ", Iter.Cur);
John Porto3c275ce2015-12-22 08:14:00 -0800870 assert(Target->getRegistersForVariable(Iter.Cur).any());
Jim Stichnothc59288b2015-11-09 11:38:40 -0800871 Iter.RegMask = RegMaskFull & Target->getRegistersForVariable(Iter.Cur);
Jim Stichnothb40595a2016-01-29 06:14:31 -0800872 Iter.RegMaskUnfiltered =
873 RegMaskFull & Target->getAllRegistersForVariable(Iter.Cur);
Andrew Sculld24cfda2015-08-25 10:31:15 -0700874 KillsRange.trim(Iter.Cur->getLiveRange().getStart());
875
876 // Check for pre-colored ranges. If Cur is pre-colored, it definitely gets
877 // that register. Previously processed live ranges would have avoided that
878 // register due to it being pre-colored. Future processed live ranges won't
879 // evict that register because the live range has infinite weight.
880 if (Iter.Cur->hasReg()) {
881 allocatePrecoloredRegister(Iter.Cur);
882 continue;
883 }
884
885 handleActiveRangeExpiredOrInactive(Iter.Cur);
886 handleInactiveRangeExpiredOrReactivated(Iter.Cur);
887
Jim Stichnothb40595a2016-01-29 06:14:31 -0800888 // Calculate available registers into Iter.Free[] and Iter.FreeUnfiltered[].
Andrew Sculld24cfda2015-08-25 10:31:15 -0700889 Iter.Free = Iter.RegMask;
Jim Stichnothb40595a2016-01-29 06:14:31 -0800890 Iter.FreeUnfiltered = Iter.RegMaskUnfiltered;
Andrew Sculld24cfda2015-08-25 10:31:15 -0700891 for (SizeT i = 0; i < Iter.RegMask.size(); ++i) {
Jim Stichnothb40595a2016-01-29 06:14:31 -0800892 if (RegUses[i] > 0) {
Andrew Sculld24cfda2015-08-25 10:31:15 -0700893 Iter.Free[i] = false;
Jim Stichnothb40595a2016-01-29 06:14:31 -0800894 Iter.FreeUnfiltered[i] = false;
895 }
Andrew Sculld24cfda2015-08-25 10:31:15 -0700896 }
897
898 findRegisterPreference(Iter);
899 filterFreeWithInactiveRanges(Iter);
900
901 // Disable AllowOverlap if an Active variable, which is not Prefer, shares
902 // Prefer's register, and has a definition within Cur's live range.
903 if (Iter.AllowOverlap) {
John Portoe82b5602016-02-24 15:58:55 -0800904 const auto &Aliases = *RegAliases[Iter.PreferReg];
Andrew Sculld24cfda2015-08-25 10:31:15 -0700905 for (const Variable *Item : Active) {
Jim Stichnoth8aa39662016-02-10 11:20:30 -0800906 const RegNumT RegNum = Item->getRegNumTmp();
Jim Stichnothc59288b2015-11-09 11:38:40 -0800907 if (Item != Iter.Prefer && Aliases[RegNum] &&
Andrew Sculld24cfda2015-08-25 10:31:15 -0700908 overlapsDefs(Func, Iter.Cur, Item)) {
909 Iter.AllowOverlap = false;
910 dumpDisableOverlap(Func, Item, "Active");
911 }
912 }
913 }
914
915 Iter.Weights.resize(Iter.RegMask.size());
916 std::fill(Iter.Weights.begin(), Iter.Weights.end(), RegWeight());
917
918 Iter.PrecoloredUnhandledMask.resize(Iter.RegMask.size());
919 Iter.PrecoloredUnhandledMask.reset();
920
921 filterFreeWithPrecoloredRanges(Iter);
922
Jim Stichnothb40595a2016-01-29 06:14:31 -0800923 // Remove scratch registers from the Iter.Free[] list, and mark their
924 // Iter.Weights[] as infinite, if KillsRange overlaps Cur's live range.
Andrew Sculld24cfda2015-08-25 10:31:15 -0700925 constexpr bool UseTrimmed = true;
926 if (Iter.Cur->getLiveRange().overlaps(KillsRange, UseTrimmed)) {
927 Iter.Free.reset(KillsMask);
Jim Stichnothb40595a2016-01-29 06:14:31 -0800928 Iter.FreeUnfiltered.reset(KillsMask);
Jim Stichnoth8aa39662016-02-10 11:20:30 -0800929 for (RegNumT i : RegNumBVIter(KillsMask)) {
Andrew Sculld24cfda2015-08-25 10:31:15 -0700930 Iter.Weights[i].setWeight(RegWeight::Inf);
931 if (Iter.PreferReg == i)
932 Iter.AllowOverlap = false;
933 }
934 }
935
936 // Print info about physical register availability.
Jim Stichnotha1da6ff2015-11-16 15:59:39 -0800937 if (BuildDefs::dump() && Verbose) {
Andrew Sculld24cfda2015-08-25 10:31:15 -0700938 Ostream &Str = Ctx->getStrDump();
Jim Stichnoth8aa39662016-02-10 11:20:30 -0800939 for (RegNumT i : RegNumBVIter(Iter.RegMaskUnfiltered)) {
940 Str << Target->getRegName(i, Iter.Cur->getType()) << "(U=" << RegUses[i]
941 << ",F=" << Iter.Free[i] << ",P=" << Iter.PrecoloredUnhandledMask[i]
942 << ") ";
Andrew Sculld24cfda2015-08-25 10:31:15 -0700943 }
944 Str << "\n";
945 }
946
947 if (Iter.Prefer && (Iter.AllowOverlap || Iter.Free[Iter.PreferReg])) {
Jim Stichnotha1da6ff2015-11-16 15:59:39 -0800948 // First choice: a preferred register that is either free or is allowed to
949 // overlap with its linked variable.
Andrew Sculld24cfda2015-08-25 10:31:15 -0700950 allocatePreferredRegister(Iter);
951 } else if (Iter.Free.any()) {
952 // Second choice: any free register.
Jim Stichnothb40595a2016-01-29 06:14:31 -0800953 constexpr bool Filtered = true;
954 allocateFreeRegister(Iter, Filtered);
Andrew Sculld24cfda2015-08-25 10:31:15 -0700955 } else {
Jim Stichnotha1da6ff2015-11-16 15:59:39 -0800956 // Fallback: there are no free registers, so we look for the lowest-weight
957 // register and see if Cur has higher weight.
Andrew Sculld24cfda2015-08-25 10:31:15 -0700958 handleNoFreeRegisters(Iter);
959 }
960 dump(Func);
961 }
962
963 // Move anything Active or Inactive to Handled for easier handling.
964 Handled.insert(Handled.end(), Active.begin(), Active.end());
965 Active.clear();
966 Handled.insert(Handled.end(), Inactive.begin(), Inactive.end());
967 Inactive.clear();
968 dump(Func);
969
970 assignFinalRegisters(RegMaskFull, PreDefinedRegisters, Randomized);
971
Jim Stichnothe4a8f402015-01-20 12:52:51 -0800972 if (Verbose)
973 Ctx->unlockStr();
Jim Stichnothd97c7df2014-06-04 11:57:08 -0700974}
975
976// ======================== Dump routines ======================== //
977
Andrew Sculld24cfda2015-08-25 10:31:15 -0700978void LinearScan::dumpLiveRangeTrace(const char *Label, const Variable *Item) {
979 if (!BuildDefs::dump())
980 return;
981
982 if (Verbose) {
983 Ostream &Str = Ctx->getStrDump();
984 Str << Label;
985 dumpLiveRange(Item, Func);
986 Str << "\n";
987 }
988}
989
Jim Stichnothd97c7df2014-06-04 11:57:08 -0700990void LinearScan::dump(Cfg *Func) const {
Jim Stichnoth20b71f52015-06-24 15:52:24 -0700991 if (!BuildDefs::dump())
Karl Schimpfb6c96af2014-11-17 10:58:39 -0800992 return;
Jim Stichnotha1da6ff2015-11-16 15:59:39 -0800993 if (!Verbose)
Jim Stichnothd97c7df2014-06-04 11:57:08 -0700994 return;
Jim Stichnothe4a8f402015-01-20 12:52:51 -0800995 Ostream &Str = Func->getContext()->getStrDump();
Jim Stichnoth800dab22014-09-20 12:25:02 -0700996 Func->resetCurrentNode();
Jim Stichnothd97c7df2014-06-04 11:57:08 -0700997 Str << "**** Current regalloc state:\n";
998 Str << "++++++ Handled:\n";
Jim Stichnoth5ce0abb2014-10-15 10:16:54 -0700999 for (const Variable *Item : Handled) {
1000 dumpLiveRange(Item, Func);
Jim Stichnothd97c7df2014-06-04 11:57:08 -07001001 Str << "\n";
1002 }
1003 Str << "++++++ Unhandled:\n";
Jim Stichnoth7e571362015-01-09 11:43:26 -08001004 for (const Variable *Item : reverse_range(Unhandled)) {
1005 dumpLiveRange(Item, Func);
Jim Stichnothd97c7df2014-06-04 11:57:08 -07001006 Str << "\n";
1007 }
1008 Str << "++++++ Active:\n";
Jim Stichnoth5ce0abb2014-10-15 10:16:54 -07001009 for (const Variable *Item : Active) {
1010 dumpLiveRange(Item, Func);
Jim Stichnothd97c7df2014-06-04 11:57:08 -07001011 Str << "\n";
1012 }
1013 Str << "++++++ Inactive:\n";
Jim Stichnoth5ce0abb2014-10-15 10:16:54 -07001014 for (const Variable *Item : Inactive) {
1015 dumpLiveRange(Item, Func);
Jim Stichnothd97c7df2014-06-04 11:57:08 -07001016 Str << "\n";
1017 }
1018}
1019
1020} // end of namespace Ice