78#define DEBUG_TYPE "machine-cp"
80STATISTIC(NumDeletes,
"Number of dead copies deleted");
81STATISTIC(NumCopyForwards,
"Number of copy uses forwarded");
82STATISTIC(NumCopyBackwardPropagated,
"Number of copy defs backward propagated");
83STATISTIC(SpillageChainsLength,
"Length of spillage chains");
84STATISTIC(NumSpillageChains,
"Number of spillage chains");
86 "Controls which register COPYs are forwarded");
95static std::optional<DestSourcePair> isCopyInstr(
const MachineInstr &
MI,
99 return TII.isCopyInstr(
MI);
102 return std::optional<DestSourcePair>(
125 auto CI =
Copies.find(Unit);
127 CI->second.Avail =
false;
141 std::optional<DestSourcePair> CopyOperands =
142 isCopyInstr(*
MI,
TII, UseCopyInstr);
143 assert(CopyOperands &&
"Expect copy");
145 auto Dest =
TRI.regunits(CopyOperands->Destination->getReg().asMCReg());
146 auto Src =
TRI.regunits(CopyOperands->Source->getReg().asMCReg());
147 RegUnitsToInvalidate.
insert(Dest.begin(), Dest.end());
148 RegUnitsToInvalidate.
insert(Src.begin(), Src.end());
160 for (
MCRegUnit Unit : RegUnitsToInvalidate)
172 markRegsUnavailable(
I->second.DefRegs,
TRI);
176 std::optional<DestSourcePair> CopyOperands =
177 isCopyInstr(*
MI,
TII, UseCopyInstr);
179 MCRegister Def = CopyOperands->Destination->getReg().asMCReg();
180 MCRegister Src = CopyOperands->Source->getReg().asMCReg();
182 markRegsUnavailable(Def,
TRI);
197 auto SrcCopy =
Copies.find(SrcUnit);
198 if (SrcCopy !=
Copies.end() && SrcCopy->second.LastSeenUseInCopy) {
201 for (
auto itr = SrcCopy->second.DefRegs.begin();
202 itr != SrcCopy->second.DefRegs.end(); itr++) {
204 SrcCopy->second.DefRegs.erase(itr);
210 if (SrcCopy->second.DefRegs.empty() && !SrcCopy->second.MI) {
228 std::optional<DestSourcePair> CopyOperands =
229 isCopyInstr(*
MI,
TII, UseCopyInstr);
230 assert(CopyOperands &&
"Tracking non-copy?");
232 MCRegister Src = CopyOperands->Source->getReg().asMCReg();
233 MCRegister Def = CopyOperands->Destination->getReg().asMCReg();
237 Copies[Unit] = {
MI,
nullptr, {},
true};
242 auto I =
Copies.insert({Unit, {
nullptr,
nullptr, {},
false}});
243 auto &
Copy =
I.first->second;
245 Copy.DefRegs.push_back(Def);
246 Copy.LastSeenUseInCopy =
MI;
250 bool hasAnyCopies() {
256 bool MustBeAvailable =
false) {
257 auto CI =
Copies.find(RegUnit);
260 if (MustBeAvailable && !CI->second.Avail)
262 return CI->second.MI;
267 auto CI =
Copies.find(RegUnit);
270 if (CI->second.DefRegs.size() != 1)
272 MCRegUnit RU = *
TRI.regunits(CI->second.DefRegs[0]).begin();
273 return findCopyForUnit(RU,
TRI,
true);
286 std::optional<DestSourcePair> CopyOperands =
287 isCopyInstr(*AvailCopy,
TII, UseCopyInstr);
288 Register AvailSrc = CopyOperands->Source->getReg();
289 Register AvailDef = CopyOperands->Destination->getReg();
290 if (!
TRI.isSubRegisterEq(AvailSrc, Reg))
298 if (MO.clobbersPhysReg(AvailSrc) || MO.clobbersPhysReg(AvailDef))
311 findCopyForUnit(RU,
TRI,
true);
316 std::optional<DestSourcePair> CopyOperands =
317 isCopyInstr(*AvailCopy,
TII, UseCopyInstr);
318 Register AvailSrc = CopyOperands->Source->getReg();
319 Register AvailDef = CopyOperands->Destination->getReg();
320 if (!
TRI.isSubRegisterEq(AvailDef, Reg))
329 if (MO.clobbersPhysReg(AvailSrc) || MO.clobbersPhysReg(AvailDef))
342 auto CI =
Copies.find(RU);
343 if (CI ==
Copies.end() || !CI->second.Avail)
347 std::optional<DestSourcePair> CopyOperands =
348 isCopyInstr(*DefCopy,
TII, UseCopyInstr);
349 Register Def = CopyOperands->Destination->getReg();
350 if (!
TRI.isSubRegisterEq(Def, Reg))
358 if (MO.clobbersPhysReg(Def)) {
371 auto CI =
Copies.find(RU);
374 return CI->second.LastSeenUseInCopy;
393 MachineCopyPropagation(
bool CopyInstr =
false)
407 MachineFunctionProperties::Property::NoVRegs);
411 typedef enum { DebugUse =
false, RegularUse =
true }
DebugType;
420 bool isForwardableRegClassCopy(
const MachineInstr &Copy,
422 bool isBackwardPropagatableRegClassCopy(
const MachineInstr &Copy,
437 bool Changed =
false;
442char MachineCopyPropagation::ID = 0;
447 "Machine Copy Propagation Pass",
false,
false)
456 if (DT == RegularUse) {
457 LLVM_DEBUG(
dbgs() <<
"MCP: Copy is used - not dead: "; Copy->dump());
458 MaybeDeadCopies.remove(Copy);
460 CopyDbgUsers[Copy].insert(&Reader);
476 std::optional<DestSourcePair> CopyOperands =
477 isCopyInstr(PreviousCopy, *
TII, UseCopyInstr);
478 MCRegister PreviousSrc = CopyOperands->Source->getReg().asMCReg();
479 MCRegister PreviousDef = CopyOperands->Destination->getReg().asMCReg();
480 if (Src == PreviousSrc && Def == PreviousDef)
482 if (!
TRI->isSubRegister(PreviousSrc, Src))
484 unsigned SubIdx =
TRI->getSubRegIndex(PreviousSrc, Src);
485 return SubIdx ==
TRI->getSubRegIndex(PreviousDef, Def);
491bool MachineCopyPropagation::eraseIfRedundant(
MachineInstr &Copy,
495 if (
MRI->isReserved(Src) ||
MRI->isReserved(Def))
500 Tracker.findAvailCopy(Copy, Def, *
TRI, *
TII, UseCopyInstr);
504 auto PrevCopyOperands = isCopyInstr(*PrevCopy, *
TII, UseCopyInstr);
506 if (PrevCopyOperands->Destination->isDead())
515 std::optional<DestSourcePair> CopyOperands =
516 isCopyInstr(Copy, *
TII, UseCopyInstr);
519 Register CopyDef = CopyOperands->Destination->getReg();
520 assert(CopyDef == Src || CopyDef == Def);
523 MI.clearRegisterKills(CopyDef,
TRI);
526 if (!CopyOperands->Source->isUndef()) {
527 PrevCopy->
getOperand(PrevCopyOperands->Source->getOperandNo())
531 Copy.eraseFromParent();
537bool MachineCopyPropagation::isBackwardPropagatableRegClassCopy(
539 std::optional<DestSourcePair> CopyOperands =
540 isCopyInstr(Copy, *
TII, UseCopyInstr);
541 Register Def = CopyOperands->Destination->getReg();
545 return URC->contains(Def);
555bool MachineCopyPropagation::isForwardableRegClassCopy(
const MachineInstr &Copy,
558 std::optional<DestSourcePair> CopyOperands =
559 isCopyInstr(Copy, *
TII, UseCopyInstr);
560 Register CopySrcReg = CopyOperands->Source->getReg();
566 return URC->contains(CopySrcReg);
568 auto UseICopyOperands = isCopyInstr(UseI, *
TII, UseCopyInstr);
569 if (!UseICopyOperands)
592 Register UseDstReg = UseICopyOperands->Destination->getReg();
594 bool IsCrossClass =
false;
596 if (RC->contains(CopySrcReg) && RC->contains(UseDstReg)) {
598 if (
TRI->getCrossCopyRegClass(RC) != RC) {
610 Register CopyDstReg = CopyOperands->Destination->getReg();
612 if (RC->contains(CopySrcReg) && RC->contains(CopyDstReg) &&
613 TRI->getCrossCopyRegClass(RC) != RC)
627bool MachineCopyPropagation::hasImplicitOverlap(
const MachineInstr &
MI,
630 if (&MIUse != &
Use && MIUse.isReg() && MIUse.isImplicit() &&
631 MIUse.isUse() &&
TRI->regsOverlap(
Use.getReg(), MIUse.getReg()))
641bool MachineCopyPropagation::hasOverlappingMultipleDef(
644 if ((&MIDef != &MODef) && MIDef.isReg() &&
645 TRI->regsOverlap(Def, MIDef.getReg()))
655 if (!Tracker.hasAnyCopies())
661 for (
unsigned OpIdx = 0, OpEnd =
MI.getNumOperands(); OpIdx < OpEnd;
683 *
TRI, *
TII, UseCopyInstr);
687 std::optional<DestSourcePair> CopyOperands =
688 isCopyInstr(*Copy, *
TII, UseCopyInstr);
689 Register CopyDstReg = CopyOperands->Destination->getReg();
696 if (MOUse.
getReg() != CopyDstReg) {
697 unsigned SubRegIdx =
TRI->getSubRegIndex(CopyDstReg, MOUse.
getReg());
699 "MI source is not a sub-register of Copy destination");
700 ForwardedReg =
TRI->getSubReg(CopySrcReg, SubRegIdx);
702 LLVM_DEBUG(
dbgs() <<
"MCP: Copy source does not have sub-register "
703 <<
TRI->getSubRegIndexName(SubRegIdx) <<
'\n');
709 if (
MRI->isReserved(CopySrcReg) && !
MRI->isConstantPhysReg(CopySrcReg))
712 if (!isForwardableRegClassCopy(*Copy,
MI, OpIdx))
715 if (hasImplicitOverlap(
MI, MOUse))
721 if (isCopyInstr(
MI, *
TII, UseCopyInstr) &&
722 MI.modifiesRegister(CopySrcReg,
TRI) &&
723 !
MI.definesRegister(CopySrcReg)) {
729 LLVM_DEBUG(
dbgs() <<
"MCP: Skipping forwarding due to debug counter:\n "
736 <<
"\n in " <<
MI <<
" from " << *Copy);
738 MOUse.
setReg(ForwardedReg);
749 KMI.clearRegisterKills(CopySrcReg,
TRI);
762 std::optional<DestSourcePair> CopyOperands =
763 isCopyInstr(
MI, *
TII, UseCopyInstr);
766 Register RegSrc = CopyOperands->Source->getReg();
767 Register RegDef = CopyOperands->Destination->getReg();
769 if (!
TRI->regsOverlap(RegDef, RegSrc)) {
771 "MachineCopyPropagation should be run after register allocation!");
791 if (eraseIfRedundant(
MI, Def, Src) || eraseIfRedundant(
MI, Src, Def))
797 CopyOperands = isCopyInstr(
MI, *
TII, UseCopyInstr);
798 Src = CopyOperands->Source->getReg().asMCReg();
802 ReadRegister(Src,
MI, RegularUse);
804 if (!MO.isReg() || !MO.readsReg())
809 ReadRegister(Reg,
MI, RegularUse);
815 if (!
MRI->isReserved(Def))
816 MaybeDeadCopies.insert(&
MI);
825 Tracker.clobberRegister(Def, *
TRI, *
TII, UseCopyInstr);
827 if (!MO.isReg() || !MO.isDef())
832 Tracker.clobberRegister(Reg, *
TRI, *
TII, UseCopyInstr);
835 Tracker.trackCopy(&
MI, *
TRI, *
TII, UseCopyInstr);
843 if (MO.isReg() && MO.isEarlyClobber()) {
849 ReadRegister(Reg,
MI, RegularUse);
850 Tracker.clobberRegister(Reg, *
TRI, *
TII, UseCopyInstr);
868 "MachineCopyPropagation should be run after register allocation!");
870 if (MO.isDef() && !MO.isEarlyClobber()) {
873 }
else if (MO.readsReg())
874 ReadRegister(
Reg.asMCReg(),
MI, MO.isDebug() ? DebugUse : RegularUse);
883 MaybeDeadCopies.
begin();
884 DI != MaybeDeadCopies.end();) {
886 std::optional<DestSourcePair> CopyOperands =
887 isCopyInstr(*MaybeDead, *
TII, UseCopyInstr);
888 MCRegister Reg = CopyOperands->Destination->getReg().asMCReg();
896 LLVM_DEBUG(
dbgs() <<
"MCP: Removing copy due to regmask clobbering: ";
901 Tracker.clobberRegister(Reg, *
TRI, *
TII, UseCopyInstr);
905 DI = MaybeDeadCopies.erase(DI);
914 Tracker.clobberRegister(Reg, *
TRI, *
TII, UseCopyInstr);
922 LLVM_DEBUG(
dbgs() <<
"MCP: Removing copy due to no live-out succ: ";
925 std::optional<DestSourcePair> CopyOperands =
926 isCopyInstr(*MaybeDead, *
TII, UseCopyInstr);
929 Register SrcReg = CopyOperands->Source->getReg();
930 Register DestReg = CopyOperands->Destination->getReg();
935 CopyDbgUsers[MaybeDead].
begin(), CopyDbgUsers[MaybeDead].
end());
945 MaybeDeadCopies.clear();
946 CopyDbgUsers.clear();
959 if (
MRI.isReserved(Def) ||
MRI.isReserved(Src))
966 if (!Tracker.hasAnyCopies())
969 for (
unsigned OpIdx = 0, OpEnd =
MI.getNumOperands(); OpIdx != OpEnd;
992 std::optional<DestSourcePair> CopyOperands =
993 isCopyInstr(*Copy, *
TII, UseCopyInstr);
994 Register Def = CopyOperands->Destination->getReg();
995 Register Src = CopyOperands->Source->getReg();
997 if (MODef.
getReg() != Src)
1000 if (!isBackwardPropagatableRegClassCopy(*Copy,
MI, OpIdx))
1003 if (hasImplicitOverlap(
MI, MODef))
1006 if (hasOverlappingMultipleDef(
MI, MODef, Def))
1011 <<
MI <<
" from " << *Copy);
1017 MaybeDeadCopies.insert(Copy);
1019 ++NumCopyBackwardPropagated;
1023void MachineCopyPropagation::BackwardCopyPropagateBlock(
1030 std::optional<DestSourcePair> CopyOperands =
1031 isCopyInstr(
MI, *
TII, UseCopyInstr);
1032 if (CopyOperands &&
MI.getNumOperands() == 2) {
1033 Register DefReg = CopyOperands->Destination->getReg();
1034 Register SrcReg = CopyOperands->Source->getReg();
1036 if (!
TRI->regsOverlap(DefReg, SrcReg)) {
1044 Tracker.trackCopy(&
MI, *
TRI, *
TII, UseCopyInstr);
1052 if (MO.isReg() && MO.isEarlyClobber()) {
1056 Tracker.invalidateRegister(Reg, *
TRI, *
TII, UseCopyInstr);
1068 Tracker.invalidateRegister(MO.getReg().asMCReg(), *
TRI, *
TII,
1071 if (MO.readsReg()) {
1076 for (
MCRegUnit Unit :
TRI->regunits(MO.getReg().asMCReg())) {
1077 if (
auto *Copy = Tracker.findCopyDefViaUnit(Unit, *
TRI)) {
1078 CopyDbgUsers[
Copy].insert(&
MI);
1082 Tracker.invalidateRegister(MO.getReg().asMCReg(), *
TRI, *
TII,
1089 for (
auto *Copy : MaybeDeadCopies) {
1090 std::optional<DestSourcePair> CopyOperands =
1091 isCopyInstr(*Copy, *
TII, UseCopyInstr);
1092 Register Src = CopyOperands->Source->getReg();
1093 Register Def = CopyOperands->Destination->getReg();
1095 CopyDbgUsers[Copy].
end());
1097 MRI->updateDbgUsersToReg(Src.asMCReg(),
Def.asMCReg(), MaybeDeadDbgUsers);
1098 Copy->eraseFromParent();
1102 MaybeDeadCopies.clear();
1103 CopyDbgUsers.clear();
1111 auto &SC = SpillChain[Leader];
1112 auto &RC = ReloadChain[Leader];
1113 for (
auto I = SC.rbegin(),
E = SC.rend();
I !=
E; ++
I)
1170 auto TryFoldSpillageCopies =
1173 assert(
SC.size() == RC.size() &&
"Spill-reload should be paired");
1189 if (CopySourceInvalid.
count(Spill))
1193 if (CopySourceInvalid.
count(Reload))
1198 if (RC->contains(Def) && RC->contains(Src))
1208 MO.setReg(
New->getReg());
1212 std::optional<DestSourcePair> InnerMostSpillCopy =
1213 isCopyInstr(*SC[0], *
TII, UseCopyInstr);
1214 std::optional<DestSourcePair> OuterMostSpillCopy =
1215 isCopyInstr(*
SC.back(), *
TII, UseCopyInstr);
1216 std::optional<DestSourcePair> InnerMostReloadCopy =
1217 isCopyInstr(*RC[0], *
TII, UseCopyInstr);
1218 std::optional<DestSourcePair> OuterMostReloadCopy =
1219 isCopyInstr(*RC.back(), *
TII, UseCopyInstr);
1220 if (!CheckCopyConstraint(OuterMostSpillCopy->Source->getReg(),
1221 InnerMostSpillCopy->Source->getReg()) ||
1222 !CheckCopyConstraint(InnerMostReloadCopy->Destination->getReg(),
1223 OuterMostReloadCopy->Destination->getReg()))
1226 SpillageChainsLength +=
SC.size() + RC.size();
1227 NumSpillageChains += 1;
1228 UpdateReg(SC[0], InnerMostSpillCopy->Destination,
1229 OuterMostSpillCopy->Source);
1230 UpdateReg(RC[0], InnerMostReloadCopy->Source,
1231 OuterMostReloadCopy->Destination);
1233 for (
size_t I = 1;
I <
SC.size() - 1; ++
I) {
1234 SC[
I]->eraseFromParent();
1235 RC[
I]->eraseFromParent();
1240 auto IsFoldableCopy = [
this](
const MachineInstr &MaybeCopy) {
1241 if (MaybeCopy.getNumImplicitOperands() > 0)
1243 std::optional<DestSourcePair> CopyOperands =
1244 isCopyInstr(MaybeCopy, *
TII, UseCopyInstr);
1247 Register Src = CopyOperands->Source->getReg();
1248 Register Def = CopyOperands->Destination->getReg();
1249 return Src &&
Def && !
TRI->regsOverlap(Src, Def) &&
1250 CopyOperands->Source->isRenamable() &&
1251 CopyOperands->Destination->isRenamable();
1256 if (!IsFoldableCopy(Spill) || !IsFoldableCopy(Reload))
1258 std::optional<DestSourcePair> SpillCopy =
1259 isCopyInstr(Spill, *
TII, UseCopyInstr);
1260 std::optional<DestSourcePair> ReloadCopy =
1261 isCopyInstr(Reload, *
TII, UseCopyInstr);
1262 if (!SpillCopy || !ReloadCopy)
1264 return SpillCopy->Source->getReg() == ReloadCopy->Destination->getReg() &&
1265 SpillCopy->Destination->getReg() == ReloadCopy->Source->getReg();
1268 auto IsChainedCopy = [&,
this](
const MachineInstr &Prev,
1270 if (!IsFoldableCopy(Prev) || !IsFoldableCopy(Current))
1272 std::optional<DestSourcePair> PrevCopy =
1273 isCopyInstr(Prev, *
TII, UseCopyInstr);
1274 std::optional<DestSourcePair> CurrentCopy =
1275 isCopyInstr(Current, *
TII, UseCopyInstr);
1276 if (!PrevCopy || !CurrentCopy)
1278 return PrevCopy->Source->getReg() == CurrentCopy->Destination->getReg();
1282 std::optional<DestSourcePair> CopyOperands =
1283 isCopyInstr(
MI, *
TII, UseCopyInstr);
1287 if (!CopyOperands) {
1295 Tracker.findLastSeenUseInCopy(
Reg.asMCReg(), *
TRI);
1301 CopySourceInvalid.
insert(LastUseCopy);
1309 if (Tracker.findLastSeenDefInCopy(
MI,
Reg.asMCReg(), *
TRI, *
TII,
1312 RegsToClobber.
insert(Reg);
1314 for (
Register Reg : RegsToClobber) {
1315 Tracker.clobberRegister(Reg, *
TRI, *
TII, UseCopyInstr);
1322 Register Src = CopyOperands->Source->getReg();
1323 Register Def = CopyOperands->Destination->getReg();
1325 LLVM_DEBUG(
dbgs() <<
"MCP: Searching paired spill for reload: ");
1328 Tracker.findLastSeenDefInCopy(
MI, Src.asMCReg(), *
TRI, *
TII, UseCopyInstr);
1329 bool MaybeSpillIsChained = ChainLeader.
count(MaybeSpill);
1330 if (!MaybeSpillIsChained && MaybeSpill &&
1331 IsSpillReloadPair(*MaybeSpill,
MI)) {
1367 Tracker.findLastSeenUseInCopy(
Def.asMCReg(), *
TRI);
1368 auto Leader = ChainLeader.
find(MaybePrevReload);
1370 if (Leader == ChainLeader.
end() ||
1371 (MaybePrevReload && !IsChainedCopy(*MaybePrevReload,
MI))) {
1374 "SpillChain should not have contained newly found chain");
1376 assert(MaybePrevReload &&
1377 "Found a valid leader through nullptr should not happend");
1380 "Existing chain's length should be larger than zero");
1383 "Newly found paired spill-reload should not belong to any chain "
1385 ChainLeader.
insert({MaybeSpill,
L});
1387 SpillChain[
L].push_back(MaybeSpill);
1388 ReloadChain[
L].push_back(&
MI);
1391 }
else if (MaybeSpill && !MaybeSpillIsChained) {
1408 Tracker.clobberRegister(Src.asMCReg(), *
TRI, *
TII, UseCopyInstr);
1412 Tracker.trackCopy(&
MI, *
TRI, *
TII, UseCopyInstr);
1415 for (
auto I = SpillChain.
begin(),
E = SpillChain.
end();
I !=
E; ++
I) {
1416 auto &
SC =
I->second;
1418 "Reload chain of the same leader should exist");
1419 auto &RC = ReloadChain[
I->first];
1420 TryFoldSpillageCopies(SC, RC);
1423 MaybeDeadCopies.clear();
1424 CopyDbgUsers.clear();
1428bool MachineCopyPropagation::runOnMachineFunction(
MachineFunction &MF) {
1432 bool isSpillageCopyElimEnabled =
false;
1435 isSpillageCopyElimEnabled =
1439 isSpillageCopyElimEnabled =
true;
1442 isSpillageCopyElimEnabled =
false;
1453 if (isSpillageCopyElimEnabled)
1454 EliminateSpillageCopies(
MBB);
1455 BackwardCopyPropagateBlock(
MBB);
1456 ForwardCopyPropagateBlock(
MBB);
1464 return new MachineCopyPropagation(UseCopyInstr);
unsigned const MachineRegisterInfo * MRI
static GCRegistry::Add< CoreCLRGC > E("coreclr", "CoreCLR-compatible GC")
#define LLVM_ATTRIBUTE_UNUSED
static void clear(coro::Shape &Shape)
This file provides an implementation of debug counters.
#define DEBUG_COUNTER(VARNAME, COUNTERNAME, DESC)
This file defines the DenseMap class.
const HexagonInstrInfo * TII
static cl::opt< cl::boolOrDefault > EnableSpillageCopyElimination("enable-spill-copy-elim", cl::Hidden)
static void LLVM_ATTRIBUTE_UNUSED printSpillReloadChain(DenseMap< MachineInstr *, SmallVector< MachineInstr * > > &SpillChain, DenseMap< MachineInstr *, SmallVector< MachineInstr * > > &ReloadChain, MachineInstr *Leader)
static bool isBackwardPropagatableCopy(const DestSourcePair &CopyOperands, const MachineRegisterInfo &MRI, const TargetInstrInfo &TII)
static bool isNopCopy(const MachineInstr &PreviousCopy, MCRegister Src, MCRegister Def, const TargetRegisterInfo *TRI, const TargetInstrInfo *TII, bool UseCopyInstr)
Return true if PreviousCopy did copy register Src to register Def.
static cl::opt< bool > MCPUseCopyInstr("mcp-use-is-copy-instr", cl::init(false), cl::Hidden)
unsigned const TargetRegisterInfo * TRI
#define INITIALIZE_PASS(passName, arg, name, cfg, analysis)
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
This file implements a set that has insertion order iteration characteristics.
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)
Represent the analysis usage information of a pass.
void setPreservesCFG()
This function should be called by the pass, iff they do not:
ArrayRef - Represent a constant reference to an array (0 or more elements consecutively in memory),...
static bool shouldExecute(unsigned CounterName)
iterator find(const_arg_type_t< KeyT > Val)
size_type count(const_arg_type_t< KeyT > Val) const
Return 1 if the specified key is in the map, 0 otherwise.
std::pair< iterator, bool > insert(const std::pair< KeyT, ValueT > &KV)
Implements a dense probed hash-table based set.
Wrapper class representing physical registers. Should be passed by value.
StringRef getName() const
Return the name of the corresponding LLVM basic block, or an empty string.
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.
virtual bool runOnMachineFunction(MachineFunction &MF)=0
runOnMachineFunction - This method must be overloaded to perform the desired machine code transformat...
virtual MachineFunctionProperties getRequiredProperties() const
Properties which a MachineFunction may have at a given point in time.
MachineFunctionProperties & set(Property P)
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.
void eraseFromParent()
Unlink 'this' from the containing basic block and delete it.
const MachineOperand & getOperand(unsigned i) const
const TargetRegisterClass * getRegClassConstraint(unsigned OpIdx, const TargetInstrInfo *TII, const TargetRegisterInfo *TRI) const
Compute the static register class constraint for operand OpIdx.
MachineOperand class - Representation of each machine instruction operand.
void setIsRenamable(bool Val=true)
bool isReg() const
isReg - Tests if this is a MO_Register operand.
void setReg(Register Reg)
Change the register this operand corresponds to.
bool isRenamable() const
isRenamable - Returns true if this register may be renamed, i.e.
void setIsUndef(bool Val=true)
Register getReg() const
getReg - Returns the register number.
static bool clobbersPhysReg(const uint32_t *RegMask, MCRegister PhysReg)
clobbersPhysReg - Returns true if this RegMask clobbers PhysReg.
MachineRegisterInfo - Keep track of information for virtual and physical registers,...
static PassRegistry * getPassRegistry()
getPassRegistry - Access the global registry object, which is automatically initialized at applicatio...
Wrapper class representing virtual and physical registers.
MCRegister asMCReg() const
Utility to check-convert this value to a MCRegister.
constexpr bool isPhysical() const
Return true if the specified register number is in the physical register namespace.
iterator begin()
Get an iterator to the beginning of the SetVector.
A SetVector that performs no allocations if smaller than a certain size.
SmallSet - This maintains a set of unique values, optimizing for the case when the set is small (less...
std::pair< const_iterator, bool > insert(const T &V)
insert - Insert an element into the set if it isn't already there.
This class consists of common code factored out of the SmallVector class to reduce code duplication b...
void push_back(const T &Elt)
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
TargetInstrInfo - Interface to description of machine instruction set.
TargetRegisterInfo base class - We assume that the target defines a static array of TargetRegisterDes...
virtual const TargetRegisterInfo * getRegisterInfo() const
getRegisterInfo - If register information is available, return it.
virtual bool enableSpillageCopyElimination() const
Enable spillage copy elimination in MachineCopyPropagation pass.
virtual const TargetInstrInfo * getInstrInfo() const
A Use represents the edge between a Value definition and its users.
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.
reverse_self_iterator getReverseIterator()
self_iterator getIterator()
This provides a very simple, boring adaptor for a begin and end iterator into a range type.
unsigned ID
LLVM IR allows to use arbitrary numbers as calling convention identifiers.
@ SC
CHAIN = SC CHAIN, Imm128 - System call.
Reg
All possible values of the reg field in the ModR/M byte.
initializer< Ty > init(const Ty &Val)
NodeAddr< DefNode * > Def
const_iterator begin(StringRef path, Style style=Style::native)
Get begin iterator over path.
const_iterator end(StringRef path)
Get end iterator over path.
This is an optimization pass for GlobalISel generic memory operations.
auto drop_begin(T &&RangeOrContainer, size_t N=1)
Return a range covering RangeOrContainer with the first N elements excluded.
auto size(R &&Range, std::enable_if_t< std::is_base_of< std::random_access_iterator_tag, typename std::iterator_traits< decltype(Range.begin())>::iterator_category >::value, void > *=nullptr)
Get the size of a range.
iterator_range< T > make_range(T x, T y)
Convenience function for iterating over sub-ranges.
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...
auto reverse(ContainerTy &&C)
raw_ostream & dbgs()
dbgs() - This returns a reference to a raw_ostream for debugging messages.
auto drop_end(T &&RangeOrContainer, size_t N=1)
Return a range covering RangeOrContainer with the last N elements excluded.
bool is_contained(R &&Range, const E &Element)
Returns true if Element is found in Range.
MachineFunctionPass * createMachineCopyPropagationPass(bool UseCopyInstr)
void initializeMachineCopyPropagationPass(PassRegistry &)
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.
char & MachineCopyPropagationID
MachineCopyPropagation - This pass performs copy propagation on machine instructions.
const MachineOperand * Source
const MachineOperand * Destination