58#define DEBUG_TYPE "regalloc"
62STATISTIC(NumCoalesced,
"Number of copies coalesced");
75class InstrPosIndexes {
77 void unsetInitialized() { IsInitialized =
false; }
79 void init(
const MachineBasicBlock &
MBB) {
81 Instr2PosIndex.
clear();
83 for (
const MachineInstr &
MI :
MBB) {
84 LastIndex += InstrDist;
85 Instr2PosIndex[&
MI] = LastIndex;
92 bool getIndex(
const MachineInstr &
MI,
uint64_t &Index) {
100 assert(
MI.getParent() == CurMBB &&
"MI is not in CurMBB");
101 auto It = Instr2PosIndex.find(&
MI);
102 if (It != Instr2PosIndex.end()) {
116 unsigned Distance = 1;
118 End = std::next(Start);
119 while (Start != CurMBB->begin() &&
120 !Instr2PosIndex.count(&*std::prev(Start))) {
124 while (End != CurMBB->end() && !Instr2PosIndex.count(&*(End))) {
132 Start == CurMBB->begin() ? 0 : Instr2PosIndex.at(&*std::prev(Start));
134 if (End == CurMBB->end())
135 Step =
static_cast<uint64_t>(InstrDist);
138 uint64_t EndIndex = Instr2PosIndex.at(&*End);
139 assert(EndIndex > LastIndex &&
"Index must be ascending order");
140 unsigned NumAvailableIndexes = EndIndex - LastIndex - 1;
159 Step = (NumAvailableIndexes + 1) / (Distance + 1);
164 if (
LLVM_UNLIKELY(!Step || (!LastIndex && Step == InstrDist))) {
166 Index = Instr2PosIndex.at(&
MI);
170 for (
auto I = Start;
I != End; ++
I) {
172 Instr2PosIndex[&*
I] = LastIndex;
174 Index = Instr2PosIndex.at(&
MI);
179 bool IsInitialized =
false;
180 enum { InstrDist = 1024 };
181 const MachineBasicBlock *CurMBB =
nullptr;
182 DenseMap<const MachineInstr *, uint64_t> Instr2PosIndex;
185class RegAllocFastImpl {
188 bool ClearVirtRegs_ =
true)
189 : ShouldAllocateRegisterImpl(
F), StackSlotForVirtReg(-1),
190 ClearVirtRegs(ClearVirtRegs_) {}
193 MachineFrameInfo *MFI =
nullptr;
194 MachineRegisterInfo *MRI =
nullptr;
195 const TargetRegisterInfo *TRI =
nullptr;
196 const TargetInstrInfo *TII =
nullptr;
197 RegisterClassInfo RegClassInfo;
201 MachineBasicBlock *MBB =
nullptr;
204 IndexedMap<int, VirtReg2IndexFunctor> StackSlotForVirtReg;
209 MachineInstr *LastUse =
nullptr;
212 bool LiveOut =
false;
213 bool Reloaded =
false;
216 explicit LiveReg(
Register VirtReg) : VirtReg(VirtReg) {}
217 explicit LiveReg() =
default;
219 unsigned getSparseSetIndex()
const {
return VirtReg.virtRegIndex(); }
222 using LiveRegMap = SparseSet<LiveReg, unsigned, identity, uint16_t>;
225 LiveRegMap LiveVirtRegs;
228 DenseMap<Register, LiveReg> BundleVirtRegsMap;
230 DenseMap<Register, SmallVector<MachineOperand *, 2>> LiveDbgValueMap;
233 DenseMap<Register, SmallVector<MachineInstr *, 1>> DanglingDbgValues;
237 BitVector MayLiveAcrossBlocks;
258 std::vector<unsigned> RegUnitStates;
276 SmallVector<unsigned, 0> UsedInInstr;
278 SmallVector<unsigned, 8> DefOperandIndexes;
283 InstrPosIndexes PosIndexes;
285 void setRegUnitState(MCRegUnit Unit,
unsigned NewState);
286 unsigned getRegUnitState(MCRegUnit Unit)
const;
288 void setPhysRegState(MCRegister PhysReg,
unsigned NewState);
289 bool isPhysRegFree(MCRegister PhysReg)
const;
292 void markRegUsedInInstr(MCRegister PhysReg) {
293 for (MCRegUnit Unit : TRI->regunits(PhysReg))
294 UsedInInstr[
static_cast<unsigned>(
Unit)] = InstrGen | 1;
298 bool isClobberedByRegMasks(MCRegister PhysReg)
const {
299 return llvm::any_of(RegMasks, [PhysReg](
const uint32_t *Mask) {
305 bool isRegUsedInInstr(MCRegister PhysReg,
bool LookAtPhysRegUses)
const {
306 if (LookAtPhysRegUses && isClobberedByRegMasks(PhysReg))
308 for (MCRegUnit Unit : TRI->regunits(PhysReg))
309 if (UsedInInstr[
static_cast<unsigned>(Unit)] >=
310 (InstrGen | !LookAtPhysRegUses))
317 void markPhysRegUsedInInstr(MCRegister PhysReg) {
318 for (MCRegUnit Unit : TRI->regunits(PhysReg)) {
319 assert(UsedInInstr[
static_cast<unsigned>(Unit)] <= InstrGen &&
320 "non-phys use before phys use?");
321 UsedInInstr[
static_cast<unsigned>(
Unit)] = InstrGen;
326 void unmarkRegUsedInInstr(MCRegister PhysReg) {
327 for (MCRegUnit Unit : TRI->regunits(PhysReg))
328 UsedInInstr[
static_cast<unsigned>(
Unit)] = 0;
335 spillImpossible = ~0
u
344 void allocateBasicBlock(MachineBasicBlock &MBB);
349 void findAndSortDefOperandIndexes(
const MachineInstr &
MI);
351 void allocateInstruction(MachineInstr &
MI);
352 void handleDebugValue(MachineInstr &
MI);
353 void handleBundle(MachineInstr &
MI);
355 bool usePhysReg(MachineInstr &
MI, MCRegister PhysReg);
356 bool definePhysReg(MachineInstr &
MI, MCRegister PhysReg);
357 bool displacePhysReg(MachineInstr &
MI, MCRegister PhysReg);
358 void freePhysReg(MCRegister PhysReg);
360 unsigned calcSpillCost(
MCPhysReg PhysReg)
const;
370 void assignVirtToPhysReg(MachineInstr &
MI, LiveReg &, MCRegister PhysReg);
371 void allocVirtReg(MachineInstr &
MI, LiveReg &LR,
Register Hint,
372 bool LookAtPhysRegUses =
false);
373 void allocVirtRegUndef(MachineOperand &MO);
374 void assignDanglingDebugValues(MachineInstr &Def,
Register VirtReg,
376 bool defineLiveThroughVirtReg(MachineInstr &
MI,
unsigned OpNum,
378 bool defineVirtReg(MachineInstr &
MI,
unsigned OpNum,
Register VirtReg,
379 bool LookAtPhysRegUses =
false);
380 bool useVirtReg(MachineInstr &
MI, MachineOperand &MO,
Register VirtReg);
382 MCPhysReg getErrorAssignment(
const LiveReg &LR, MachineInstr &
MI,
386 getMBBBeginInsertionPoint(MachineBasicBlock &MBB,
387 SmallSet<Register, 2> &PrologLiveIns)
const;
389 void reloadAtBegin(MachineBasicBlock &MBB);
390 bool setPhysReg(MachineInstr &
MI, MachineOperand &MO,
391 const LiveReg &Assignment);
396 bool shouldAllocateRegister(
const Register Reg)
const;
397 int getStackSpaceFor(
Register VirtReg);
399 MCRegister AssignedReg,
bool Kill,
bool LiveOut);
406 bool mayBeSpillFromInlineAsmBr(
const MachineInstr &
MI)
const;
408 void dumpState()
const;
412 RegAllocFastImpl Impl;
418 : MachineFunctionPass(ID), Impl(
F, ClearVirtRegs_) {}
421 return Impl.runOnMachineFunction(MF);
424 StringRef getPassName()
const override {
return "Fast Register Allocator"; }
426 void getAnalysisUsage(AnalysisUsage &AU)
const override {
431 MachineFunctionProperties getRequiredProperties()
const override {
432 return MachineFunctionProperties().setNoPHIs();
435 MachineFunctionProperties getSetProperties()
const override {
436 if (Impl.ClearVirtRegs) {
437 return MachineFunctionProperties().setNoVRegs();
440 return MachineFunctionProperties();
443 MachineFunctionProperties getClearedProperties()
const override {
444 return MachineFunctionProperties().setIsSSA();
450char RegAllocFast::ID = 0;
457 if (!ShouldAllocateRegisterImpl)
460 return ShouldAllocateRegisterImpl(*
TRI, *MRI,
Reg);
463void RegAllocFastImpl::setRegUnitState(MCRegUnit Unit,
unsigned NewState) {
464 RegUnitStates[
static_cast<unsigned>(
Unit)] = NewState;
467unsigned RegAllocFastImpl::getRegUnitState(MCRegUnit Unit)
const {
468 return RegUnitStates[
static_cast<unsigned>(
Unit)];
471void RegAllocFastImpl::setPhysRegState(MCRegister PhysReg,
unsigned NewState) {
472 for (MCRegUnit Unit :
TRI->regunits(PhysReg))
473 setRegUnitState(Unit, NewState);
476bool RegAllocFastImpl::isPhysRegFree(MCRegister PhysReg)
const {
477 for (MCRegUnit Unit :
TRI->regunits(PhysReg)) {
478 if (getRegUnitState(Unit) != regFree)
486int RegAllocFastImpl::getStackSpaceFor(
Register VirtReg) {
488 int SS = StackSlotForVirtReg[VirtReg];
495 unsigned Size =
TRI->getSpillSize(RC);
500 Align CurrentAlign =
ST.getFrameLowering()->getStackAlign();
501 if (Alignment > CurrentAlign && !
TRI->canRealignStack(MF))
508 StackSlotForVirtReg[VirtReg] = FrameIdx;
515 PosIndexes.getIndex(
A, IndexA);
518 PosIndexes.getIndex(
A, IndexA);
519 return IndexA < IndexB;
526bool RegAllocFastImpl::mayBeSpillFromInlineAsmBr(
const MachineInstr &
MI)
const {
531 for (
const auto &
Op :
MI.operands())
538bool RegAllocFastImpl::mayLiveOut(
Register VirtReg) {
544 const MachineInstr *SelfLoopDef =
nullptr;
551 if (DefInst.getParent() !=
MBB) {
555 if (!SelfLoopDef ||
dominates(PosIndexes, DefInst, *SelfLoopDef))
556 SelfLoopDef = &DefInst;
567 static const unsigned Limit = 8;
570 if (UseInst.getParent() !=
MBB || ++
C >= Limit) {
579 if (SelfLoopDef == &UseInst ||
580 !
dominates(PosIndexes, *SelfLoopDef, UseInst)) {
591bool RegAllocFastImpl::mayLiveIn(
Register VirtReg) {
596 static const unsigned Limit = 8;
599 if (DefInst.getParent() !=
MBB || ++
C >= Limit) {
611 Register VirtReg, MCRegister AssignedReg,
612 bool Kill,
bool LiveOut) {
615 int FI = getStackSpaceFor(VirtReg);
627 SmallVectorImpl<MachineOperand *> &LRIDbgOperands = LiveDbgValueMap[VirtReg];
628 SmallMapVector<MachineInstr *, SmallVector<const MachineOperand *>, 2>
630 for (MachineOperand *MO : LRIDbgOperands)
631 SpilledOperandsMap[MO->getParent()].push_back(MO);
632 for (
const auto &MISpilledOperands : SpilledOperandsMap) {
633 MachineInstr &
DBG = *MISpilledOperands.first;
635 if (
DBG.isDebugValueList())
638 *
MBB, Before, *MISpilledOperands.first, FI, MISpilledOperands.second);
641 LLVM_DEBUG(
dbgs() <<
"Inserting debug info due to spill:\n" << *NewDV);
648 MachineInstr *ClonedDV =
MBB->
getParent()->CloneMachineInstr(NewDV);
650 LLVM_DEBUG(
dbgs() <<
"Cloning debug info due to live out spill\n");
656 if (
DBG.isNonListDebugValue()) {
657 MachineOperand &MO =
DBG.getDebugOperand(0);
666 LRIDbgOperands.
clear();
671 Register VirtReg, MCRegister PhysReg) {
674 int FI = getStackSpaceFor(VirtReg);
685 MachineBasicBlock &
MBB, SmallSet<Register, 2> &PrologLiveIns)
const {
694 if (!
TII->isBasicBlockPrologue(*
I) && !mayBeSpillFromInlineAsmBr(*
I))
699 for (MachineOperand &MO :
I->operands()) {
711void RegAllocFastImpl::reloadAtBegin(MachineBasicBlock &
MBB) {
712 if (LiveVirtRegs.empty())
717 for (MachineBasicBlock::RegisterMaskPair
P :
MBB.
liveins())
718 setPhysRegState(
P.PhysReg, regLiveIn);
720 SmallSet<Register, 2> PrologLiveIns;
725 getMBBBeginInsertionPoint(
MBB, PrologLiveIns);
726 for (
const LiveReg &LR : LiveVirtRegs) {
727 MCRegister PhysReg = LR.PhysReg;
728 if (!PhysReg || LR.Error)
731 MCRegUnit FirstUnit = *
TRI->regunits(PhysReg).begin();
732 if (getRegUnitState(FirstUnit) == regLiveIn)
736 "no reload in start block. Missing vreg def?");
738 if (PrologLiveIns.
count(PhysReg)) {
742 reload(
MBB.
begin(), LR.VirtReg, PhysReg);
744 reload(InsertBefore, LR.VirtReg, PhysReg);
746 LiveVirtRegs.clear();
753bool RegAllocFastImpl::usePhysReg(MachineInstr &
MI, MCRegister
Reg) {
755 bool displacedAny = displacePhysReg(
MI,
Reg);
756 setPhysRegState(
Reg, regPreAssigned);
757 markRegUsedInInstr(
Reg);
765bool RegAllocFastImpl::definePhysReg(MachineInstr &
MI, MCRegister
Reg) {
766 bool displacedAny = displacePhysReg(
MI,
Reg);
767 setPhysRegState(
Reg, regPreAssigned);
774bool RegAllocFastImpl::displacePhysReg(MachineInstr &
MI, MCRegister PhysReg) {
775 bool displacedAny =
false;
777 for (MCRegUnit Unit :
TRI->regunits(PhysReg)) {
778 switch (
unsigned VirtReg = getRegUnitState(Unit)) {
780 LiveRegMap::iterator LRI = findLiveVirtReg(VirtReg);
781 assert(LRI != LiveVirtRegs.end() &&
"datastructures in sync");
784 while (mayBeSpillFromInlineAsmBr(*ReloadBefore))
786 reload(ReloadBefore, VirtReg, LRI->PhysReg);
788 setPhysRegState(LRI->PhysReg, regFree);
789 LRI->PhysReg = MCRegister();
790 LRI->Reloaded =
true;
795 setRegUnitState(Unit, regFree);
805void RegAllocFastImpl::freePhysReg(MCRegister PhysReg) {
808 MCRegUnit FirstUnit = *
TRI->regunits(PhysReg).begin();
809 switch (
unsigned VirtReg = getRegUnitState(FirstUnit)) {
815 setPhysRegState(PhysReg, regFree);
818 LiveRegMap::iterator LRI = findLiveVirtReg(VirtReg);
819 assert(LRI != LiveVirtRegs.end());
821 setPhysRegState(LRI->PhysReg, regFree);
822 LRI->PhysReg = MCRegister();
832unsigned RegAllocFastImpl::calcSpillCost(
MCPhysReg PhysReg)
const {
833 for (MCRegUnit Unit :
TRI->regunits(PhysReg)) {
834 switch (
unsigned VirtReg = getRegUnitState(Unit)) {
840 return spillImpossible;
842 bool SureSpill = StackSlotForVirtReg[VirtReg] != -1 ||
843 findLiveVirtReg(VirtReg)->LiveOut;
844 return SureSpill ? spillClean : spillDirty;
851void RegAllocFastImpl::assignDanglingDebugValues(MachineInstr &Definition,
854 auto UDBGValIter = DanglingDbgValues.
find(VirtReg);
855 if (UDBGValIter == DanglingDbgValues.
end())
858 SmallVectorImpl<MachineInstr *> &Dangling = UDBGValIter->second;
859 for (MachineInstr *DbgValue : Dangling) {
860 assert(DbgValue->isDebugValue());
861 if (!DbgValue->hasDebugOperandForReg(VirtReg))
865 MCRegister SetToReg =
Reg;
868 E = DbgValue->getIterator();
870 if (
I->modifiesRegister(
Reg,
TRI) || --Limit == 0) {
873 SetToReg = MCRegister();
877 for (MachineOperand &MO : DbgValue->getDebugOperandsForReg(VirtReg)) {
889void RegAllocFastImpl::assignVirtToPhysReg(MachineInstr &AtMI, LiveReg &LR,
890 MCRegister PhysReg) {
894 assert(!LR.PhysReg &&
"Already assigned a physreg");
895 assert(PhysReg &&
"Trying to assign no register");
896 LR.PhysReg = PhysReg;
897 setPhysRegState(PhysReg, VirtReg.
id());
899 assignDanglingDebugValues(AtMI, VirtReg, PhysReg);
905 static const unsigned ChainLengthLimit = 3;
906 for (
unsigned C = 0;
C <= ChainLengthLimit; ++
C) {
917 Reg =
Def->getOperand(1).getReg();
926 static const unsigned DefLimit = 3;
931 Reg = traceCopyChain(
Reg);
943void RegAllocFastImpl::allocVirtReg(MachineInstr &
MI, LiveReg &LR,
944 Register Hint0,
bool LookAtPhysRegUses) {
945 const Register VirtReg = LR.VirtReg;
950 <<
" in class " <<
TRI->getRegClassName(&RC)
955 !isRegUsedInInstr(Hint0, LookAtPhysRegUses)) {
957 if (isPhysRegFree(Hint0)) {
960 assignVirtToPhysReg(
MI, LR, Hint0);
971 Register Hint1 = traceCopies(VirtReg);
973 !isRegUsedInInstr(Hint1, LookAtPhysRegUses)) {
975 if (isPhysRegFree(Hint1)) {
978 assignVirtToPhysReg(
MI, LR, Hint1);
989 unsigned BestCost = spillImpossible;
991 for (
MCPhysReg PhysReg : AllocationOrder) {
993 if (isRegUsedInInstr(PhysReg, LookAtPhysRegUses)) {
998 unsigned Cost = calcSpillCost(PhysReg);
1002 assignVirtToPhysReg(
MI, LR, PhysReg);
1006 if (PhysReg == Hint0 || PhysReg == Hint1)
1007 Cost -= spillPrefBonus;
1009 if (
Cost < BestCost) {
1018 LR.PhysReg = getErrorAssignment(LR,
MI, RC);
1023 displacePhysReg(
MI, BestReg);
1024 assignVirtToPhysReg(
MI, LR, BestReg);
1027void RegAllocFastImpl::allocVirtRegUndef(MachineOperand &MO) {
1031 if (!shouldAllocateRegister(VirtReg))
1037 for (
const MachineOperand &Tied :
MI.all_uses()) {
1038 if (!Tied.isTied() || Tied.getReg() != VirtReg)
1041 MI.getOperand(
MI.findTiedOperandIdx(
MI.getOperandNo(&Tied)))
1044 for (MachineOperand &O :
MI.all_uses()) {
1045 if (
O.getReg() != VirtReg)
1048 unsigned SubIdx =
O.isTied() ? 0 :
O.getSubReg();
1049 O.setReg(SubIdx ?
TRI->getSubReg(DefReg, SubIdx) : DefReg);
1056 LiveRegMap::iterator LRI = findLiveVirtReg(VirtReg);
1058 bool IsRenamable =
true;
1059 if (LRI != LiveVirtRegs.end() && LRI->PhysReg) {
1060 PhysReg = LRI->PhysReg;
1064 if (AllocationOrder.
empty()) {
1070 PhysReg = getErrorAssignment(*LRI, *MO.
getParent(), RC);
1072 IsRenamable =
false;
1074 PhysReg = AllocationOrder.
front();
1078 if (SubRegIdx != 0) {
1079 PhysReg =
TRI->getSubReg(PhysReg, SubRegIdx);
1089bool RegAllocFastImpl::defineLiveThroughVirtReg(MachineInstr &
MI,
1092 if (!shouldAllocateRegister(VirtReg))
1094 LiveRegMap::iterator LRI = findLiveVirtReg(VirtReg);
1095 if (LRI != LiveVirtRegs.end()) {
1096 MCRegister PrevReg = LRI->PhysReg;
1097 if (PrevReg && isRegUsedInInstr(PrevReg,
true)) {
1099 <<
" (tied/earlyclobber resolution)\n");
1100 freePhysReg(PrevReg);
1101 LRI->PhysReg = MCRegister();
1108 TII->get(TargetOpcode::COPY), PrevReg)
1111 MachineOperand &MO =
MI.getOperand(OpNum);
1116 return defineVirtReg(
MI, OpNum, VirtReg,
true);
1126bool RegAllocFastImpl::defineVirtReg(MachineInstr &
MI,
unsigned OpNum,
1127 Register VirtReg,
bool LookAtPhysRegUses) {
1129 if (!shouldAllocateRegister(VirtReg))
1131 MachineOperand &MO =
MI.getOperand(OpNum);
1132 LiveRegMap::iterator LRI;
1134 std::tie(LRI, New) = LiveVirtRegs.insert(LiveReg(VirtReg));
1137 if (mayLiveOut(VirtReg)) {
1138 LRI->LiveOut =
true;
1145 if (!LRI->PhysReg) {
1146 allocVirtReg(
MI, *LRI,
Register(), LookAtPhysRegUses);
1148 assert((!isRegUsedInInstr(LRI->PhysReg, LookAtPhysRegUses) || LRI->Error) &&
1149 "TODO: preassign mismatch");
1151 <<
" use existing assignment to "
1155 MCRegister PhysReg = LRI->PhysReg;
1157 if (LRI->Reloaded || LRI->LiveOut) {
1158 if (!
MI.isImplicitDef()) {
1162 <<
" RL: " << LRI->Reloaded <<
'\n');
1163 bool Kill = LRI->LastUse ==
nullptr;
1164 spill(SpillBefore, VirtReg, PhysReg,
Kill, LRI->LiveOut);
1168 if (
MI.getOpcode() == TargetOpcode::INLINEASM_BR) {
1169 int FI = StackSlotForVirtReg[VirtReg];
1171 for (MachineOperand &MO :
MI.operands()) {
1173 MachineBasicBlock *Succ = MO.
getMBB();
1182 LRI->LastUse =
nullptr;
1183 }
else if (!LRI->LastUse) {
1188 LRI->LiveOut =
false;
1189 LRI->Reloaded =
false;
1191 if (
MI.getOpcode() == TargetOpcode::BUNDLE) {
1192 BundleVirtRegsMap[VirtReg] = *LRI;
1194 markRegUsedInInstr(PhysReg);
1195 return setPhysReg(
MI, MO, *LRI);
1200bool RegAllocFastImpl::useVirtReg(MachineInstr &
MI, MachineOperand &MO,
1203 if (!shouldAllocateRegister(VirtReg))
1205 LiveRegMap::iterator LRI;
1207 std::tie(LRI, New) = LiveVirtRegs.insert(LiveReg(VirtReg));
1210 if (mayLiveOut(VirtReg)) {
1211 LRI->LiveOut =
true;
1218 assert((!MO.
isKill() || LRI->LastUse == &
MI) &&
"Invalid kill flag");
1222 if (!LRI->PhysReg) {
1225 if (
MI.isCopy() &&
MI.getOperand(1).getSubReg() == 0) {
1226 Hint =
MI.getOperand(0).getReg();
1227 if (
Hint.isVirtual()) {
1228 assert(!shouldAllocateRegister(Hint));
1232 "Copy destination should already be assigned");
1235 allocVirtReg(
MI, *LRI, Hint,
false);
1240 if (
MI.getOpcode() == TargetOpcode::BUNDLE) {
1241 BundleVirtRegsMap[VirtReg] = *LRI;
1243 markRegUsedInInstr(LRI->PhysReg);
1244 return setPhysReg(
MI, MO, *LRI);
1250MCPhysReg RegAllocFastImpl::getErrorAssignment(
const LiveReg &LR,
1264 if (AllocationOrder.
empty()) {
1268 "no registers from class available to allocate", Fn,
1273 assert(!RawRegs.
empty() &&
"register classes cannot have no registers");
1274 return RawRegs.
front();
1277 if (!LR.Error && EmitError) {
1280 if (
MI.isInlineAsm()) {
1281 MI.emitInlineAsmError(
1282 "inline assembly requires more registers than available");
1286 "ran out of registers during register allocation", Fn,
1291 return AllocationOrder.
front();
1296bool RegAllocFastImpl::setPhysReg(MachineInstr &
MI, MachineOperand &MO,
1297 const LiveReg &Assignment) {
1298 MCRegister PhysReg = Assignment.PhysReg;
1299 assert(PhysReg &&
"assignments should always be to a valid physreg");
1327 MI.addRegisterKilled(PhysReg,
TRI,
true);
1336 MI.addRegisterDead(PhysReg,
TRI,
true);
1338 MI.addRegisterDefined(PhysReg,
TRI);
1347void RegAllocFastImpl::dumpState()
const {
1348 for (MCRegUnit Unit :
TRI->regunits()) {
1349 switch (
unsigned VirtReg = getRegUnitState(Unit)) {
1352 case regPreAssigned:
1359 LiveRegMap::const_iterator
I = findLiveVirtReg(VirtReg);
1360 assert(
I != LiveVirtRegs.end() &&
"have LiveVirtRegs entry");
1361 if (
I->LiveOut ||
I->Reloaded) {
1369 assert(
TRI->hasRegUnit(
I->PhysReg, Unit) &&
"inverse mapping present");
1376 for (
const LiveReg &LR : LiveVirtRegs) {
1379 MCRegister PhysReg = LR.PhysReg;
1382 for (MCRegUnit Unit :
TRI->regunits(PhysReg)) {
1383 assert(getRegUnitState(Unit) == VirtReg &&
"inverse map valid");
1391void RegAllocFastImpl::addRegClassDefCounts(
1393 assert(RegClassDefCounts.
size() ==
TRI->getNumRegClasses());
1396 if (!shouldAllocateRegister(
Reg))
1399 for (
unsigned RCIdx = 0, RCIdxEnd =
TRI->getNumRegClasses();
1400 RCIdx != RCIdxEnd; ++RCIdx) {
1404 ++RegClassDefCounts[RCIdx];
1410 for (
unsigned RCIdx = 0, RCIdxEnd =
TRI->getNumRegClasses();
1411 RCIdx != RCIdxEnd; ++RCIdx) {
1413 for (MCRegAliasIterator Alias(
Reg,
TRI,
true); Alias.isValid(); ++Alias) {
1415 ++RegClassDefCounts[RCIdx];
1429 !
MI.getOperand(
MI.findTiedOperandIdx(
MI.getOperandNo(&MO))).isUndef();
1435void RegAllocFastImpl::findAndSortDefOperandIndexes(
const MachineInstr &
MI) {
1436 DefOperandIndexes.
clear();
1439 for (
unsigned I = 0,
E =
MI.getNumOperands();
I <
E; ++
I) {
1440 const MachineOperand &MO =
MI.getOperand(
I);
1447 markPhysRegUsedInInstr(
Reg);
1457 if (DefOperandIndexes.
size() <= 1)
1465 SmallVector<unsigned> RegClassDefCounts(
TRI->getNumRegClasses(), 0);
1467 for (
const MachineOperand &MO :
MI.all_defs())
1468 addRegClassDefCounts(RegClassDefCounts, MO.
getReg());
1470 llvm::sort(DefOperandIndexes, [&](
unsigned I0,
unsigned I1) {
1471 const MachineOperand &MO0 =
MI.getOperand(I0);
1472 const MachineOperand &MO1 =
MI.getOperand(I1);
1480 unsigned ClassSize0 = RegClassInfo.
getOrder(&RC0).size();
1481 unsigned ClassSize1 = RegClassInfo.
getOrder(&RC1).size();
1483 bool SmallClass0 = ClassSize0 < RegClassDefCounts[RC0.
getID()];
1484 bool SmallClass1 = ClassSize1 < RegClassDefCounts[RC1.
getID()];
1485 if (SmallClass0 > SmallClass1)
1487 if (SmallClass0 < SmallClass1)
1493 if (Livethrough0 > Livethrough1)
1495 if (Livethrough0 < Livethrough1)
1503void RegAllocFastImpl::allocateInstruction(MachineInstr &
MI) {
1526 BundleVirtRegsMap.
clear();
1529 bool HasPhysRegUse =
false;
1530 bool HasRegMask =
false;
1531 bool HasVRegDef =
false;
1532 bool HasDef =
false;
1533 bool HasEarlyClobber =
false;
1534 bool NeedToAssignLiveThroughs =
false;
1535 for (MachineOperand &MO :
MI.operands()) {
1539 if (!shouldAllocateRegister(
Reg))
1545 HasEarlyClobber =
true;
1547 NeedToAssignLiveThroughs =
true;
1553 bool displacedAny = definePhysReg(
MI,
Reg);
1555 HasEarlyClobber =
true;
1560 HasPhysRegUse =
true;
1574 bool ReArrangedImplicitOps =
true;
1582 if (NeedToAssignLiveThroughs) {
1583 while (ReArrangedImplicitOps) {
1584 ReArrangedImplicitOps =
false;
1585 findAndSortDefOperandIndexes(
MI);
1586 for (
unsigned OpIdx : DefOperandIndexes) {
1587 MachineOperand &MO =
MI.getOperand(OpIdx);
1591 ReArrangedImplicitOps = defineLiveThroughVirtReg(
MI, OpIdx,
Reg);
1593 ReArrangedImplicitOps = defineVirtReg(
MI, OpIdx,
Reg);
1597 if (ReArrangedImplicitOps)
1603 while (ReArrangedImplicitOps) {
1604 ReArrangedImplicitOps =
false;
1605 for (MachineOperand &MO :
MI.all_defs()) {
1608 ReArrangedImplicitOps =
1609 defineVirtReg(
MI,
MI.getOperandNo(&MO),
Reg);
1610 if (ReArrangedImplicitOps)
1621 for (MachineOperand &MO :
reverse(
MI.all_defs())) {
1632 "tied def assigned to clobbered register");
1647 unmarkRegUsedInInstr(
Reg);
1656 for (
const auto *RM : RegMasks)
1659 for (
const LiveReg &LR : LiveVirtRegs) {
1660 MCRegister PhysReg = LR.PhysReg;
1661 if (PhysReg && isClobberedByRegMasks(PhysReg))
1662 displacePhysReg(
MI, PhysReg);
1667 if (HasPhysRegUse) {
1668 for (MachineOperand &MO :
MI.operands()) {
1676 if (!usePhysReg(
MI,
Reg))
1684 bool HasUndefUse =
false;
1685 bool ReArrangedImplicitMOs =
true;
1686 while (ReArrangedImplicitMOs) {
1687 ReArrangedImplicitMOs =
false;
1688 for (MachineOperand &MO :
MI.operands()) {
1706 ReArrangedImplicitMOs = useVirtReg(
MI, MO,
Reg);
1707 if (ReArrangedImplicitMOs)
1716 for (MachineOperand &MO :
MI.all_uses()) {
1721 assert(MO.
isUndef() &&
"Should only have undef virtreg uses left");
1722 allocVirtRegUndef(MO);
1728 if (HasEarlyClobber) {
1729 for (MachineOperand &MO :
reverse(
MI.all_defs())) {
1732 assert(!MO.
getSubReg() &&
"should be already handled in def processing");
1758 (
MI.getOperand(0).getReg() ==
MI.getOperand(1).getReg() ||
1759 MI.getOperand(0).isDead()) &&
1760 MI.getNumOperands() == 2) {
1766void RegAllocFastImpl::handleDebugValue(MachineInstr &
MI) {
1769 assert(
MI.isDebugValue() &&
"not a DBG_VALUE*");
1770 for (
const auto &MO :
MI.debug_operands()) {
1776 if (!shouldAllocateRegister(
Reg))
1780 int SS = StackSlotForVirtReg[
Reg];
1790 LiveRegMap::iterator LRI = findLiveVirtReg(
Reg);
1794 if (LRI != LiveVirtRegs.end() && LRI->PhysReg) {
1796 for (
auto &RegMO : DbgOps)
1797 setPhysReg(
MI, *RegMO, *LRI);
1799 DanglingDbgValues[
Reg].push_back(&
MI);
1804 LiveDbgValueMap[
Reg].append(DbgOps.begin(), DbgOps.end());
1808void RegAllocFastImpl::handleBundle(MachineInstr &
MI) {
1811 while (BundledMI->isBundledWithPred()) {
1812 for (MachineOperand &MO : BundledMI->operands()) {
1820 auto DI = BundleVirtRegsMap.
find(
Reg);
1821 assert(DI != BundleVirtRegsMap.
end() &&
"Unassigned virtual register");
1823 setPhysReg(
MI, MO, DI->second);
1830void RegAllocFastImpl::allocateBasicBlock(MachineBasicBlock &
MBB) {
1834 PosIndexes.unsetInitialized();
1835 RegUnitStates.assign(
TRI->getNumRegUnits(), regFree);
1836 assert(LiveVirtRegs.empty() &&
"Mapping not cleared from last block?");
1839 setPhysRegState(LiveReg.PhysReg, regPreAssigned);
1849 if (
MI.isDebugValue()) {
1850 handleDebugValue(
MI);
1854 allocateInstruction(
MI);
1858 if (
MI.getOpcode() == TargetOpcode::BUNDLE) {
1866 LLVM_DEBUG(
dbgs() <<
"Loading live registers at begin of block.\n");
1871 for (MachineInstr *
MI : Coalesced)
1873 NumCoalesced += Coalesced.size();
1875 for (
auto &UDBGPair : DanglingDbgValues) {
1876 for (MachineInstr *DbgValue : UDBGPair.second) {
1881 LLVM_DEBUG(
dbgs() <<
"Register did not survive for " << *DbgValue
1886 DanglingDbgValues.clear();
1892 LLVM_DEBUG(
dbgs() <<
"********** FAST REGISTER ALLOCATION **********\n"
1893 <<
"********** Function: " << MF.
getName() <<
'\n');
1901 unsigned NumRegUnits =
TRI->getNumRegUnits();
1903 UsedInInstr.
assign(NumRegUnits, 0);
1908 StackSlotForVirtReg.
resize(NumVirtRegs);
1909 LiveVirtRegs.setUniverse(NumVirtRegs);
1910 MayLiveAcrossBlocks.
clear();
1911 MayLiveAcrossBlocks.
resize(NumVirtRegs);
1914 for (MachineBasicBlock &
MBB : MF)
1915 allocateBasicBlock(
MBB);
1917 if (ClearVirtRegs) {
1923 StackSlotForVirtReg.
clear();
1924 LiveDbgValueMap.
clear();
1931 RegAllocFastImpl Impl(Opts.Filter, Opts.ClearVRegs);
1932 bool Changed = Impl.runOnMachineFunction(MF);
1942 bool PrintFilterName = Opts.FilterName !=
"all";
1943 bool PrintNoClearVRegs = !Opts.ClearVRegs;
1944 bool PrintSemicolon = PrintFilterName && PrintNoClearVRegs;
1946 OS <<
"regallocfast";
1947 if (PrintFilterName || PrintNoClearVRegs) {
1949 if (PrintFilterName)
1950 OS <<
"filter=" << Opts.FilterName;
1953 if (PrintNoClearVRegs)
1954 OS <<
"no-clear-vregs";
1962 bool ClearVirtRegs) {
1963 return new RegAllocFast(Ftor, ClearVirtRegs);
assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")
static GCRegistry::Add< ShadowStackGC > C("shadow-stack", "Very portable GC for uncooperative code generators")
static GCRegistry::Add< ErlangGC > A("erlang", "erlang-compatible garbage collector")
static GCRegistry::Add< CoreCLRGC > E("coreclr", "CoreCLR-compatible GC")
static GCRegistry::Add< OcamlGC > B("ocaml", "ocaml 3.10-compatible GC")
#define LLVM_UNLIKELY(EXPR)
This file defines the DenseMap class.
const HexagonInstrInfo * TII
This file implements an indexed map.
Register const TargetRegisterInfo * TRI
This file implements a map that provides insertion order iteration.
Promote Memory to Register
#define INITIALIZE_PASS(passName, arg, name, cfg, analysis)
static bool isCoalescable(const MachineInstr &MI)
static cl::opt< bool > IgnoreMissingDefs("rafast-ignore-missing-defs", cl::Hidden)
static bool isLiveThroughDef(const MachineInstr &MI, const MachineOperand &MO)
Early clobber, partial def, or tied to a use that carries a value: the register is occupied while the...
static bool dominates(InstrPosIndexes &PosIndexes, const MachineInstr &A, const MachineInstr &B)
static RegisterRegAlloc fastRegAlloc("fast", "fast register allocator", createFastRegisterAllocator)
This file defines the SmallSet class.
This file defines the SmallVector class.
This file defines the SparseSet class derived from the version described in Briggs,...
This file defines the 'Statistic' class, which is designed to be an easy way to expose various metric...
#define STATISTIC(VARNAME, DESC)
LLVM_ABI void setPreservesCFG()
This function should be called by the pass, iff they do not:
const T & front() const
Get the first element.
size_t size() const
Get the array size.
bool empty() const
Check if the array is empty.
bool test(unsigned Idx) const
Returns true if bit Idx is set.
void resize(unsigned N, bool t=false)
Grow or shrink the bitvector.
void clear()
Removes all bits from the bitvector.
BitVector & set()
Set all bits in the bitvector.
Represents analyses that only rely on functions' control flow.
iterator find(const_arg_type_t< KeyT > Val)
FunctionPass class - This class is used to implement most global optimizations.
LLVMContext & getContext() const
getContext - Return a reference to the LLVMContext associated with this function.
void storeRegToStackSlot(MachineBasicBlock &MBB, MachineBasicBlock::iterator MBBI, Register SrcReg, bool isKill, int FrameIndex, const TargetRegisterClass *RC, Register VReg, MachineInstr::MIFlag Flags=MachineInstr::NoFlags) const override
Store the specified register of the given register class to the specified stack frame index.
void loadRegFromStackSlot(MachineBasicBlock &MBB, MachineBasicBlock::iterator MBBI, Register DestReg, int FrameIndex, const TargetRegisterClass *RC, Register VReg, unsigned SubReg=0, MachineInstr::MIFlag Flags=MachineInstr::NoFlags) const override
Load the specified register of the given register class from the specified stack frame index.
Register isStoreToStackSlot(const MachineInstr &MI, int &FrameIndex) const override
If the specified machine instruction is a direct store to a stack slot, return the virtual or physica...
void resize(typename StorageT::size_type S)
LLVM_ABI void diagnose(const DiagnosticInfo &DI)
Report a message to the currently installed diagnostic handler.
unsigned getID() const
getID() - Return the register class ID number.
ArrayRef< MCPhysReg > getRegisters() const
bool contains(MCRegister Reg) const
contains - Return true if the specified register is included in this register class.
bool hasSubClassEq(const MCRegisterClass *RC) const
Returns true if RC is a sub-class of or equal to this class.
constexpr bool isPhysical() const
Return true if the specified register number is in the physical register namespace.
An RAII based helper class to modify MachineFunctionProperties when running pass.
bool isInlineAsmBrIndirectTarget() const
Returns true if this is the indirect dest of an INLINEASM_BR.
iterator_range< liveout_iterator > liveouts() const
MachineInstrBundleIterator< const MachineInstr > const_iterator
LLVM_ABI instr_iterator insert(instr_iterator I, MachineInstr *M)
Insert MI into the instruction list before I, possibly inside a bundle.
iterator_range< livein_iterator > liveins() const
LLVM_ABI iterator getFirstTerminator()
Returns an iterator to the first terminator instruction of this basic block.
LLVM_ABI void dump() const
Instructions::iterator instr_iterator
void addLiveIn(MCRegister PhysReg, LaneBitmask LaneMask=LaneBitmask::getAll())
Adds the specified register as a live in.
const MachineFunction * getParent() const
Return the MachineFunction containing this basic block.
LLVM_ABI instr_iterator erase(instr_iterator I)
Remove an instruction from the instruction list and delete it.
LLVM_ABI bool isSuccessor(const MachineBasicBlock *MBB) const
Return true if the specified MBB is a successor of this block.
MachineInstrBundleIterator< MachineInstr > iterator
LLVM_ABI bool isLiveIn(MCRegister Reg, LaneBitmask LaneMask=LaneBitmask::getAll()) const
Return true if the specified register is in the live in set.
bool isSpillSlotObjectIndex(int ObjectIdx) const
Returns true if the specified index corresponds to a spill slot.
LLVM_ABI int CreateSpillStackObject(uint64_t Size, Align Alignment, TargetStackID::Value StackID=TargetStackID::Default)
Create a new statically sized stack object that represents a spill slot, returning a nonnegative iden...
MachineFunctionPass - This class adapts the FunctionPass interface to allow convenient creation of pa...
void getAnalysisUsage(AnalysisUsage &AU) const override
getAnalysisUsage - Subclasses that override getAnalysisUsage must call this.
const TargetSubtargetInfo & getSubtarget() const
getSubtarget - Return the subtarget for which this machine code is being compiled.
StringRef getName() const
getName - Return the name of the corresponding LLVM function.
MachineFrameInfo & getFrameInfo()
getFrameInfo - Return the frame info object for the current function.
MachineRegisterInfo & getRegInfo()
getRegInfo - Return information about the registers currently in use.
Function & getFunction()
Return the LLVM function that this machine code represents.
const MachineFunctionProperties & getProperties() const
Get the function properties.
const MachineBasicBlock & front() const
const MachineInstrBuilder & addReg(Register RegNo, RegState Flags={}, unsigned SubReg=0) const
Add a new virtual register operand.
Representation of each machine instruction.
bool hasDebugOperandForReg(Register Reg) const
Returns whether this debug value has at least one debug operand with the register Reg.
void setDebugValueUndef()
Sets all register debug operands in this debug value instruction to be undef.
const MachineBasicBlock * getParent() const
bool isDebugValue() const
MachineOperand class - Representation of each machine instruction operand.
void setSubReg(unsigned subReg)
unsigned getSubReg() const
bool readsReg() const
readsReg - Returns true if this operand reads the previous value of its register.
LLVM_ABI void setIsRenamable(bool Val=true)
bool isReg() const
isReg - Tests if this is a MO_Register operand.
bool isRegMask() const
isRegMask - Tests if this is a MO_RegisterMask operand.
MachineBasicBlock * getMBB() const
void setIsDead(bool Val=true)
LLVM_ABI void setReg(Register Reg)
Change the register this operand corresponds to.
void setIsKill(bool Val=true)
MachineInstr * getParent()
getParent - Return the instruction that this operand belongs to.
void setIsUndef(bool Val=true)
bool isEarlyClobber() const
Register getReg() const
getReg - Returns the register number.
bool isInternalRead() const
static bool clobbersPhysReg(const uint32_t *RegMask, MCRegister PhysReg)
clobbersPhysReg - Returns true if this RegMask clobbers PhysReg.
const uint32_t * getRegMask() const
getRegMask - Returns a bit mask of registers preserved by this RegMask operand.
bool isMBB() const
isMBB - Tests if this is a MO_MachineBasicBlock operand.
LLVM_ABI void freezeReservedRegs()
freezeReservedRegs - Called by the register allocator to freeze the set of reserved registers before ...
const TargetRegisterClass * getRegClass(Register Reg) const
Return the register class of the specified virtual register.
iterator_range< def_instr_iterator > def_instructions(Register Reg) const
bool isReserved(MCRegister PhysReg) const
isReserved - Returns true when PhysReg is a reserved register.
MachineOperand * getOneDef(Register Reg) const
Returns the defining operand if there is exactly one operand defining the specified register,...
LLVM_ABI void clearVirtRegs()
clearVirtRegs - Remove all virtual registers (after physreg assignment).
bool isAllocatable(MCRegister PhysReg) const
isAllocatable - Returns true when PhysReg belongs to an allocatable register class and it hasn't been...
iterator_range< use_instr_nodbg_iterator > use_nodbg_instructions(Register Reg) const
const MachineFunction & getMF() const
void addPhysRegsUsedFromRegMask(const uint32_t *RegMask)
addPhysRegsUsedFromRegMask - Mark any registers not in RegMask as used.
unsigned getNumVirtRegs() const
getNumVirtRegs - Return the number of virtual registers created.
A set of analyses that are preserved following a run of a transformation pass.
static PreservedAnalyses all()
Construct a special preserved set that preserves all passes.
LLVM_ABI PreservedAnalyses run(MachineFunction &MF, MachineFunctionAnalysisManager &)
LLVM_ABI void printPipeline(raw_ostream &OS, function_ref< StringRef(StringRef)> MapClassName2PassName)
LLVM_ABI void runOnMachineFunction(const MachineFunction &MF, bool Rev=false)
runOnFunction - Prepare to answer questions about MF.
ArrayRef< MCPhysReg > getOrder(const TargetRegisterClass *RC) const
getOrder - Returns the preferred allocation order for RC.
Wrapper class representing virtual and physical registers.
unsigned virtRegIndex() const
Convert a virtual register number to a 0-based index.
constexpr bool isValid() const
constexpr bool isVirtual() const
Return true if the specified register number is in the virtual register namespace.
constexpr unsigned id() const
constexpr bool isPhysical() const
Return true if the specified register number is in the physical register namespace.
size_type count(const T &V) const
count - Return 1 if the element is in the set, 0 otherwise.
std::pair< const_iterator, bool > insert(const T &V)
insert - Insert an element into the set if it isn't already there.
void assign(size_type NumElts, ValueParamT Elt)
void push_back(const T &Elt)
typename DenseT::const_iterator const_iterator
typename DenseT::iterator iterator
Represent a constant reference to a string, i.e.
virtual const TargetInstrInfo * getInstrInfo() const
virtual const TargetRegisterInfo * getRegisterInfo() const =0
Return the target's register information.
An efficient, type-erasing, non-owning reference to a callable.
This class implements an extremely fast bulk output stream that can only output to a stream.
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
constexpr char Align[]
Key for Kernel::Arg::Metadata::mAlign.
initializer< Ty > init(const Ty &Val)
NodeAddr< DefNode * > Def
This is an optimization pass for GlobalISel generic memory operations.
LLVM_ABI FunctionPass * createFastRegisterAllocator()
FastRegisterAllocation Pass - This pass register allocates as fast as possible.
std::function< bool(const TargetRegisterInfo &TRI, const MachineRegisterInfo &MRI, const Register Reg)> RegAllocFilterFunc
Filter function for register classes during regalloc.
MachineInstrBuilder BuildMI(MachineFunction &MF, const MIMetadata &MIMD, const MCInstrDesc &MCID)
Builder interface. Specify how to create the initial instruction itself.
@ Kill
The last use of a register.
LLVM_ABI void updateDbgValueForSpill(MachineInstr &Orig, int FrameIndex, Register Reg)
Update a DBG_VALUE whose value has been spilled to FrameIndex.
LLVM_ABI Printable printRegUnit(MCRegUnit Unit, const TargetRegisterInfo *TRI)
Create Printable object to print register units on a raw_ostream.
AnalysisManager< MachineFunction > MachineFunctionAnalysisManager
LLVM_ABI PreservedAnalyses getMachineFunctionPassPreservedAnalyses()
Returns the minimum set of Analyses that all machine function passes must preserve.
bool any_of(R &&range, UnaryPredicate P)
Provide wrappers to std::any_of which take ranges instead of having to pass begin/end explicitly.
auto reverse(ContainerTy &&C)
void sort(IteratorTy Start, IteratorTy End)
LLVM_ABI raw_ostream & dbgs()
dbgs() - This returns a reference to a raw_ostream for debugging messages.
class LLVM_GSL_OWNER SmallVector
Forward declaration of SmallVector so that calculateSmallVectorDefaultInlinedElements can reference s...
MutableArrayRef(T &OneElt) -> MutableArrayRef< T >
uint16_t MCPhysReg
An unsigned integer type large enough to represent all physical registers, but not necessarily virtua...
DWARFExpression::Operation Op
ArrayRef(const T &OneElt) -> ArrayRef< T >
LLVM_ABI MachineInstr * buildDbgValueForSpill(MachineBasicBlock &BB, MachineBasicBlock::iterator I, const MachineInstr &Orig, int FrameIndex, Register SpillReg)
Clone a DBG_VALUE whose value has been spilled to FrameIndex.
iterator_range< pointer_iterator< WrappedIteratorT > > make_pointer_range(RangeT &&Range)
LLVM_ABI Printable printReg(Register Reg, const TargetRegisterInfo *TRI=nullptr, unsigned SubIdx=0, const MachineRegisterInfo *MRI=nullptr)
Prints virtual and physical registers with or without a TRI instance.
MCRegisterClass TargetRegisterClass