70#define DEBUG_TYPE "machine-sink"
74 cl::desc(
"Split critical edges during machine sinking"),
79 cl::desc(
"Use block frequency info to find successors to sink"),
83 "machine-sink-split-probability-threshold",
85 "Percentage threshold for splitting single-instruction critical edge. "
86 "If the branch threshold is higher than this threshold, we allow "
87 "speculative execution of up to 1 instruction to avoid branching to "
88 "splitted critical edge"),
92 "machine-sink-load-instrs-threshold",
93 cl::desc(
"Do not try to find alias store for a load if there is a in-path "
94 "block whose instruction number is higher than this threshold."),
98 "machine-sink-load-blocks-threshold",
99 cl::desc(
"Do not try to find alias store for a load if the block number in "
100 "the straight line is higher than this threshold."),
105 cl::desc(
"Sink instructions into cycles to avoid "
110 "machine-sink-cycle-limit",
112 "The maximum number of instructions considered for cycle sinking."),
115STATISTIC(NumSunk,
"Number of machine instructions sunk");
116STATISTIC(NumCycleSunk,
"Number of machine instructions sunk into a cycle");
119STATISTIC(NumPostRACopySink,
"Number of copies sunk after RA");
125class MachineSinking {
162 using AllSuccsCache =
176 using SinkItem = std::pair<MachineInstr *, MachineBasicBlock *>;
195 CachedRegisterPressure;
197 bool EnableSinkAndFold;
206 : DT(DT), PDT(PDT), CI(CI), PSI(PSI), MBFI(MBFI), MBPI(MBPI),
AA(
AA),
207 RegClassInfo(RegClassInfo), LIS(LIS),
SI(
SI), MLI(MLI),
208 EnableSinkAndFold(EnableSinkAndFold) {}
212 void releaseMemory() {
213 CEBCandidates.
clear();
214 CEMergeCandidates.
clear();
244 AllSuccsCache &AllSuccessors);
254 bool &LocalUse)
const;
257 AllSuccsCache &AllSuccessors);
269 AllSuccsCache &AllSuccessors);
278 AllSuccsCache &AllSuccessors)
const;
281 bool UseCache =
true);
283 bool registerPressureSetExceedsLimit(
unsigned NRegs,
320char MachineSinkingLegacy::ID = 0;
346 if (!TII->isBasicBlockPrologue(*PI))
348 for (auto &MO : MI.operands()) {
351 Register Reg = MO.getReg();
355 if (Reg.isPhysical() &&
356 (TII->isIgnorableUse(MI, MI.getOperandNo(&MO)) ||
357 (MRI && MRI->isConstantPhysReg(Reg))))
359 if (PI->modifiesRegister(Reg, TRI))
362 if (PI->readsRegister(Reg, TRI))
365 auto *DefOp = PI->findRegisterDefOperand(Reg, TRI, false, true);
366 if (DefOp && !DefOp->isDead())
375bool MachineSinking::PerformTrivialForwardCoalescing(
MachineInstr &
MI,
397 MI.eraseFromParent();
407bool MachineSinking::PerformSinkAndFold(MachineInstr &
MI,
408 MachineBasicBlock *
MBB) {
409 if (
MI.isCopy() ||
MI.mayLoadOrStore() ||
410 MI.getOpcode() == TargetOpcode::REG_SEQUENCE)
418 bool SawStore =
true;
419 if (!
MI.isSafeToMove(SawStore))
424 if (
MI.isConvergent())
433 for (
const MachineOperand &MO :
MI.operands()) {
434 if (MO.isImm() || MO.isRegMask() || MO.isRegLiveOut() || MO.isMetadata() ||
435 MO.isMCSymbol() || MO.isDbgInstrRef() || MO.isCFIIndex() ||
436 MO.isIntrinsicID() || MO.isPredicate() || MO.isShuffleMask())
455 else if (UsedRegB == 0)
464 TII->isIgnorableUse(
MI,
MI.getOperandNo(&MO))))
474 using SinkInfo = std::pair<MachineInstr *, ExtAddrMode>;
480 UsedRegA == 0 ? nullptr : MRI->
getRegClass(UsedRegA);
482 UsedRegB == 0 ? nullptr : MRI->
getRegClass(UsedRegB);
485 while (!Worklist.
empty()) {
490 MachineInstr &UseInst = *MO.getParent();
493 if (
const MachineOperand &O = UseInst.
getOperand(0);
O.isReg())
514 return MO.isReg() && MO.getReg() == Reg;
518 if (!
TII->canFoldIntoAddrMode(UseInst,
Reg,
MI, AM))
535 if (RCA ==
nullptr) {
540 unsigned NRegs = !!RCA + !!RCB;
546 if (RCB ==
nullptr) {
547 if (registerPressureSetExceedsLimit(NRegs, RCA,
MBB))
549 }
else if (registerPressureSetExceedsLimit(1, RCA,
MBB) ||
550 registerPressureSetExceedsLimit(1, RCB,
MBB)) {
560 if (SinkInto.
empty())
564 for (
auto &[SinkDst, MaybeAM] : SinkInto) {
565 MachineInstr *
New =
nullptr;
568 if (SinkDst->isCopy()) {
581 Register DstReg = SinkDst->getOperand(0).getReg();
582 TII->reMaterialize(*SinkDst->getParent(), InsertPt, DstReg, 0,
MI);
583 New = &*std::prev(InsertPt);
584 if (!
New->getDebugLoc())
585 New->setDebugLoc(SinkDst->getDebugLoc());
596 New =
TII->emitLdStWithAddr(*SinkDst, MaybeAM);
608 if (SinkDst->mayStore() && !SinkDst->hasOrderedMemoryRef())
609 StoreInstrCache.clear();
610 SinkDst->eraseFromParent();
618 while (!Worklist.
empty()) {
622 assert((
U->isCopy() ||
U->isDebugInstr()) &&
623 "Only debug uses and copies must remain");
625 Worklist.
push_back(
U->getOperand(0).getReg());
631 for (MachineOperand *MO :
Cleanup) {
634 I->eraseFromParent();
641 MI.eraseFromParent();
649bool MachineSinking::AllUsesDominatedByBlock(
Register Reg,
650 MachineBasicBlock *
MBB,
651 MachineBasicBlock *DefMBB,
653 bool &LocalUse)
const {
675 MachineInstr *UseInst = MO.getParent();
676 unsigned OpNo = MO.getOperandNo();
677 MachineBasicBlock *UseBlock = UseInst->getParent();
678 return UseBlock == MBB && UseInst->isPHI() &&
679 UseInst->getOperand(OpNo + 1).getMBB() == DefMBB;
688 unsigned OpNo = &MO - &UseInst->
getOperand(0);
689 MachineBasicBlock *UseBlock = UseInst->
getParent();
690 if (UseInst->
isPHI()) {
694 }
else if (UseBlock == DefMBB) {
710 assert(
MI.mayLoad() &&
"Expected MI that loads!");
714 if (
MI.memoperands_empty())
719 if (PSV->isGOT() || PSV->isConstantPool())
725void MachineSinking::FindCycleSinkCandidates(
726 CycleRef Cycle, MachineBasicBlock *BB,
727 SmallVectorImpl<MachineInstr *> &Candidates) {
728 for (
auto &
MI : *BB) {
730 if (
MI.isMetaInstruction()) {
731 LLVM_DEBUG(
dbgs() <<
"CycleSink: not sinking meta instruction\n");
735 LLVM_DEBUG(
dbgs() <<
"CycleSink: Instruction not a candidate for this "
740 LLVM_DEBUG(
dbgs() <<
"CycleSink: Instruction is not cycle invariant\n");
743 bool DontMoveAcrossStore =
true;
744 if (!
MI.isSafeToMove(DontMoveAcrossStore)) {
745 LLVM_DEBUG(
dbgs() <<
"CycleSink: Instruction not safe to move.\n");
749 LLVM_DEBUG(
dbgs() <<
"CycleSink: Dont sink GOT or constant pool loads\n");
752 if (
MI.isConvergent())
755 const MachineOperand &MO =
MI.getOperand(0);
761 LLVM_DEBUG(
dbgs() <<
"CycleSink: Instruction added as candidate.\n");
773 .getCachedResult<ProfileSummaryAnalysis>(
786 MachineSinking Impl(EnableSinkAndFold, DT, PDT, MLI,
SI, LIS, CI, PSI, MBFI,
787 MBPI,
AA, RegClassInfo);
801 OS << MapClassName2PassName(
name());
802 if (EnableSinkAndFold)
803 OS <<
"<enable-sink-fold>";
813 auto *DT = &getAnalysis<MachineDominatorTreeWrapperPass>().getDomTree();
815 &getAnalysis<MachinePostDominatorTreeWrapperPass>().getPostDomTree();
816 auto *CI = &getAnalysis<MachineCycleInfoWrapperPass>().getCycleInfo();
817 auto *PSI = &getAnalysis<ProfileSummaryInfoWrapperPass>().getPSI();
820 ? &getAnalysis<MachineBlockFrequencyInfoWrapperPass>().getMBFI()
823 &getAnalysis<MachineBranchProbabilityInfoWrapperPass>().getMBPI();
824 auto *
AA = &getAnalysis<AAResultsWrapperPass>().getAAResults();
826 auto *LISWrapper = getAnalysisIfAvailable<LiveIntervalsWrapperPass>();
827 auto *LIS = LISWrapper ? &LISWrapper->getLIS() :
nullptr;
828 auto *SIWrapper = getAnalysisIfAvailable<SlotIndexesWrapperPass>();
829 auto *
SI = SIWrapper ? &SIWrapper->getSI() :
nullptr;
830 auto *MLIWrapper = getAnalysisIfAvailable<MachineLoopInfoWrapperPass>();
831 auto *MLI = MLIWrapper ? &MLIWrapper->getLI() :
nullptr;
833 &getAnalysis<MachineRegisterClassInfoWrapperPass>().getRCI();
835 MachineSinking Impl(EnableSinkAndFold, DT, PDT, MLI,
SI, LIS, CI, PSI, MBFI,
836 MBPI,
AA, RegClassInfo);
848 bool EverMadeChange =
false;
851 bool MadeChange =
false;
854 CEBCandidates.clear();
855 CEMergeCandidates.clear();
862 MachineDomTreeUpdater::UpdateStrategy::Lazy);
863 for (
const auto &Pair : ToSplit) {
864 auto NewSucc = Pair.first->SplitCriticalEdge(
865 Pair.second, {LIS, SI, nullptr, MLI},
nullptr, &MDTU);
866 if (NewSucc !=
nullptr) {
883 EverMadeChange =
true;
888 SchedModel.
init(STI);
889 bool HasHighPressure;
891 DenseMap<SinkItem, MachineInstr *> SunkInstrs;
893 enum CycleSinkStage { COPY, LOW_LATENCY, AGGRESSIVE, END };
894 for (
unsigned Stage = CycleSinkStage::COPY; Stage != CycleSinkStage::END;
895 ++Stage, SunkInstrs.
clear()) {
896 HasHighPressure =
false;
898 for (
auto Cycle : Cycles) {
904 SmallVector<MachineInstr *, 8> Candidates;
905 FindCycleSinkCandidates(Cycle, Preheader, Candidates);
914 if (Stage == CycleSinkStage::COPY) {
917 <<
"CycleSink: Limit reached of instructions to "
928 if (Stage == CycleSinkStage::LOW_LATENCY &&
929 !
TII->hasLowDefLatency(SchedModel, *
I, 0))
932 if (!aggressivelySinkIntoCycle(Cycle, *
I, SunkInstrs))
934 EverMadeChange =
true;
939 if (!HasHighPressure)
940 HasHighPressure = registerPressureExceedsLimit(*Preheader);
942 if (!HasHighPressure)
947 HasStoreCache.clear();
948 StoreInstrCache.clear();
951 for (
auto I : RegsToClearKillFlags)
953 RegsToClearKillFlags.clear();
956 return EverMadeChange;
959bool MachineSinking::ProcessBlock(MachineBasicBlock &
MBB) {
969 bool MadeChange =
false;
972 AllSuccsCache AllSuccessors;
977 bool ProcessedBegin, SawStore =
false;
979 MachineInstr &
MI = *
I;
987 if (
MI.isDebugOrPseudoInstr() ||
MI.isFakeUse()) {
988 if (
MI.isDebugValue())
993 if (EnableSinkAndFold && PerformSinkAndFold(
MI, &
MBB)) {
1002 if (PerformTrivialForwardCoalescing(
MI, &
MBB)) {
1013 }
while (!ProcessedBegin);
1015 SeenDbgUsers.clear();
1016 SeenDbgVars.clear();
1018 CachedRegisterPressure.clear();
1022void MachineSinking::ProcessDbgInst(MachineInstr &
MI) {
1025 assert(
MI.isDebugValue() &&
"Expected DBG_VALUE for processing");
1027 DebugVariable Var(
MI.getDebugVariable(),
MI.getDebugExpression(),
1028 MI.getDebugLoc()->getInlinedAt());
1029 bool SeenBefore = SeenDbgVars.contains(Var);
1031 for (MachineOperand &MO :
MI.debug_operands()) {
1033 SeenDbgUsers[MO.
getReg()].push_back(SeenDbgUser(&
MI, SeenBefore));
1037 SeenDbgVars.insert(Var);
1040bool MachineSinking::isWorthBreakingCriticalEdge(
1041 MachineInstr &
MI, MachineBasicBlock *From, MachineBasicBlock *To,
1042 MachineBasicBlock *&DeferredFromBlock) {
1048 if (!CEBCandidates.insert(std::make_pair(From, To)).second)
1059 for (
const auto &MO :
MI.all_defs()) {
1064 auto Key = std::make_pair(SrcReg, To);
1065 auto Res = CEMergeCandidates.try_emplace(
Key, From);
1070 DeferredFromBlock = Res.first->second;
1083 for (
const MachineOperand &MO :
MI.all_uses()) {
1108 return TII->shouldBreakCriticalEdgeToSink(
MI);
1111bool MachineSinking::isLegalToBreakCriticalEdge(MachineInstr &
MI,
1112 MachineBasicBlock *FromBB,
1113 MachineBasicBlock *ToBB,
1114 bool BreakPHIEdge) {
1119 CycleRef FromCycle = CI->
getCycle(FromBB);
1120 CycleRef ToCycle = CI->
getCycle(ToBB);
1123 if (FromCycle == ToCycle && FromCycle &&
1166 if (!BreakPHIEdge) {
1168 if (Pred != FromBB && !DT->
dominates(ToBB, Pred))
1175bool MachineSinking::PostponeSplitCriticalEdge(MachineInstr &
MI,
1176 MachineBasicBlock *FromBB,
1177 MachineBasicBlock *ToBB,
1178 bool BreakPHIEdge) {
1179 bool Status =
false;
1180 MachineBasicBlock *DeferredFromBB =
nullptr;
1181 if (isWorthBreakingCriticalEdge(
MI, FromBB, ToBB, DeferredFromBB)) {
1184 if ((!DeferredFromBB ||
1185 ToSplit.count(std::make_pair(DeferredFromBB, ToBB)) ||
1186 isLegalToBreakCriticalEdge(
MI, DeferredFromBB, ToBB, BreakPHIEdge)) &&
1187 isLegalToBreakCriticalEdge(
MI, FromBB, ToBB, BreakPHIEdge)) {
1188 ToSplit.insert(std::make_pair(FromBB, ToBB));
1190 ToSplit.insert(std::make_pair(DeferredFromBB, ToBB));
1198std::vector<unsigned> &
1199MachineSinking::getBBRegisterPressure(
const MachineBasicBlock &
MBB,
1206 auto RP = CachedRegisterPressure.find(&
MBB);
1207 if (UseCache && RP != CachedRegisterPressure.end())
1210 RegionPressure Pressure;
1211 RegPressureTracker RPTracker(Pressure);
1219 MII != MIE; --MII) {
1220 const MachineInstr &
MI = *std::prev(MII);
1221 if (
MI.isDebugOrPseudoInstr())
1223 RegisterOperands RegOpers;
1225 RPTracker.recedeSkipDebugValues();
1226 assert(&*RPTracker.getPos() == &
MI &&
"RPTracker sync error!");
1227 RPTracker.recede(RegOpers);
1230 RPTracker.closeRegion();
1232 if (RP != CachedRegisterPressure.end()) {
1233 CachedRegisterPressure[&
MBB] = RPTracker.getPressure().MaxSetPressure;
1234 return CachedRegisterPressure[&
MBB];
1237 auto It = CachedRegisterPressure.insert(
1238 std::make_pair(&
MBB, RPTracker.getPressure().MaxSetPressure));
1239 return It.first->second;
1242bool MachineSinking::registerPressureSetExceedsLimit(
1244 const MachineBasicBlock &
MBB) {
1245 unsigned Weight = NRegs *
TRI->getRegClassWeight(RC).RegWeight;
1246 const int *PS =
TRI->getRegClassPressureSets(RC);
1247 std::vector<unsigned> BBRegisterPressure = getBBRegisterPressure(
MBB);
1248 for (; *PS != -1; PS++)
1249 if (Weight + BBRegisterPressure[*PS] >=
1256bool MachineSinking::registerPressureExceedsLimit(
1257 const MachineBasicBlock &
MBB) {
1258 std::vector<unsigned> BBRegisterPressure = getBBRegisterPressure(
MBB,
false);
1260 for (
unsigned PS = 0; PS < BBRegisterPressure.size(); ++PS) {
1270bool MachineSinking::isProfitableToSinkTo(
Register Reg, MachineInstr &
MI,
1271 MachineBasicBlock *
MBB,
1272 MachineBasicBlock *SuccToSinkTo,
1273 AllSuccsCache &AllSuccessors) {
1274 assert(SuccToSinkTo &&
"Invalid SinkTo Candidate BB");
1276 if (
MBB == SuccToSinkTo)
1289 bool NonPHIUse =
false;
1291 MachineBasicBlock *UseBlock = UseInst.
getParent();
1292 if (UseBlock == SuccToSinkTo && !UseInst.
isPHI())
1300 bool BreakPHIEdge =
false;
1302 if (MachineBasicBlock *MBB2 =
1303 FindSuccToSinkTo(
MI, SuccToSinkTo, BreakPHIEdge, AllSuccessors))
1304 return isProfitableToSinkTo(
Reg,
MI, SuccToSinkTo, MBB2, AllSuccessors);
1315 for (
const MachineOperand &MO :
MI.operands()) {
1326 !
TII->isIgnorableUse(
MI,
MI.getOperandNo(&MO)))
1334 bool LocalUse =
false;
1335 if (!AllUsesDominatedByBlock(
Reg, SuccToSinkTo,
MBB, BreakPHIEdge,
1347 if (Cycle != MCycle ||
1356 LLVM_DEBUG(
dbgs() <<
"register pressure exceed limit, not profitable.");
1370SmallVector<MachineBasicBlock *, 4> &
1371MachineSinking::GetAllSortedSuccessors(MachineInstr &
MI, MachineBasicBlock *
MBB,
1372 AllSuccsCache &AllSuccessors)
const {
1374 auto Succs = AllSuccessors.find(
MBB);
1375 if (Succs != AllSuccessors.end())
1376 return Succs->second;
1378 SmallVector<MachineBasicBlock *, 4> AllSuccs(
MBB->
successors());
1389 if (DTChild->getIDom()->getBlock() ==
MI.getParent() &&
1392 AllSuccs.push_back(DTChild->getBlock());
1397 AllSuccs, [&](
const MachineBasicBlock *L,
const MachineBasicBlock *R) {
1401 (!LHSFreq && !RHSFreq))
1403 return LHSFreq < RHSFreq;
1406 auto it = AllSuccessors.insert(std::make_pair(
MBB, AllSuccs));
1408 return it.first->second;
1413MachineSinking::FindSuccToSinkTo(MachineInstr &
MI, MachineBasicBlock *
MBB,
1415 AllSuccsCache &AllSuccessors) {
1416 assert(
MBB &&
"Invalid MachineBasicBlock!");
1423 MachineBasicBlock *SuccToSinkTo =
nullptr;
1424 for (
const MachineOperand &MO :
MI.operands()) {
1438 !
TII->isIgnorableUse(
MI,
MI.getOperandNo(&MO)))
1440 }
else if (!MO.
isDead()) {
1458 bool LocalUse =
false;
1459 if (!AllUsesDominatedByBlock(
Reg, SuccToSinkTo,
MBB, BreakPHIEdge,
1470 for (MachineBasicBlock *SuccBlock :
1471 GetAllSortedSuccessors(
MI,
MBB, AllSuccessors)) {
1472 bool LocalUse =
false;
1473 if (AllUsesDominatedByBlock(
Reg, SuccBlock,
MBB, BreakPHIEdge,
1475 SuccToSinkTo = SuccBlock;
1486 if (!isProfitableToSinkTo(
Reg,
MI,
MBB, SuccToSinkTo, AllSuccessors))
1493 if (
MBB == SuccToSinkTo)
1498 if (SuccToSinkTo && SuccToSinkTo->
isEHPad())
1508 if (SuccToSinkTo && !
TII->isSafeToSink(
MI, SuccToSinkTo, CI))
1511 return SuccToSinkTo;
1526 auto *
MBB =
MI.getParent();
1527 if (
MBB->pred_size() != 1)
1530 auto *PredMBB = *
MBB->pred_begin();
1531 auto *PredBB = PredMBB->getBasicBlock();
1537 !PredBB->getTerminator()->getMetadata(LLVMContext::MD_make_implicit))
1542 bool OffsetIsScalable;
1543 if (!
TII->getMemOperandWithOffset(
MI, BaseOp,
Offset, OffsetIsScalable,
TRI))
1546 if (!BaseOp->
isReg())
1549 if (!(
MI.mayLoad() && !
MI.isPredicable()))
1552 MachineBranchPredicate MBP;
1553 if (
TII->analyzeBranchPredicate(*PredMBB, MBP,
false))
1556 return MBP.LHS.isReg() && MBP.RHS.isImm() && MBP.RHS.getImm() == 0 &&
1557 (MBP.Predicate == MachineBranchPredicate::PRED_NE ||
1558 MBP.Predicate == MachineBranchPredicate::PRED_EQ) &&
1559 MBP.LHS.getReg() == BaseOp->
getReg();
1576 auto CopyOperands =
TII.isCopyInstr(SinkInst);
1579 SrcMO = CopyOperands->Source;
1580 DstMO = CopyOperands->Destination;
1591 bool arePhysRegs = !
Reg.isVirtual();
1592 if (arePhysRegs != PostRA)
1599 if (DbgMO.getSubReg() != SrcMO->
getSubReg() ||
1600 DbgMO.getSubReg() != DstMO->getSubReg())
1606 if (PostRA &&
Reg != DstMO->getReg())
1610 DbgMO.setReg(SrcMO->
getReg());
1616using MIRegs = std::pair<MachineInstr *, SmallVector<Register, 2>>;
1624 if (SuccToSinkTo.
empty())
1632 SuccToSinkTo.
splice(InsertPos, ParentBlock,
MI,
1639 for (
const auto &DbgValueToSink : DbgValuesToSink) {
1642 SuccToSinkTo.
insert(InsertPos, NewDbgMI);
1644 bool PropagatedAllSunkOps =
true;
1648 PropagatedAllSunkOps =
false;
1653 if (!PropagatedAllSunkOps)
1660bool MachineSinking::hasStoreBetween(MachineBasicBlock *From,
1661 MachineBasicBlock *To, MachineInstr &
MI) {
1667 auto BlockPair = std::make_pair(From, To);
1671 if (
auto It = HasStoreCache.find(BlockPair); It != HasStoreCache.end())
1674 if (
auto It = StoreInstrCache.find(BlockPair); It != StoreInstrCache.end())
1676 return I->mayAlias(AA, MI, false);
1679 bool SawStore =
false;
1680 bool HasAliasedStore =
false;
1681 DenseSet<MachineBasicBlock *> HandledBlocks;
1682 DenseSet<MachineBasicBlock *> HandledDomBlocks;
1689 if (BB == To || BB == From)
1693 if (HandledBlocks.
count(BB))
1696 HandledBlocks.
insert(BB);
1699 if (!HandledDomBlocks.
count(BB))
1700 HandledDomBlocks.
insert(BB);
1706 for (
auto *DomBB : HandledDomBlocks) {
1707 if (DomBB != BB && DT->
dominates(DomBB, BB))
1708 HasStoreCache[std::make_pair(DomBB, To)] =
true;
1709 else if (DomBB != BB && DT->
dominates(BB, DomBB))
1710 HasStoreCache[std::make_pair(From, DomBB)] =
true;
1712 HasStoreCache[BlockPair] =
true;
1716 for (MachineInstr &
I : *BB) {
1719 if (
I.isCall() ||
I.hasOrderedMemoryRef()) {
1720 for (
auto *DomBB : HandledDomBlocks) {
1721 if (DomBB != BB && DT->
dominates(DomBB, BB))
1722 HasStoreCache[std::make_pair(DomBB, To)] =
true;
1723 else if (DomBB != BB && DT->
dominates(BB, DomBB))
1724 HasStoreCache[std::make_pair(From, DomBB)] =
true;
1726 HasStoreCache[BlockPair] =
true;
1736 if (
I.mayAlias(AA,
MI,
false))
1737 HasAliasedStore =
true;
1738 StoreInstrCache[BlockPair].push_back(&
I);
1745 HasStoreCache[BlockPair] =
false;
1746 return HasAliasedStore;
1754bool MachineSinking::aggressivelySinkIntoCycle(
1755 CycleRef Cycle, MachineInstr &
I,
1756 DenseMap<SinkItem, MachineInstr *> &SunkInstrs) {
1758 if (
I.getNumDefs() > 1)
1761 LLVM_DEBUG(
dbgs() <<
"AggressiveCycleSink: Finding sink block for: " <<
I);
1765 MachineOperand &DefMO =
I.getOperand(0);
1770 for (std::pair<RegSubRegPair, MachineInstr *> Entry :
Uses) {
1771 MachineInstr *
MI =
Entry.second;
1775 dbgs() <<
"AggressiveCycleSink: Not attempting to sink for PHI.\n");
1779 if (
MI->isPosition() ||
TII->isBasicBlockPrologue(*
MI)) {
1780 LLVM_DEBUG(
dbgs() <<
"AggressiveCycleSink: Use is BasicBlock prologue, "
1786 dbgs() <<
"AggressiveCycleSink: Use not in cycle, can't sink.\n");
1790 MachineBasicBlock *SinkBlock =
MI->getParent();
1791 MachineInstr *NewMI =
nullptr;
1792 SinkItem MapEntry(&
I, SinkBlock);
1794 auto SI = SunkInstrs.
find(MapEntry);
1798 if (SI != SunkInstrs.
end()) {
1799 LLVM_DEBUG(
dbgs() <<
"AggressiveCycleSink: Already sunk to block: "
1806 LLVM_DEBUG(
dbgs() <<
"AggressiveCycleSink: Sinking instruction to block: "
1809 NewMI =
I.
getMF()->CloneMachineInstr(&
I);
1818 SunkInstrs.
insert({MapEntry, NewMI});
1822 for (MachineOperand &MO : NewMI->
all_uses()) {
1824 RegsToClearKillFlags.insert(MO.
getReg());
1839 I.eraseFromParent();
1845bool MachineSinking::SinkInstruction(MachineInstr &
MI,
bool &SawStore,
1846 AllSuccsCache &AllSuccessors) {
1852 if (!
MI.isSafeToMove(SawStore))
1857 if (
MI.isConvergent())
1873 bool BreakPHIEdge =
false;
1874 MachineBasicBlock *ParentBlock =
MI.getParent();
1875 MachineBasicBlock *SuccToSinkTo =
1876 FindSuccToSinkTo(
MI, ParentBlock, BreakPHIEdge, AllSuccessors);
1885 for (
const MachineOperand &MO :
MI.all_defs()) {
1893 LLVM_DEBUG(
dbgs() <<
"Sink instr " <<
MI <<
"\tinto block " << *SuccToSinkTo);
1900 bool TryBreak =
false;
1902 MI.mayLoad() ? hasStoreBetween(ParentBlock, SuccToSinkTo,
MI) :
true;
1903 if (!
MI.isSafeToMove(
Store)) {
1904 LLVM_DEBUG(
dbgs() <<
" *** NOTE: Won't sink load along critical edge.\n");
1910 if (!TryBreak && !DT->
dominates(ParentBlock, SuccToSinkTo)) {
1916 if (!TryBreak && CI->
getCycle(SuccToSinkTo) &&
1930 bool Status = PostponeSplitCriticalEdge(
MI, ParentBlock, SuccToSinkTo,
1934 "break critical edge\n");
1945 PostponeSplitCriticalEdge(
MI, ParentBlock, SuccToSinkTo, BreakPHIEdge);
1948 "break critical edge\n");
1957 LLVM_DEBUG(
dbgs() <<
" *** Not sinking: prologue interference\n");
1963 for (
auto &MO :
MI.all_defs()) {
1966 auto It = SeenDbgUsers.find(MO.
getReg());
1967 if (It == SeenDbgUsers.end())
1971 auto &
Users = It->second;
1972 for (
auto &User :
Users) {
1973 MachineInstr *DbgMI =
User.getPointer();
1974 if (
User.getInt()) {
1989 if (
MI.getMF()->getFunction().getSubprogram() &&
MI.isCopy())
1990 SalvageUnsunkDebugUsersOfCopy(
MI, SuccToSinkTo);
1999 for (MachineOperand &MO :
MI.all_uses())
2000 RegsToClearKillFlags.insert(MO.
getReg());
2005void MachineSinking::SalvageUnsunkDebugUsersOfCopy(
2006 MachineInstr &
MI, MachineBasicBlock *TargetBlock) {
2013 SmallVector<MachineInstr *, 4> DbgDefUsers;
2016 for (
auto &MO :
MI.all_defs()) {
2025 if (
User.getParent() ==
MI.getParent())
2029 "DBG_VALUE user of vreg, but has no operand for it?");
2036 for (
auto *User : DbgDefUsers) {
2037 for (
auto &
Reg : DbgUseRegs) {
2038 for (
auto &DbgOp :
User->getDebugOperandsForReg(
Reg)) {
2039 DbgOp.setReg(
MI.getOperand(1).getReg());
2040 DbgOp.setSubReg(
MI.getOperand(1).getSubReg());
2082class PostRAMachineSinkingImpl {
2084 LiveRegUnits ModifiedRegUnits, UsedRegUnits;
2090 DenseMap<MCRegUnit, SmallVector<MIRegs, 2>> SeenDbgInstrs;
2095 const TargetRegisterInfo *
TRI,
const TargetInstrInfo *
TII);
2101class PostRAMachineSinkingLegacy :
public MachineFunctionPass {
2106 PostRAMachineSinkingLegacy() : MachineFunctionPass(
ID) {}
2107 StringRef getPassName()
const override {
return "PostRA Machine Sink"; }
2109 void getAnalysisUsage(AnalysisUsage &AU)
const override {
2114 MachineFunctionProperties getRequiredProperties()
const override {
2115 return MachineFunctionProperties().setNoVRegs();
2121char PostRAMachineSinkingLegacy::ID = 0;
2125 "PostRA Machine Sink",
false,
false)
2134static MachineBasicBlock *
2140 for (
auto *
SI : SinkableBBs) {
2141 if (aliasWithRegsInLiveIn(*
SI,
Reg,
TRI)) {
2161static MachineBasicBlock *
2167 for (
auto DefReg : DefedRegsInCopy) {
2170 if (!BB || (SingleBB && SingleBB != BB))
2181 for (
auto U : UsedOpsInCopy) {
2187 if (UI.killsRegister(SrcReg,
TRI)) {
2188 UI.clearRegisterKills(SrcReg,
TRI);
2200 for (
Register DefReg : DefedRegsInCopy)
2203 for (
auto U : UsedOpsInCopy)
2213 bool HasRegDependency =
false;
2214 for (
unsigned i = 0, e =
MI->getNumOperands(); i != e; ++i) {
2223 HasRegDependency =
true;
2232 }
else if (MO.
isUse()) {
2234 HasRegDependency =
true;
2240 return HasRegDependency;
2243bool PostRAMachineSinkingImpl::tryToSinkCopy(MachineBasicBlock &CurBB,
2245 const TargetRegisterInfo *
TRI,
2246 const TargetInstrInfo *
TII) {
2247 SmallPtrSet<MachineBasicBlock *, 2> SinkableBBs;
2251 for (MachineBasicBlock *SI : CurBB.
successors())
2252 if (!
SI->livein_empty() &&
SI->pred_size() == 1)
2255 if (SinkableBBs.
empty())
2262 ModifiedRegUnits.
clear();
2263 UsedRegUnits.
clear();
2264 SeenDbgInstrs.clear();
2268 SmallVector<unsigned, 2> UsedOpsInCopy;
2274 if (
MI.isDebugValue() && !
MI.isDebugRef()) {
2275 SmallDenseMap<MCRegUnit, SmallVector<Register, 2>, 4> MIUnits;
2276 bool IsValid =
true;
2277 for (MachineOperand &MO :
MI.debug_operands()) {
2282 ModifiedRegUnits, UsedRegUnits)) {
2288 for (MCRegUnit Unit :
TRI->regunits(MO.
getReg()))
2293 for (
auto &RegOps : MIUnits)
2294 SeenDbgInstrs[RegOps.first].emplace_back(&
MI,
2295 std::move(RegOps.second));
2301 if (!
TII->shouldPostRASink(
MI))
2304 if (
MI.isDebugOrPseudoInstr())
2311 if (!
MI.isCopy() || !
MI.getOperand(0).isRenamable()) {
2319 ModifiedRegUnits, UsedRegUnits)) {
2325 "Unexpect SrcReg or DefReg");
2326 MachineBasicBlock *SuccBB =
2336 "Unexpected predecessor");
2341 MapVector<MachineInstr *, MIRegs::second_type> DbgValsToSinkMap;
2342 for (
auto &MO :
MI.all_defs()) {
2343 for (MCRegUnit Unit :
TRI->regunits(MO.
getReg())) {
2344 for (
const auto &
MIRegs : SeenDbgInstrs.lookup(Unit)) {
2345 auto &Regs = DbgValsToSinkMap[
MIRegs.first];
2350 auto DbgValsToSink = DbgValsToSinkMap.
takeVector();
2359 LLVM_DEBUG(
dbgs() <<
" *** Not sinking: prologue interference\n");
2370 ++NumPostRACopySink;
2388bool PostRAMachineSinkingLegacy::runOnMachineFunction(
MachineFunction &MF) {
2392 return PostRAMachineSinkingImpl().run(MF);
2400 if (!PostRAMachineSinkingImpl().
run(MF))
MachineInstrBuilder MachineInstrBuilder & DefMI
assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")
This file defines the DenseSet and SmallDenseSet classes.
This file builds on the ADT/GraphTraits.h file to build generic depth first graph iterator.
ManagedStatic< HTTPClientCleanup > Cleanup
static Register UseReg(const MachineOperand &MO)
const HexagonInstrInfo * TII
iv Induction Variable Users
static bool mayLoadFromGOTOrConstantPool(MachineInstr &MI)
Return true if this machine instruction loads from global offset table or constant pool.
static cl::opt< unsigned > SinkLoadInstsPerBlockThreshold("machine-sink-load-instrs-threshold", cl::desc("Do not try to find alias store for a load if there is a in-path " "block whose instruction number is higher than this threshold."), cl::init(2000), cl::Hidden)
static cl::opt< unsigned > SinkIntoCycleLimit("machine-sink-cycle-limit", cl::desc("The maximum number of instructions considered for cycle sinking."), cl::init(50), cl::Hidden)
TargetInstrInfo::RegSubRegPair RegSubRegPair
static void clearKillFlags(MachineInstr *MI, MachineBasicBlock &CurBB, const SmallVectorImpl< unsigned > &UsedOpsInCopy, const LiveRegUnits &UsedRegUnits, const TargetRegisterInfo *TRI)
static void performSink(MachineInstr &MI, MachineBasicBlock &SuccToSinkTo, MachineBasicBlock::iterator InsertPos, ArrayRef< MIRegs > DbgValuesToSink)
Sink an instruction and its associated debug instructions.
static cl::opt< bool > SplitEdges("machine-sink-split", cl::desc("Split critical edges during machine sinking"), cl::init(true), cl::Hidden)
static bool SinkingPreventsImplicitNullCheck(MachineInstr &MI, const TargetInstrInfo *TII, const TargetRegisterInfo *TRI)
Return true if MI is likely to be usable as a memory operation by the implicit null check optimizatio...
static cl::opt< bool > SinkInstsIntoCycle("sink-insts-to-avoid-spills", cl::desc("Sink instructions into cycles to avoid " "register spills"), cl::init(false), cl::Hidden)
static cl::opt< unsigned > SinkLoadBlocksThreshold("machine-sink-load-blocks-threshold", cl::desc("Do not try to find alias store for a load if the block number in " "the straight line is higher than this threshold."), cl::init(20), cl::Hidden)
static void updateLiveIn(MachineInstr *MI, MachineBasicBlock *SuccBB, const SmallVectorImpl< unsigned > &UsedOpsInCopy, const SmallVectorImpl< Register > &DefedRegsInCopy)
static bool hasRegisterDependency(MachineInstr *MI, SmallVectorImpl< unsigned > &UsedOpsInCopy, SmallVectorImpl< Register > &DefedRegsInCopy, LiveRegUnits &ModifiedRegUnits, LiveRegUnits &UsedRegUnits)
Register const TargetRegisterInfo * TRI
std::pair< MachineInstr *, SmallVector< Register, 2 > > MIRegs
Machine code static false bool blockPrologueInterferes(const MachineBasicBlock *BB, MachineBasicBlock::const_iterator End, const MachineInstr &MI, const TargetRegisterInfo *TRI, const TargetInstrInfo *TII, const MachineRegisterInfo *MRI)
Return true if a target defined block prologue instruction interferes with a sink candidate.
static cl::opt< unsigned > SplitEdgeProbabilityThreshold("machine-sink-split-probability-threshold", cl::desc("Percentage threshold for splitting single-instruction critical edge. " "If the branch threshold is higher than this threshold, we allow " "speculative execution of up to 1 instruction to avoid branching to " "splitted critical edge"), cl::init(40), cl::Hidden)
static bool attemptDebugCopyProp(MachineInstr &SinkInst, MachineInstr &DbgMI, Register Reg)
If the sunk instruction is a copy, try to forward the copy instead of leaving an 'undef' DBG_VALUE in...
static cl::opt< bool > UseBlockFreqInfo("machine-sink-bfi", cl::desc("Use block frequency info to find successors to sink"), cl::init(true), cl::Hidden)
static MachineBasicBlock * getSingleLiveInSuccBB(MachineBasicBlock &CurBB, const SmallPtrSetImpl< MachineBasicBlock * > &SinkableBBs, Register Reg, const TargetRegisterInfo *TRI)
This file implements a map that provides insertion order iteration.
Promote Memory to Register
#define INITIALIZE_PASS_DEPENDENCY(depName)
#define INITIALIZE_PASS_END(passName, arg, name, cfg, analysis)
#define INITIALIZE_PASS_BEGIN(passName, arg, name, cfg, analysis)
#define INITIALIZE_PASS(passName, arg, name, cfg, analysis)
This file defines the PointerIntPair class.
Remove Loads Into Fake Uses
This file implements a set that has insertion order iteration characteristics.
static bool ProcessBlock(BasicBlock &BB, DominatorTree &DT, LoopInfo &LI, AAResults &AA)
static bool SinkInstruction(Instruction *Inst, SmallPtrSetImpl< Instruction * > &Stores, DominatorTree &DT, LoopInfo &LI, AAResults &AA)
SinkInstruction - Determine whether it is safe to sink the specified machine instruction out of its c...
This file defines the SmallSet class.
This file defines the SmallVector class.
This file defines the 'Statistic' class, which is designed to be an easy way to expose various metric...
#define STATISTIC(VARNAME, DESC)
Target-Independent Code Generator Pass Configuration Options pass.
A manager for alias analyses.
A wrapper pass to provide the legacy pass manager access to a suitably prepared AAResults object.
PassT::Result * getCachedResult(IRUnitT &IR) const
Get the cached result of an analysis pass for a given IR unit.
PassT::Result & getResult(IRUnitT &IR, ExtraArgTs... ExtraArgs)
Get the result of an analysis pass for a given IR unit.
Represent the analysis usage information of a pass.
AnalysisUsage & addRequired()
AnalysisUsage & addPreserved()
Add the specified Pass class to the set of analyses preserved by this pass.
LLVM_ABI void setPreservesCFG()
This function should be called by the pass, iff they do not:
Represent a constant reference to an array (0 or more elements consecutively in memory),...
uint64_t getFrequency() const
Returns the frequency as a fixpoint number scaled by the entry frequency.
Represents analyses that only rely on functions' control flow.
Opaque handle to a cycle within a GenericCycleInfo that wraps the cycle's preorder index.
static LLVM_ABI DebugLoc getMergedLocation(DebugLoc LocA, DebugLoc LocB)
When two instructions are combined into a single instruction we also need to combine the original loc...
static DebugLoc getDropped()
iterator find(const_arg_type_t< KeyT > Val)
std::pair< iterator, bool > insert(const std::pair< KeyT, ValueT > &KV)
Implements a dense probed hash-table based set.
bool dominates(const DomTreeNodeBase< NodeT > *A, const DomTreeNodeBase< NodeT > *B) const
dominates - Returns true iff A dominates B.
bool isReachableFromEntry(const NodeT *A) const
isReachableFromEntry - Return true if A is dominated by the entry block of the function containing it...
DomTreeNodeBase< NodeT > * getNode(const NodeT *BB) const
getNode - return the (Post)DominatorTree node for the specified basic block.
iterator_range< const_toplevel_iterator > toplevel_cycles() const
bool isReducible(CycleRef C) const
BlockT * getCyclePreheader(CycleRef C) const
Return the preheader block for C.
void splitCriticalEdge(BlockT *Pred, BlockT *Succ, BlockT *New)
bool contains(CycleRef Outer, CycleRef Inner) const
Returns true iff Outer contains Inner. O(1). Non-strict.
unsigned getCycleDepth(const BlockT *Block) const
Return the depth of the innermost cycle containing Block, or 0 if it is not contained in any cycle.
BlockT * getHeader(CycleRef C) const
CycleRef getCycle(const BlockT *Block) const
Find the innermost cycle containing Block.
Module * getParent()
Get the module that this global value is contained inside of...
bool isAsCheapAsAMove(const MachineInstr &MI) const override
bool shouldSink(const MachineInstr &MI) const override
A set of register units used to track register liveness.
static void accumulateUsedDefed(const MachineInstr &MI, LiveRegUnits &ModifiedRegUnits, LiveRegUnits &UsedRegUnits, const TargetRegisterInfo *TRI)
For a machine instruction MI, adds all register units used in UsedRegUnits and defined or clobbered i...
bool available(MCRegister Reg) const
Returns true if no part of physical register Reg is live.
void init(const TargetRegisterInfo &TRI)
Initialize and clear the set.
LLVM_ABI void addLiveIns(const MachineBasicBlock &MBB)
Adds registers living into block MBB.
void clear()
Clears the set.
bool hasSuperClassEq(const MCRegisterClass *RC) const
Returns true if RC is a super-class of or equal to this class.
bool contains(MCRegister Reg) const
contains - Return true if the specified register is included in this register class.
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.
unsigned pred_size() const
bool isEHPad() const
Returns true if the block is a landing pad.
instr_iterator instr_begin()
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.
LLVM_ABI iterator SkipPHIsAndLabels(iterator I)
Return the first instruction in MBB after I that is not a PHI or a label.
unsigned succ_size() const
LLVM_ABI void sortUniqueLiveIns()
Sorts and uniques the LiveIns vector.
LLVM_ABI DebugLoc findDebugLoc(instr_iterator MBBI)
Find the next valid DebugLoc starting at MBBI, skipping any debug instructions.
pred_iterator pred_begin()
LLVM_ABI void removeLiveInOverlappedWith(MCRegister Reg)
Remove the specified register from any overlapped live in.
instr_iterator instr_end()
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.
iterator_range< succ_iterator > successors()
LLVM_ABI bool isSuccessor(const MachineBasicBlock *MBB) const
Return true if the specified MBB is a successor of this block.
iterator_range< pred_iterator > predecessors()
void splice(iterator Where, MachineBasicBlock *Other, iterator From)
Take an instruction from MBB 'Other' at the position From, and insert it into this MBB right before '...
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.
MachineBlockFrequencyInfo pass uses BlockFrequencyInfoImpl implementation to estimate machine basic b...
LLVM_ABI BlockFrequency getBlockFreq(const MachineBasicBlock *MBB) const
getblockFreq - Return block frequency.
LLVM_ABI void onEdgeSplit(const MachineBasicBlock &NewPredecessor, const MachineBasicBlock &NewSuccessor, const MachineBranchProbabilityInfo &MBPI)
incrementally calculate block frequencies when we split edges, to avoid full CFG traversal.
LLVM_ABI BranchProbability getEdgeProbability(const MachineBasicBlock *Src, const MachineBasicBlock *Dst) const
Legacy analysis pass which computes a MachineCycleInfo.
Analysis pass which computes a MachineDominatorTree.
Analysis pass which computes a MachineDominatorTree.
DominatorTree Class - Concrete subclass of DominatorTreeBase that is used to compute a normal dominat...
bool dominates(const MachineInstr *A, const MachineInstr *B) const
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.
MachineRegisterInfo & getRegInfo()
getRegInfo - Return information about the registers currently in use.
Function & getFunction()
Return the LLVM function that this machine code represents.
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.
LLVM_ABI iterator_range< filter_iterator< const MachineOperand *, std::function< bool(const MachineOperand &Op)> > > getDebugOperandsForReg(Register Reg) const
Returns a range of all of the operands that correspond to a debug use of Reg.
bool mayLoadOrStore(QueryType Type=AnyInBundle) const
Return true if this instruction could possibly read or modify memory.
const MachineBasicBlock * getParent() const
bool isCopyLike() const
Return true if the instruction behaves like a copy.
bool isDebugInstr() const
LLVM_ABI void substituteRegister(Register FromReg, Register ToReg, unsigned SubIdx, const TargetRegisterInfo &RegInfo)
Replace all occurrences of FromReg with ToReg:SubIdx, properly composing subreg indices where necessa...
LLVM_ABI const MachineFunction * getMF() const
Return the function that contains the basic block that this instruction belongs to.
filtered_mop_range all_uses()
Returns an iterator range over all operands that are (explicit or implicit) register uses.
const MachineOperand & getOperand(unsigned i) const
void setDebugLoc(DebugLoc DL)
Replace current source information with new such.
Analysis pass that exposes the MachineLoopInfo for a machine function.
A description of a memory reference used in the backend.
MachineOperand class - Representation of each machine instruction operand.
void setSubReg(unsigned subReg)
unsigned getSubReg() const
bool isReg() const
isReg - Tests if this is a MO_Register operand.
MachineBasicBlock * getMBB() const
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.
Register getReg() const
getReg - Returns the register number.
MachinePostDominatorTree - an analysis pass wrapper for DominatorTree used to compute the post-domina...
MachineRegisterInfo - Keep track of information for virtual and physical registers,...
LLVM_ABI bool hasOneNonDBGUse(Register RegNo) const
hasOneNonDBGUse - Return true if there is exactly one non-Debug use of the specified register.
const TargetRegisterClass * getRegClass(Register Reg) const
Return the register class of the specified virtual register.
LLVM_ABI void clearKillFlags(Register Reg) const
clearKillFlags - Iterate over all the uses of the given register and clear the kill flag from the Mac...
LLVM_ABI LLVM_READONLY MachineInstr * getVRegDef(Register Reg) const
getVRegDef - Return the machine instr that defines the specified virtual register or null if none is ...
iterator_range< use_nodbg_iterator > use_nodbg_operands(Register Reg) const
bool use_nodbg_empty(Register RegNo) const
use_nodbg_empty - Return true if there are no non-Debug instructions using the specified register.
MachineBasicBlock * getDefBlock(Register Reg) const
Return the machine basic block in which the specified virtual register is defined,...
LLVM_ABI Register createVirtualRegister(const TargetRegisterClass *RegClass, StringRef Name="")
createVirtualRegister - Create and return a new virtual register in the function with the specified r...
iterator_range< use_instr_nodbg_iterator > use_nodbg_instructions(Register Reg) const
const MachineFunction & getMF() const
bool hasOneDef(Register RegNo) const
Return true if there is exactly one operand defining the specified register.
iterator_range< use_instr_iterator > use_instructions(Register Reg) const
LLVM_ABI bool isConstantPhysReg(MCRegister PhysReg) const
Returns true if PhysReg is unallocatable and constant throughout the function.
iterator_range< use_iterator > use_operands(Register Reg) const
unsigned getNumVirtRegs() const
getNumVirtRegs - Return the number of virtual registers created.
LLVM_ABI void replaceRegWith(Register FromReg, Register ToReg)
replaceRegWith - Replace all instances of FromReg with ToReg in the machine function.
LLVM_ABI PreservedAnalyses run(MachineFunction &MF, MachineFunctionAnalysisManager &)
LLVM_ABI void printPipeline(raw_ostream &OS, function_ref< StringRef(StringRef)> MapClassName2PassName)
VectorType takeVector()
Clear the MapVector and return the underlying vector.
PointerIntPair - This class implements a pair of a pointer and small integer.
LLVM_ABI PreservedAnalyses run(MachineFunction &MF, MachineFunctionAnalysisManager &MFAM)
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.
PreservedAnalyses & preserveSet()
Mark an analysis set as preserved.
An analysis pass based on legacy pass manager to deliver ProfileSummaryInfo.
Analysis providing profile information.
Special value supplied for machine level alias analysis.
unsigned getRegPressureSetLimit(unsigned Idx) const
Get the register unit limit for the given pressure set index.
LLVM_ABI void collect(const MachineInstr &MI, const TargetRegisterInfo &TRI, const MachineRegisterInfo &MRI, bool TrackLaneMasks, bool IgnoreDead)
Analyze the given instruction MI and fill in the Uses, Defs and DeadDefs list based on the MachineOpe...
Wrapper class representing virtual and physical registers.
constexpr bool isVirtual() const
Return true if the specified register number is in the virtual register namespace.
constexpr bool isPhysical() const
Return true if the specified register number is in the physical register namespace.
A vector that has set insertion semantics.
A templated base class for SmallPtrSet which provides the typesafe interface that is common across al...
size_type count(ConstPtrType Ptr) const
count - Return 1 if the specified pointer is in the set, 0 otherwise.
std::pair< iterator, bool > insert(PtrType Ptr)
Inserts Ptr if and only if there is no element in the container equal to Ptr.
SmallSet - This maintains a set of unique values, optimizing for the case when the set is small (less...
This class consists of common code factored out of the SmallVector class to reduce code duplication b...
reference emplace_back(ArgTypes &&... Args)
void push_back(const T &Elt)
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
Represent a constant reference to a string, i.e.
TargetInstrInfo - Interface to description of machine instruction set.
Target-Independent Code Generator Pass Configuration Options.
bool getEnableSinkAndFold() const
TargetRegisterInfo base class - We assume that the target defines a static array of TargetRegisterDes...
Provide an instruction scheduling machine model to CodeGen passes.
LLVM_ABI void init(const TargetSubtargetInfo *TSInfo, bool EnableSModel=true, bool EnableSItins=true)
Initialize the machine model for instruction scheduling.
TargetSubtargetInfo - Generic base class for all target subtargets.
virtual const TargetInstrInfo * getInstrInfo() const
virtual const TargetRegisterInfo * getRegisterInfo() const =0
Return the target's register information.
std::pair< iterator, bool > insert(const ValueT &V)
size_type count(const_arg_type_t< ValueT > V) const
Return 1 if the specified key is in the set, 0 otherwise.
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.
Abstract Attribute helper functions.
initializer< Ty > init(const Ty &Val)
PointerTypeMap run(const Module &M)
Compute the PointerTypeMap for the module M.
@ User
could "use" a pointer
This is an optimization pass for GlobalISel generic memory operations.
void stable_sort(R &&Range)
bool all_of(R &&range, UnaryPredicate P)
Provide wrappers to std::all_of which take ranges instead of having to pass begin/end explicitly.
OuterAnalysisManagerProxy< ModuleAnalysisManager, MachineFunction > ModuleAnalysisManagerMachineFunctionProxy
Provide the ModuleAnalysisManager to Function proxy.
@ Store
The extracted value is stored (ExtractElement only).
iterator_range< T > make_range(T x, T y)
Convenience function for iterating over sub-ranges.
void append_range(Container &C, Range &&R)
Wrapper function to append range R to container C.
LLVM_ABI bool shouldOptimizeForSize(const MachineFunction *MF, ProfileSummaryInfo *PSI, const MachineBlockFrequencyInfo *BFI, PGSOQueryType QueryType=PGSOQueryType::Other)
Returns true if machine function MF is suggested to be size-optimized based on the profile.
iterator_range< early_inc_iterator_impl< detail::IterOfRange< RangeT > > > make_early_inc_range(RangeT &&Range)
Make a range that does early increment to allow mutation of the underlying range without disrupting i...
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)
LLVM_ABI bool isCycleInvariant(const MachineCycleInfo &CI, CycleRef Cycle, MachineInstr &I)
LLVM_ABI raw_ostream & dbgs()
dbgs() - This returns a reference to a raw_ostream for debugging messages.
LLVM_ABI char & PostRAMachineSinkingID
This pass perform post-ra machine sink for COPY instructions.
class LLVM_GSL_OWNER SmallVector
Forward declaration of SmallVector so that calculateSmallVectorDefaultInlinedElements can reference s...
DomTreeNodeBase< MachineBasicBlock > MachineDomTreeNode
LLVM_ATTRIBUTE_VISIBILITY_DEFAULT AnalysisKey InnerAnalysisManagerProxy< AnalysisManagerT, IRUnitT, ExtraArgTs... >::Key
auto count_if(R &&Range, UnaryPredicate P)
Wrapper function around std::count_if to count the number of times an element satisfying a given pred...
LLVM_ABI char & MachineSinkingLegacyID
MachineSinking - This pass performs sinking on machine instructions.
iterator_range< df_iterator< T > > depth_first(const T &G)
AAResults AliasAnalysis
Temporary typedef for legacy code that uses a generic AliasAnalysis pointer or reference.
LLVM_ABI Printable printMBBReference(const MachineBasicBlock &MBB)
Prints a machine basic block reference.
MCRegisterClass TargetRegisterClass
Represents a predicate at the MachineFunction level.
A pair composed of a register and a sub-register index.