16#define DEBUG_TYPE "execution-deps-fix"
20 assert(
Reg < AliasMap.size() &&
"Invalid register");
21 const auto &Entry = AliasMap[
Reg];
26 DomainValue *dv = Avail.empty() ?
new (Allocator.Allocate()) DomainValue
27 : Avail.pop_back_val();
30 assert(dv->
Refs == 0 &&
"Reference count wasn't cleared");
31 assert(!dv->
Next &&
"Chained DomainValue shouldn't have been recycled");
54 DomainValue *DV = DVRef;
70void ExecutionDomainFix::setLiveReg(
int rx,
DomainValue *dv) {
71 assert(
unsigned(rx) < NumRegs &&
"Invalid index");
72 assert(!LiveRegs.empty() &&
"Must enter basic block first.");
74 if (LiveRegs[rx] == dv)
78 LiveRegs[rx] = retain(dv);
81void ExecutionDomainFix::kill(
int rx) {
82 assert(
unsigned(rx) < NumRegs &&
"Invalid index");
83 assert(!LiveRegs.empty() &&
"Must enter basic block first.");
88 LiveRegs[rx] =
nullptr;
91void ExecutionDomainFix::force(
int rx,
unsigned domain) {
92 assert(
unsigned(rx) < NumRegs &&
"Invalid index");
93 assert(!LiveRegs.empty() &&
"Must enter basic block first.");
94 if (DomainValue *dv = LiveRegs[rx]) {
103 assert(LiveRegs[rx] &&
"Not live after collapse?");
104 LiveRegs[rx]->addDomain(domain);
108 setLiveReg(rx, alloc(domain));
112void ExecutionDomainFix::collapse(
DomainValue *dv,
unsigned domain) {
121 if (!LiveRegs.empty() && dv->
Refs > 1)
122 for (
unsigned rx = 0; rx != NumRegs; ++rx)
123 if (LiveRegs[rx] == dv)
124 setLiveReg(rx, alloc(domain));
128 assert(!
A->isCollapsed() &&
"Cannot merge into collapsed");
129 assert(!
B->isCollapsed() &&
"Cannot merge from collapsed");
133 unsigned common =
A->getCommonDomains(
B->AvailableDomains);
136 A->AvailableDomains = common;
137 A->Instrs.append(
B->Instrs.begin(),
B->Instrs.end());
144 for (
unsigned rx = 0; rx != NumRegs; ++rx) {
145 assert(!LiveRegs.empty() &&
"no space allocated for live registers");
146 if (LiveRegs[rx] ==
B)
152void ExecutionDomainFix::enterBasicBlock(
155 MachineBasicBlock *
MBB = TraversedMBB.
MBB;
159 if (LiveRegs.empty())
160 LiveRegs.assign(NumRegs,
nullptr);
170 assert(
unsigned(pred->getNumber()) < MBBOutRegsInfos.size() &&
171 "Should have pre-allocated MBBInfos for all MBBs");
172 LiveRegsDVInfo &Incoming = MBBOutRegsInfos[pred->getNumber()];
175 if (Incoming.empty())
178 for (
unsigned rx = 0; rx != NumRegs; ++rx) {
179 DomainValue *pdv = resolve(Incoming[rx]);
188 if (LiveRegs[rx]->isCollapsed()) {
190 unsigned Domain = LiveRegs[rx]->getFirstDomain();
198 merge(LiveRegs[rx], pdv);
204 << (!TraversedMBB.
IsDone ?
": incomplete\n"
205 :
": all preds known\n"));
208void ExecutionDomainFix::leaveBasicBlock(
210 assert(!LiveRegs.empty() &&
"Must enter basic block first.");
212 assert(MBBNumber < MBBOutRegsInfos.size() &&
213 "Unexpected basic block number.");
215 for (DomainValue *OldLiveReg : MBBOutRegsInfos[MBBNumber]) {
218 MBBOutRegsInfos[MBBNumber] = LiveRegs;
224 std::pair<uint16_t, uint16_t> DomP = TII->getExecutionDomain(*
MI);
227 visitSoftInstr(
MI, DomP.second);
229 visitHardInstr(
MI, DomP.first);
235void ExecutionDomainFix::processDefs(
MachineInstr *
MI,
bool Kill) {
236 assert(!
MI->isDebugInstr() &&
"Won't process debug values");
237 const MCInstrDesc &MCID =
MI->getDesc();
241 MachineOperand &MO =
MI->getOperand(i);
246 for (
int rx : regIndices(MO.
getReg())) {
257void ExecutionDomainFix::visitHardInstr(
MachineInstr *mi,
unsigned domain) {
265 for (
int rx : regIndices(mo.
getReg())) {
275 for (
int rx : regIndices(mo.
getReg())) {
282void ExecutionDomainFix::visitSoftInstr(
MachineInstr *mi,
unsigned mask) {
288 SmallVector<int, 4> used;
289 if (!LiveRegs.empty())
296 for (
int rx : regIndices(mo.
getReg())) {
297 DomainValue *dv = LiveRegs[rx];
322 TII->setExecutionDomain(*mi, domain);
323 visitHardInstr(mi, domain);
329 SmallVector<int, 4> Regs;
330 for (
int rx : used) {
331 assert(!LiveRegs.empty() &&
"no space allocated for live registers");
332 DomainValue *&LR = LiveRegs[rx];
340 const int Def = RDA->getReachingDef(mi, RC->getRegister(rx));
342 return RDA->getReachingDef(mi, RC->getRegister(
I)) <=
Def;
349 DomainValue *dv =
nullptr;
350 while (!Regs.
empty()) {
361 if (Latest == dv || Latest->
Next)
363 if (merge(dv, Latest))
368 assert(!LiveRegs.empty() &&
"no space allocated for live registers");
369 if (LiveRegs[i] == Latest)
383 for (
const MachineOperand &mo : mi->
operands()) {
386 for (
int rx : regIndices(mo.
getReg())) {
387 if (!LiveRegs[rx] || (mo.
isDef() && LiveRegs[rx] != dv)) {
395void ExecutionDomainFix::processBasicBlock(
397 enterBasicBlock(TraversedMBB);
402 for (MachineInstr &
MI : *TraversedMBB.
MBB) {
403 if (!
MI.isDebugInstr()) {
407 processDefs(&
MI, Kill);
410 leaveBasicBlock(TraversedMBB);
418 TRI = MF->getSubtarget().getRegisterInfo();
420 assert(NumRegs == RC->getNumRegs() &&
"Bad regclass");
423 << TRI->getRegClassName(RC) <<
" **********\n");
427 bool anyregs =
false;
429 for (
unsigned Reg : *RC) {
430 if (
MRI.isPhysRegUsed(Reg)) {
441 if (AliasMap.empty()) {
444 AliasMap.resize(TRI->getNumRegs());
445 for (
unsigned i = 0, e = RC->getNumRegs(); i != e; ++i)
448 AliasMap[(*AI).id()].push_back(i);
458 processBasicBlock(TraversedMBB);
460 for (
const LiveRegsDVInfo &OutLiveRegs : MBBOutRegsInfos)
465 MBBOutRegsInfos.clear();
467 Allocator.DestroyAll();
unsigned const MachineRegisterInfo * MRI
assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")
static GCRegistry::Add< ErlangGC > A("erlang", "erlang-compatible garbage collector")
static GCRegistry::Add< OcamlGC > B("ocaml", "ocaml 3.10-compatible GC")
return !LiveInRegUnits available(Reg)
bool runOnMachineFunction(MachineFunction &MF) override
runOnMachineFunction - This method must be overloaded to perform the desired machine code transformat...
bool skipFunction(const Function &F) const
Optional passes call this function to check whether the pass should be skipped.
This class provides the basic blocks traversal order used by passes like ReachingDefAnalysis and Exec...
TraversalOrder traverse(MachineFunction &MF)
SmallVector< TraversedMBBInfo, 4 > TraversalOrder
Identifies basic blocks that are part of loops and should to be visited twice and returns efficient t...
unsigned getNumOperands() const
Return the number of declared MachineOperands for this MachineInstruction.
unsigned getNumDefs() const
Return the number of MachineOperands that are register definitions.
MCRegAliasIterator enumerates all registers aliasing Reg.
Wrapper class representing physical registers. Should be passed by value.
int getNumber() const
MachineBasicBlocks are uniquely numbered at the function level, unless they're not in a MachineFuncti...
iterator_range< pred_iterator > predecessors()
const TargetSubtargetInfo & getSubtarget() const
getSubtarget - Return the subtarget for which this machine code is being compiled.
MachineRegisterInfo & getRegInfo()
getRegInfo - Return information about the registers currently in use.
Function & getFunction()
Return the LLVM function that this machine code represents.
unsigned getNumBlockIDs() const
getNumBlockIDs - Return the number of MBB ID's allocated.
Representation of each machine instruction.
const MCInstrDesc & getDesc() const
Returns the target instruction descriptor of this MachineInstr.
const MachineOperand & getOperand(unsigned i) const
bool isReg() const
isReg - Tests if this is a MO_Register operand.
Register getReg() const
getReg - Returns the register number.
MachineRegisterInfo - Keep track of information for virtual and physical registers,...
AnalysisType & getAnalysis() const
getAnalysis<AnalysisType>() - This function is used by subclasses to get to the analysis information ...
iterator insert(iterator I, T &&Elt)
void push_back(const T &Elt)
virtual const TargetInstrInfo * getInstrInfo() const
A range adaptor for a pair of iterators.
@ Kill
The last use of a register.
NodeAddr< DefNode * > Def
This is an optimization pass for GlobalISel generic memory operations.
auto partition_point(R &&Range, Predicate P)
Binary search for the first iterator in a range where a predicate is false.
iterator_range< T > make_range(T x, T y)
Convenience function for iterating over sub-ranges.
int countr_zero(T Val)
Count number of 0's from the least significant bit to the most stopping at the first 1.
constexpr bool isPowerOf2_32(uint32_t Value)
Return true if the argument is a power of two > 0.
LLVM_ABI raw_ostream & dbgs()
dbgs() - This returns a reference to a raw_ostream for debugging messages.
FunctionAddr VTableAddr Next
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.
LLVM_ABI Printable printMBBReference(const MachineBasicBlock &MBB)
Prints a machine basic block reference.
auto mask(ShuffFunc S, unsigned Length, OptArgs... args) -> MaskT
A DomainValue is a bit like LiveIntervals' ValNo, but it also keeps track of execution domains.
unsigned getCommonDomains(unsigned mask) const
Return bitmask of domains that are available and in mask.
void clear()
Clear this DomainValue and point to next which has all its data.
SmallVector< MachineInstr *, 8 > Instrs
Twiddleable instructions using or defining these registers.
void setSingleDomain(unsigned domain)
bool isCollapsed() const
A collapsed DomainValue has no instructions to twiddle - it simply keeps track of the domains where t...
DomainValue * Next
Pointer to the next DomainValue in a chain.
void addDomain(unsigned domain)
Mark domain as available.
unsigned AvailableDomains
Bitmask of available domains.
unsigned Refs
Basic reference counting.
unsigned getFirstDomain() const
First domain available.
bool hasDomain(unsigned domain) const
Is domain available?
MachineBasicBlock * MBB
The basic block.
bool IsDone
True if the block that is ready for its final round of processing.
bool PrimaryPass
True if this is the first time we process the basic block.