39#include "llvm/Config/llvm-config.h"
58#define DEBUG_TYPE "mips-constant-islands"
61STATISTIC(NumSplit,
"Number of uncond branches inserted");
62STATISTIC(NumCBrFixed,
"Number of cond branches fixed");
63STATISTIC(NumUBrFixed,
"Number of uncond branches fixed");
68 cl::desc(
"Align constant islands in code"));
73 "mips-constant-islands-small-offset",
75 cl::desc(
"Make small offsets be this amount for testing purposes"),
81 "mips-constant-islands-no-load-relaxation",
83 cl::desc(
"Don't relax loads to long loads - for testing purposes"),
87 switch (
MI->getOpcode()) {
96 case Mips::BeqzRxImm16:
97 case Mips::BeqzRxImmX16:
98 case Mips::BnezRxImm16:
99 case Mips::BnezRxImmX16:
109 return Mips::BimmX16;
112 return Mips::BteqzX16;
115 return Mips::BtnezX16;
118 case Mips::BeqzRxImm16:
119 case Mips::BeqzRxImmX16:
120 return Mips::BeqzRxImmX16;
121 case Mips::BnezRxImm16:
122 case Mips::BnezRxImmX16:
123 return Mips::BnezRxImmX16;
133 unsigned Bits, Scale;
143 case Mips::BeqzRxImm16:
147 case Mips::BeqzRxImmX16:
151 case Mips::BnezRxImm16:
155 case Mips::BnezRxImmX16:
178 unsigned MaxOffs = ((1 << (Bits-1))-1) * Scale;
223 unsigned postOffset()
const {
return Offset +
Size; }
226 std::vector<BasicBlockInfo> BBInfo;
231 std::vector<MachineBasicBlock*> WaterList;
237 using water_iterator = std::vector<MachineBasicBlock *>::iterator;
258 unsigned LongFormMaxDisp;
260 unsigned LongFormOpcode;
267 unsigned longformmaxdisp,
unsigned longformopcode)
268 :
MI(mi), CPEMI(cpemi), MaxDisp(maxdisp),
269 LongFormMaxDisp(longformmaxdisp), LongFormOpcode(longformopcode),
275 unsigned getMaxDisp()
const {
281 void setMaxDisp(
unsigned val) {
285 unsigned getLongFormMaxDisp()
const {
286 return LongFormMaxDisp;
289 unsigned getLongFormOpcode()
const {
290 return LongFormOpcode;
296 std::vector<CPUser> CPUsers;
307 : CPEMI(cpemi), CPI(cpi), RefCount(
rc) {}
315 std::vector<std::vector<CPEntry>> CPEntries;
323 unsigned MaxDisp : 31;
327 ImmBranch(
MachineInstr *mi,
unsigned maxdisp,
bool cond,
int ubr)
328 :
MI(mi), MaxDisp(maxdisp), isCond(cond), UncondBr(ubr) {}
333 std::vector<ImmBranch> ImmBranches;
345 unsigned PICLabelUId;
346 bool PrescannedForConstants =
false;
348 void initPICLabelUId(
unsigned UId) {
352 unsigned createPICLabelUId() {
353 return PICLabelUId++;
367 MachineFunctionProperties::Property::NoVRegs);
370 void doInitialPlacement(std::vector<MachineInstr*> &CPEMIs);
371 CPEntry *findConstPoolEntry(
unsigned CPI,
const MachineInstr *CPEMI);
373 void initializeFunctionInfo(
const std::vector<MachineInstr*> &CPEMIs);
375 unsigned getUserOffset(CPUser&)
const;
378 bool isOffsetInRange(
unsigned UserOffset,
unsigned TrialOffset,
379 unsigned Disp,
bool NegativeOK);
380 bool isOffsetInRange(
unsigned UserOffset,
unsigned TrialOffset,
387 bool decrementCPEReferenceCount(
unsigned CPI,
MachineInstr* CPEMI);
388 int findInRangeCPEntry(CPUser& U,
unsigned UserOffset);
389 int findLongFormInRangeCPEntry(CPUser& U,
unsigned UserOffset);
390 bool findAvailableWater(CPUser&U,
unsigned UserOffset,
391 water_iterator &WaterIter);
392 void createNewWater(
unsigned CPUserIndex,
unsigned UserOffset,
394 bool handleConstantPoolUser(
unsigned CPUserIndex);
396 bool removeUnusedCPEntries();
399 bool DoDump =
false);
401 CPUser &U,
unsigned &Growth);
403 bool fixupImmediateBr(ImmBranch &Br);
404 bool fixupConditionalBr(ImmBranch &Br);
405 bool fixupUnconditionalBr(ImmBranch &Br);
407 void prescanForConstants();
412char MipsConstantIslands::ID = 0;
414bool MipsConstantIslands::isOffsetInRange
415 (
unsigned UserOffset,
unsigned TrialOffset,
417 return isOffsetInRange(UserOffset, TrialOffset,
418 U.getMaxDisp(),
U.NegOk);
421#if !defined(NDEBUG) || defined(LLVM_ENABLE_DUMP)
424 for (
unsigned J = 0, E = BBInfo.size(); J !=E; ++J) {
451 if (!PrescannedForConstants) prescanForConstants();
455 MF->getRegInfo().invalidateLiveness();
459 MF->RenumberBlocks();
461 bool MadeChange =
false;
465 std::vector<MachineInstr*> CPEMIs;
467 doInitialPlacement(CPEMIs);
470 initPICLabelUId(CPEMIs.size());
475 initializeFunctionInfo(CPEMIs);
480 MadeChange |= removeUnusedCPEntries();
484 unsigned NoCPIters = 0, NoBRIters = 0;
487 LLVM_DEBUG(
dbgs() <<
"Beginning CP iteration #" << NoCPIters <<
'\n');
488 bool CPChange =
false;
489 for (
unsigned i = 0, e = CPUsers.size(); i != e; ++i)
490 CPChange |= handleConstantPoolUser(i);
491 if (CPChange && ++NoCPIters > 30)
497 NewWaterList.
clear();
499 LLVM_DEBUG(
dbgs() <<
"Beginning BR iteration #" << NoBRIters <<
'\n');
500 bool BRChange =
false;
501 for (
unsigned i = 0, e = ImmBranches.size(); i != e; ++i)
502 BRChange |= fixupImmediateBr(ImmBranches[i]);
503 if (BRChange && ++NoBRIters > 30)
506 if (!CPChange && !BRChange)
524MipsConstantIslands::doInitialPlacement(std::vector<MachineInstr*> &CPEMIs) {
530 const Align MaxAlign = MCP->getConstantPoolAlign();
549 const std::vector<MachineConstantPoolEntry> &CPs = MCP->getConstants();
552 for (
unsigned i = 0, e = CPs.size(); i != e; ++i) {
553 unsigned Size = CPs[i].getSizeInBytes(TD);
554 assert(
Size >= 4 &&
"Too small constant pool entry");
555 Align Alignment = CPs[i].getAlign();
561 unsigned LogAlign =
Log2(Alignment);
568 CPEMIs.push_back(CPEMI);
572 for (
unsigned a = LogAlign + 1; a <=
Log2(MaxAlign); ++a)
573 if (InsPoint[a] == InsAt)
576 CPEntries.emplace_back(1, CPEntry(CPEMI, i));
578 LLVM_DEBUG(
dbgs() <<
"Moved CPI#" << i <<
" to end of function, size = "
579 <<
Size <<
", align = " << Alignment.
value() <<
'\n');
599MipsConstantIslands::CPEntry
600*MipsConstantIslands::findConstPoolEntry(
unsigned CPI,
602 std::vector<CPEntry> &CPEs = CPEntries[CPI];
605 for (CPEntry &CPE : CPEs) {
606 if (CPE.CPEMI == CPEMI)
622 assert(CPI < MCP->getConstants().
size() &&
"Invalid constant pool index.");
623 return MCP->getConstants()[CPI].getAlign();
629void MipsConstantIslands::
630initializeFunctionInfo(
const std::vector<MachineInstr*> &CPEMIs) {
632 BBInfo.resize(MF->getNumBlockIDs());
639 computeBlockSize(&
MBB);
642 adjustBBOffsetsAfter(&MF->front());
649 WaterList.push_back(&
MBB);
651 if (
MI.isDebugInstr())
654 int Opc =
MI.getOpcode();
673 case Mips::BeqzRxImm16:
679 case Mips::BeqzRxImmX16:
685 case Mips::BnezRxImm16:
691 case Mips::BnezRxImmX16:
723 unsigned MaxOffs = ((1 << (
Bits-1))-1) * Scale;
724 ImmBranches.push_back(ImmBranch(&
MI, MaxOffs, isCond, UOpc));
727 if (Opc == Mips::CONSTPOOL_ENTRY)
740 unsigned LongFormBits = 0;
741 unsigned LongFormScale = 0;
742 unsigned LongFormOpcode = 0;
746 case Mips::LwRxPcTcp16:
749 LongFormOpcode = Mips::LwRxPcTcpX16;
753 case Mips::LwRxPcTcpX16:
760 unsigned CPI = MO.getIndex();
762 unsigned MaxOffs = ((1 <<
Bits)-1) * Scale;
763 unsigned LongFormMaxOffs = ((1 << LongFormBits)-1) * LongFormScale;
764 CPUsers.push_back(CPUser(&
MI, CPEMI, MaxOffs, NegOk, LongFormMaxOffs,
768 CPEntry *CPE = findConstPoolEntry(CPI, CPEMI);
769 assert(CPE &&
"Cannot find a corresponding CPEntry!");
793unsigned MipsConstantIslands::getOffsetOf(
MachineInstr *
MI)
const {
803 assert(
I !=
MBB->
end() &&
"Didn't find MI in its own basic block?");
813 return LHS->getNumber() <
RHS->getNumber();
819void MipsConstantIslands::updateForInsertedWaterBlock
831 WaterList.insert(IP, NewBB);
834unsigned MipsConstantIslands::getUserOffset(CPUser &U)
const {
835 return getOffsetOf(
U.MI);
849 MF->insert(
MBBI, NewBB);
870 MF->RenumberBlocks(NewBB);
882 if (WaterBB == OrigBB)
883 WaterList.
insert(std::next(IP), NewBB);
885 WaterList.insert(IP, OrigBB);
886 NewWaterList.
insert(OrigBB);
893 computeBlockSize(OrigBB);
897 computeBlockSize(NewBB);
900 adjustBBOffsetsAfter(OrigBB);
908bool MipsConstantIslands::isOffsetInRange(
unsigned UserOffset,
909 unsigned TrialOffset,
unsigned MaxDisp,
911 if (UserOffset <= TrialOffset) {
913 if (TrialOffset - UserOffset <= MaxDisp)
915 }
else if (NegativeOK) {
916 if (UserOffset - TrialOffset <= MaxDisp)
926bool MipsConstantIslands::isWaterInRange(
unsigned UserOffset,
929 unsigned CPEOffset = BBInfo[Water->
getNumber()].postOffset();
930 unsigned NextBlockOffset;
931 Align NextBlockAlignment;
933 if (NextBlock == MF->end()) {
934 NextBlockOffset = BBInfo[Water->
getNumber()].postOffset();
935 NextBlockAlignment =
Align(1);
937 NextBlockOffset = BBInfo[NextBlock->getNumber()].Offset;
938 NextBlockAlignment = NextBlock->getAlignment();
940 unsigned Size =
U.CPEMI->getOperand(2).getImm();
941 unsigned CPEEnd = CPEOffset +
Size;
946 if (CPEEnd > NextBlockOffset) {
947 Growth = CPEEnd - NextBlockOffset;
955 if (CPEOffset < UserOffset)
956 UserOffset += Growth;
961 return isOffsetInRange(UserOffset, CPEOffset, U);
966bool MipsConstantIslands::isCPEntryInRange
969 bool NegOk,
bool DoDump) {
970 unsigned CPEOffset = getOffsetOf(CPEMI);
974 unsigned Block =
MI->getParent()->getNumber();
977 <<
" max delta=" << MaxDisp
978 <<
format(
" insn address=%#x", UserOffset) <<
" in "
981 <<
format(
"CPE address=%#x offset=%+d: ", CPEOffset,
982 int(CPEOffset - UserOffset));
986 return isOffsetInRange(UserOffset, CPEOffset, MaxDisp, NegOk);
1006 for(
unsigned i = BBNum + 1, e = MF->getNumBlockIDs(); i < e; ++i) {
1009 unsigned Offset = BBInfo[i - 1].Offset + BBInfo[i - 1].Size;
1010 BBInfo[i].Offset =
Offset;
1018bool MipsConstantIslands::decrementCPEReferenceCount(
unsigned CPI,
1021 CPEntry *CPE = findConstPoolEntry(CPI, CPEMI);
1022 assert(CPE &&
"Unexpected!");
1023 if (--CPE->RefCount == 0) {
1024 removeDeadCPEMI(CPEMI);
1025 CPE->CPEMI =
nullptr;
1038int MipsConstantIslands::findInRangeCPEntry(CPUser& U,
unsigned UserOffset)
1044 if (isCPEntryInRange(UserMI, UserOffset, CPEMI,
U.getMaxDisp(),
U.NegOk,
1052 std::vector<CPEntry> &CPEs = CPEntries[CPI];
1053 for (CPEntry &CPE : CPEs) {
1055 if (CPE.CPEMI == CPEMI)
1058 if (CPE.CPEMI ==
nullptr)
1060 if (isCPEntryInRange(UserMI, UserOffset, CPE.CPEMI,
U.getMaxDisp(),
1062 LLVM_DEBUG(
dbgs() <<
"Replacing CPE#" << CPI <<
" with CPE#" << CPE.CPI
1065 U.CPEMI = CPE.CPEMI;
1069 MO.setIndex(CPE.CPI);
1076 return decrementCPEReferenceCount(CPI, CPEMI) ? 2 : 1;
1090int MipsConstantIslands::findLongFormInRangeCPEntry
1091 (CPUser& U,
unsigned UserOffset)
1097 if (isCPEntryInRange(UserMI, UserOffset, CPEMI,
1098 U.getLongFormMaxDisp(),
U.NegOk,
1102 U.setMaxDisp(
U.getLongFormMaxDisp());
1108 std::vector<CPEntry> &CPEs = CPEntries[CPI];
1109 for (CPEntry &CPE : CPEs) {
1111 if (CPE.CPEMI == CPEMI)
1114 if (CPE.CPEMI ==
nullptr)
1116 if (isCPEntryInRange(UserMI, UserOffset, CPE.CPEMI,
U.getLongFormMaxDisp(),
1118 LLVM_DEBUG(
dbgs() <<
"Replacing CPE#" << CPI <<
" with CPE#" << CPE.CPI
1121 U.CPEMI = CPE.CPEMI;
1125 MO.setIndex(CPE.CPI);
1132 return decrementCPEReferenceCount(CPI, CPEMI) ? 2 : 1;
1143 return ((1<<10)-1)*2;
1145 return ((1<<16)-1)*2;
1149 return ((1<<16)-1)*2;
1160bool MipsConstantIslands::findAvailableWater(CPUser &U,
unsigned UserOffset,
1161 water_iterator &WaterIter) {
1162 if (WaterList.empty())
1165 unsigned BestGrowth = ~0
u;
1166 for (water_iterator IP = std::prev(WaterList.end()),
B = WaterList.begin();;
1178 if (isWaterInRange(UserOffset, WaterBB, U, Growth) &&
1179 (WaterBB->
getNumber() <
U.HighWaterMark->getNumber() ||
1180 NewWaterList.
count(WaterBB)) && Growth < BestGrowth) {
1182 BestGrowth = Growth;
1185 <<
" Growth=" << Growth <<
'\n');
1188 if (BestGrowth == 0)
1194 return BestGrowth != ~0
u;
1204void MipsConstantIslands::createNewWater(
unsigned CPUserIndex,
1205 unsigned UserOffset,
1207 CPUser &
U = CPUsers[CPUserIndex];
1219 unsigned CPEOffset = UserBBI.
postOffset() + Delta;
1221 if (isOffsetInRange(UserOffset, CPEOffset, U)) {
1223 <<
format(
", expected CPE offset %#x\n", CPEOffset));
1230 int UncondBr = Mips::Bimm16;
1233 ImmBranches.push_back(ImmBranch(&UserMBB->
back(),
1234 MaxDisp,
false, UncondBr));
1235 BBInfo[UserMBB->
getNumber()].Size += Delta;
1236 adjustBBOffsetsAfter(UserMBB);
1247 unsigned BaseInsertOffset = UserOffset +
U.getMaxDisp();
1254 BaseInsertOffset -= 4;
1263 if (BaseInsertOffset + 8 >= UserBBI.
postOffset()) {
1267 unsigned EndInsertOffset = BaseInsertOffset + 4 +
1271 unsigned CPUIndex = CPUserIndex+1;
1272 unsigned NumCPUsers = CPUsers.size();
1274 for (
unsigned Offset = UserOffset +
TII->getInstSizeInBytes(*UserMI);
1275 Offset < BaseInsertOffset;
1277 assert(
MI != UserMBB->
end() &&
"Fell off end of block");
1278 if (CPUIndex < NumCPUsers && CPUsers[CPUIndex].
MI ==
MI) {
1279 CPUser &
U = CPUsers[CPUIndex];
1280 if (!isOffsetInRange(
Offset, EndInsertOffset, U)) {
1289 EndInsertOffset +=
U.CPEMI->getOperand(2).getImm();
1294 NewMBB = splitBlockBeforeInstr(*--
MI);
1301bool MipsConstantIslands::handleConstantPoolUser(
unsigned CPUserIndex) {
1302 CPUser &
U = CPUsers[CPUserIndex];
1308 unsigned UserOffset = getUserOffset(U);
1312 int result = findInRangeCPEntry(U, UserOffset);
1313 if (result==1)
return false;
1314 else if (result==2)
return true;
1320 if (findAvailableWater(U, UserOffset, IP)) {
1327 if (NewWaterList.
erase(WaterBB))
1328 NewWaterList.
insert(NewIsland);
1337 result = findLongFormInRangeCPEntry(U, UserOffset);
1338 if (result != 0)
return true;
1341 createNewWater(CPUserIndex, UserOffset, NewMBB);
1350 if (IP != WaterList.end())
1351 NewWaterList.
erase(WaterBB);
1354 NewWaterList.
insert(NewIsland);
1361 if (IP != WaterList.end())
1362 WaterList.erase(IP);
1368 updateForInsertedWaterBlock(NewIsland);
1371 decrementCPEReferenceCount(CPI, CPEMI);
1375 unsigned ID = createPICLabelUId();
1379 U.HighWaterMark = NewIsland;
1382 CPEntries[CPI].push_back(CPEntry(
U.CPEMI,
ID, 1));
1390 adjustBBOffsetsAfter(&*--NewIsland->
getIterator());
1400 dbgs() <<
" Moved CPE to #" <<
ID <<
" CPI=" << CPI
1408void MipsConstantIslands::removeDeadCPEMI(
MachineInstr *CPEMI) {
1414 if (CPEBB->
empty()) {
1424 adjustBBOffsetsAfter(CPEBB);
1434bool MipsConstantIslands::removeUnusedCPEntries() {
1435 unsigned MadeChange =
false;
1436 for (std::vector<CPEntry> &CPEs : CPEntries) {
1437 for (CPEntry &CPE : CPEs) {
1438 if (CPE.RefCount == 0 && CPE.CPEMI) {
1439 removeDeadCPEMI(CPE.CPEMI);
1440 CPE.CPEMI =
nullptr;
1450bool MipsConstantIslands::isBBInRange
1453 unsigned BrOffset = getOffsetOf(
MI) + PCAdj;
1454 unsigned DestOffset = BBInfo[DestBB->
getNumber()].Offset;
1458 <<
" max delta=" << MaxDisp <<
" from " << getOffsetOf(
MI)
1459 <<
" to " << DestOffset <<
" offset "
1460 <<
int(DestOffset - BrOffset) <<
"\t" << *
MI);
1462 if (BrOffset <= DestOffset) {
1464 if (DestOffset-BrOffset <= MaxDisp)
1467 if (BrOffset-DestOffset <= MaxDisp)
1475bool MipsConstantIslands::fixupImmediateBr(ImmBranch &Br) {
1481 if (isBBInRange(
MI, DestBB, Br.MaxDisp))
1485 return fixupUnconditionalBr(Br);
1486 return fixupConditionalBr(Br);
1494MipsConstantIslands::fixupUnconditionalBr(ImmBranch &Br) {
1499 unsigned BimmX16MaxDisp = ((1 << 16)-1) * 2;
1500 if (isBBInRange(
MI, DestBB, BimmX16MaxDisp)) {
1501 Br.MaxDisp = BimmX16MaxDisp;
1502 MI->setDesc(
TII->get(Mips::BimmX16));
1517 Br.MaxDisp = ((1<<24)-1) * 2;
1518 MI->setDesc(
TII->get(Mips::JalB16));
1521 adjustBBOffsetsAfter(
MBB);
1534MipsConstantIslands::fixupConditionalBr(ImmBranch &Br) {
1538 unsigned Opcode =
MI->getOpcode();
1543 if (isBBInRange(
MI, DestBB, LongFormMaxOff)) {
1544 Br.MaxDisp = LongFormMaxOff;
1545 MI->setDesc(
TII->get(LongFormOpcode));
1563 unsigned OppositeBranchOpcode =
TII->getOppositeBranchOpc(Opcode);
1579 if (isBBInRange(
MI, NewDest, Br.MaxDisp)) {
1581 dbgs() <<
" Invert Bcc condition and swap its destination with "
1583 MI->setDesc(
TII->get(OppositeBranchOpcode));
1585 MI->getOperand(TargetOperand).setMBB(NewDest);
1592 splitBlockBeforeInstr(*
MI);
1595 int delta =
TII->getInstSizeInBytes(
MBB->
back());
1603 <<
" also invert condition and change dest. to "
1608 if (
MI->getNumExplicitOperands() == 2) {
1610 .
addReg(
MI->getOperand(0).getReg())
1621 ImmBranches.push_back(ImmBranch(&
MBB->
back(), MaxDisp,
false, Br.UncondBr));
1624 BBInfo[
MI->getParent()->getNumber()].Size -=
TII->getInstSizeInBytes(*
MI);
1625 MI->eraseFromParent();
1626 adjustBBOffsetsAfter(
MBB);
1630void MipsConstantIslands::prescanForConstants() {
1633 switch (
MI.getDesc().getOpcode()) {
1634 case Mips::LwConstant32: {
1635 PrescannedForConstants =
true;
1643 const Constant *
C = ConstantInt::get(Int32Ty, V);
1644 unsigned index = MCP->getConstantPoolIndex(
C,
Align(4));
1645 MI.getOperand(2).ChangeToImmediate(index);
1647 MI.setDesc(
TII->get(Mips::LwRxPcTcp16));
1648 MI.removeOperand(1);
1649 MI.removeOperand(1);
1664 return new MipsConstantIslands();
MachineBasicBlock MachineBasicBlock::iterator MBBI
static GCRegistry::Add< OcamlGC > B("ocaml", "ocaml 3.10-compatible GC")
#define LLVM_DUMP_METHOD
Mark debug helper function definitions like dump() that should not be stripped from debug builds.
This file contains the declarations for the subclasses of Constant, which represent the different fla...
const HexagonInstrInfo * TII
This file declares the MachineConstantPool class which is an abstract constant pool to keep track of ...
static bool CompareMBBNumbers(const MachineBasicBlock *LHS, const MachineBasicBlock *RHS)
CompareMBBNumbers - Little predicate function to sort the WaterList by MBB ID.
static unsigned getUnconditionalBrDisp(int Opc)
getUnconditionalBrDisp - Returns the maximum displacement that can fit in the specific unconditional ...
static unsigned int longformBranchOpcode(unsigned int Opcode)
static unsigned int branchMaxOffsets(unsigned int Opcode)
static cl::opt< bool > NoLoadRelaxation("mips-constant-islands-no-load-relaxation", cl::init(false), cl::desc("Don't relax loads to long loads - for testing purposes"), cl::Hidden)
static cl::opt< int > ConstantIslandsSmallOffset("mips-constant-islands-small-offset", cl::init(0), cl::desc("Make small offsets be this amount for testing purposes"), cl::Hidden)
static bool BBHasFallthrough(MachineBasicBlock *MBB)
BBHasFallthrough - Return true if the specified basic block can fallthrough into the block immediatel...
static cl::opt< bool > AlignConstantIslands("mips-align-constant-islands", cl::Hidden, cl::init(true), cl::desc("Align constant islands in code"))
static unsigned int branchTargetOperand(MachineInstr *MI)
static bool BBIsJumpedOver(MachineBasicBlock *MBB)
BBIsJumpedOver - Return true of the specified basic block's only predecessor unconditionally branches...
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
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)
This is an important base class in LLVM.
A parsed version of the target data layout string in and methods for querying it.
FunctionPass class - This class is used to implement most global optimizations.
unsigned pred_size() const
void transferSuccessors(MachineBasicBlock *FromMBB)
Transfers all the successors from MBB to this machine basic block (i.e., copies all the successors Fr...
instr_iterator insert(instr_iterator I, MachineInstr *M)
Insert MI into the instruction list before I, possibly inside a bundle.
int getNumber() const
MachineBasicBlocks are uniquely numbered at the function level, unless they're not in a MachineFuncti...
void push_back(MachineInstr *MI)
const BasicBlock * getBasicBlock() const
Return the LLVM basic block that this instance corresponded to originally.
succ_iterator succ_begin()
unsigned succ_size() const
void setAlignment(Align A)
Set alignment of the basic block.
void addSuccessor(MachineBasicBlock *Succ, BranchProbability Prob=BranchProbability::getUnknown())
Add Succ as a successor of this MachineBasicBlock.
pred_iterator pred_begin()
MachineInstrBundleIterator< MachineInstr, true > reverse_iterator
const MachineFunction * getParent() const
Return the MachineFunction containing this basic block.
iterator_range< succ_iterator > successors()
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 '...
Align getAlignment() const
Return alignment of the basic block.
MachineInstrBundleIterator< MachineInstr > iterator
The MachineConstantPool class keeps track of constants referenced by a function which must be spilled...
MachineFunctionPass - This class adapts the FunctionPass interface to allow convenient creation of pa...
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.
MachineConstantPool * getConstantPool()
getConstantPool - Return the constant pool object for the current function.
void RenumberBlocks(MachineBasicBlock *MBBFrom=nullptr)
RenumberBlocks - This discards all of the MachineBasicBlock numbers and recomputes them.
BasicBlockListType::const_iterator const_iterator
const MachineInstrBuilder & addImm(int64_t Val) const
Add a new immediate operand.
const MachineInstrBuilder & addConstantPoolIndex(unsigned Idx, int Offset=0, unsigned TargetFlags=0) const
const MachineInstrBuilder & addReg(Register RegNo, unsigned flags=0, unsigned SubReg=0) const
Add a new virtual register operand.
const MachineInstrBuilder & addMBB(MachineBasicBlock *MBB, unsigned TargetFlags=0) const
Representation of each machine instruction.
unsigned getOpcode() const
Returns the opcode of this MachineInstr.
const MachineBasicBlock * getParent() const
void setDesc(const MCInstrDesc &TID)
Replace the instruction descriptor (thus opcode) of the current instruction with a new one.
bool isUnconditionalBranch(QueryType Type=AnyInBundle) const
Return true if this is a branch which always transfers control flow to some other block.
iterator_range< mop_iterator > operands()
void eraseFromParent()
Unlink 'this' from the containing basic block and delete it.
const MachineOperand & getOperand(unsigned i) const
MachineOperand class - Representation of each machine instruction operand.
MachineBasicBlock * getMBB() const
void setMBB(MachineBasicBlock *MBB)
static MachineOperand CreateImm(int64_t Val)
static MachineOperand CreateCPI(unsigned Idx, int Offset, unsigned TargetFlags=0)
MipsFunctionInfo - This class is derived from MachineFunction private Mips target-specific informatio...
static bool useConstantIslands()
virtual StringRef getPassName() const
getPassName - Return a nice clean name for a pass.
SmallSet - This maintains a set of unique values, optimizing for the case when the set is small (less...
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.
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
StringRef - Represent a constant reference to a string, i.e.
The instances of the Type class are immutable: once they are created, they are never changed.
static IntegerType * getInt32Ty(LLVMContext &C)
self_iterator getIterator()
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
@ C
The default llvm calling convention, compatible with C.
unsigned ID
LLVM IR allows to use arbitrary numbers as calling convention identifiers.
initializer< Ty > init(const Ty &Val)
This is an optimization pass for GlobalISel generic memory operations.
auto find(R &&Range, const T &Val)
Provide wrappers to std::find which take ranges instead of having to pass begin/end explicitly.
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.
MachineInstrBuilder BuildMI(MachineFunction &MF, const MIMetadata &MIMD, const MCInstrDesc &MCID)
Builder interface. Specify how to create the initial instruction itself.
bool isAligned(Align Lhs, uint64_t SizeInBytes)
Checks that SizeInBytes is a multiple of the alignment.
FunctionPass * createMipsConstantIslandPass()
Returns a pass that converts branches to long branches.
raw_ostream & dbgs()
dbgs() - This returns a reference to a raw_ostream for debugging messages.
void report_fatal_error(Error Err, bool gen_crash_diag=true)
Report a serious error, calling any installed error handler.
format_object< Ts... > format(const char *Fmt, const Ts &... Vals)
These are helper functions used to produce formatted output.
uint64_t offsetToAlignment(uint64_t Value, Align Alignment)
Returns the offset to the next integer (mod 2**64) that is greater than or equal to Value and is a mu...
auto lower_bound(R &&Range, T &&Value)
Provide wrappers to std::lower_bound which take ranges instead of having to pass begin/end explicitly...
bool is_contained(R &&Range, const E &Element)
Returns true if Element is found in Range.
APFloat neg(APFloat X)
Returns the negated value of the argument.
unsigned Log2(Align A)
Returns the log2 of the alignment.
Printable printMBBReference(const MachineBasicBlock &MBB)
Prints a machine basic block reference.
This struct is a compact representation of a valid (non-zero power of two) alignment.
uint64_t value() const
This is a hole in the type system and should not be abused.
BasicBlockInfo - Information about the offset and size of a single basic block.
unsigned Size
Size - Size of the basic block in bytes.
unsigned postOffset(Align Alignment=Align(1)) const
Compute the offset immediately following this block.
unsigned Offset
Offset - Distance from the beginning of the function to the beginning of this basic block.