21 #include "llvm/Config/llvm-config.h" 36 #define DEBUG_TYPE "branch-relaxation" 38 STATISTIC(NumSplit,
"Number of basic blocks split");
39 STATISTIC(NumConditionalRelaxed,
"Number of conditional branches relaxed");
40 STATISTIC(NumUnconditionalRelaxed,
"Number of unconditional branches relaxed");
42 #define BRANCH_RELAX_NAME "Branch relaxation pass" 68 unsigned PO = Offset +
Size;
73 unsigned AlignAmt = 1 <<
Align;
75 if (Align <= ParentAlign)
85 std::unique_ptr<RegScavenger> RS;
92 bool relaxBranchInstructions();
130 unsigned PrevNum = MF->begin()->getNumber();
132 unsigned Align = MBB.getAlignment();
133 unsigned Num = MBB.getNumber();
135 assert(!Num || BlockInfo[PrevNum].postOffset(MBB) <= BlockInfo[Num].
Offset);
142 #if !defined(NDEBUG) || defined(LLVM_ENABLE_DUMP) 145 for (
auto &MBB : *MF) {
155 void BranchRelaxation::scanFunction() {
157 BlockInfo.resize(MF->getNumBlockIDs());
167 adjustBlockOffsets(*MF->begin());
174 Size +=
TII->getInstSizeInBytes(
MI);
181 unsigned BranchRelaxation::getInstrOffset(
const MachineInstr &
MI)
const {
191 assert(
I != MBB->
end() &&
"Didn't find MI in its own basic block?");
192 Offset +=
TII->getInstSizeInBytes(*
I);
206 BlockInfo[Num].Offset = BlockInfo[PrevNum].postOffset(MBB);
244 TII->insertUnconditionalBranch(*OrigBB, NewBB,
DebugLoc());
270 adjustBlockOffsets(*OrigBB);
273 if (
TRI->trackLivenessAfterRegAlloc(*MF))
283 bool BranchRelaxation::isBlockInRange(
285 int64_t BrOffset = getInstrOffset(MI);
286 int64_t DestOffset = BlockInfo[DestBB.
getNumber()].Offset;
288 if (
TII->isBranchOffsetInRange(MI.
getOpcode(), DestOffset - BrOffset))
294 << DestOffset <<
" offset " << DestOffset - BrOffset <<
'\t' 303 bool BranchRelaxation::fixupConditionalBranch(
MachineInstr &MI) {
314 TII->insertUnconditionalBranch(*MBB, DestBB, DL, &NewBrSize);
320 unsigned &BBSize = BlockInfo[MBB->
getNumber()].Size;
326 unsigned &BBSize = BlockInfo[MBB->
getNumber()].Size;
329 BBSize -= RemovedSize;
335 adjustBlockOffsets(*MBB);
338 if (NewBB &&
TRI->trackLivenessAfterRegAlloc(*MF))
343 assert(!Fail &&
"branches to be relaxed must be analyzable");
356 if (FBB && isBlockInRange(MI, *FBB)) {
365 "its destination with " 369 insertBranch(MBB, FBB, TBB, Cond);
370 finalizeBlockChanges(MBB,
nullptr);
376 NewBB = createNewBlockAfter(*MBB);
378 insertUncondBranch(NewBB, FBB);
390 <<
", invert condition and change dest. to " 395 insertBranch(MBB, &NextBB, TBB, Cond);
397 finalizeBlockChanges(MBB, NewBB);
403 <<
" Insert a new BB after " << MBB->
back());
419 NewBB = createNewBlockAfter(*MBB);
420 insertUncondBranch(NewBB, TBB);
424 <<
" Keep the exiting condition.\n" 426 <<
" In the new BB: Insert B to " 435 insertBranch(MBB, NewBB, FBB, Cond);
437 finalizeBlockChanges(MBB, NewBB);
441 bool BranchRelaxation::fixupUnconditionalBranch(
MachineInstr &MI) {
444 unsigned OldBrSize =
TII->getInstSizeInBytes(MI);
447 int64_t DestOffset = BlockInfo[DestBB->
getNumber()].Offset;
448 int64_t SrcOffset = getInstrOffset(MI);
452 BlockInfo[MBB->
getNumber()].Size -= OldBrSize;
459 BranchBB = createNewBlockAfter(*MBB);
474 BlockInfo[BranchBB->
getNumber()].Size +=
TII->insertIndirectBranch(
475 *BranchBB, *DestBB, DL, DestOffset - SrcOffset, RS.
get());
477 adjustBlockOffsets(*MBB);
481 bool BranchRelaxation::relaxBranchInstructions() {
482 bool Changed =
false;
491 if (Last == MBB.
end())
499 if (Last->isUnconditionalBranch()) {
503 if (!isBlockInRange(*Last, *DestBB)) {
504 fixupUnconditionalBranch(*Last);
505 ++NumUnconditionalRelaxed;
514 J != MBB.
end(); J = Next) {
520 if (!isBlockInRange(MI, *DestBB)) {
521 if (Next != MBB.
end() && Next->isConditionalBranch()) {
526 splitBlockBeforeInstr(*Next, DestBB);
528 fixupConditionalBranch(MI);
529 ++NumConditionalRelaxed;
553 if (
TRI->trackLivenessAfterRegAlloc(*MF))
558 MF->RenumberBlocks();
564 LLVM_DEBUG(
dbgs() <<
" Basic blocks before relaxation\n"; dumpBBs(););
566 bool MadeChange =
false;
567 while (relaxBranchInstructions())
573 LLVM_DEBUG(
dbgs() <<
" Basic blocks after relaxation\n\n"; dumpBBs());
constexpr char Align[]
Key for Kernel::Arg::Metadata::mAlign.
DILocation * get() const
Get the underlying DILocation.
This class represents lattice values for constants.
virtual const TargetRegisterInfo * getRegisterInfo() const
getRegisterInfo - If register information is available, return it.
const DebugLoc & getDebugLoc() const
Returns the debug location id of this MachineInstr.
iterator getFirstTerminator()
Returns an iterator to the first terminator instruction of this basic block.
void transferSuccessors(MachineBasicBlock *FromMBB)
Transfers all the successors from MBB to this machine basic block (i.e., copies all the successors Fr...
format_object< Ts... > format(const char *Fmt, const Ts &... Vals)
These are helper functions used to produce formatted output.
bool reverseBranchCondition(SmallVectorImpl< MachineOperand > &Cond) const override
Reverses the branch condition of the specified condition list, returning false on success and true if...
unsigned Offset
Offset - Distance from the beginning of the function to the beginning of this basic block...
char & BranchRelaxationPassID
BranchRelaxation - This pass replaces branches that need to jump further than is supported by a branc...
STATISTIC(NumFunctions, "Total number of functions")
unsigned const TargetRegisterInfo * TRI
void computeBlockSize(MachineFunction *MF, MachineBasicBlock *MBB, BasicBlockInfo &BBI)
BasicBlockInfo - Information about the offset and size of a single basic block.
iterator_range< succ_iterator > successors()
bool analyzeBranch(MachineBasicBlock &MBB, MachineBasicBlock *&TBB, MachineBasicBlock *&FBB, SmallVectorImpl< MachineOperand > &Cond, bool AllowModify) const override
Analyze the branching code at the end of MBB, returning true if it cannot be understood (e...
MachineFunctionPass - This class adapts the FunctionPass interface to allow convenient creation of pa...
const HexagonInstrInfo * TII
Printable printMBBReference(const MachineBasicBlock &MBB)
Prints a machine basic block reference.
This class consists of common code factored out of the SmallVector class to reduce code duplication b...
void eraseFromParent()
Unlink 'this' from the containing basic block and delete it.
unsigned getAlignment() const
getAlignment - Return the alignment (log2, not bytes) of the function.
unsigned getOpcode() const
Returns the opcode of this MachineInstr.
iterator getLastNonDebugInstr()
Returns an iterator to the last non-debug instruction in the basic block, or end().
int getNumber() const
MachineBasicBlocks are uniquely numbered at the function level, unless they're not in a MachineFuncti...
virtual const TargetInstrInfo * getInstrInfo() const
instr_iterator insert(instr_iterator I, MachineInstr *M)
Insert MI into the instruction list before I, possibly inside a bundle.
TargetInstrInfo - Interface to description of machine instruction set.
void addLiveIn(MCPhysReg PhysReg, LaneBitmask LaneMask=LaneBitmask::getAll())
Adds the specified register as a live in.
This file declares the machine register scavenger class.
unsigned getAlignment() const
Return alignment of the basic block.
self_iterator getIterator()
TargetRegisterInfo base class - We assume that the target defines a static array of TargetRegisterDes...
This file implements the LivePhysRegs utility for tracking liveness of physical registers.
bool verify(const TargetRegisterInfo &TRI) const
Check that information hold by this instance make sense for the given TRI.
#define INITIALIZE_PASS(passName, arg, name, cfg, analysis)
iterator_range< T > make_range(T x, T y)
Convenience function for iterating over sub-ranges.
bool isConditionalBranch(QueryType Type=AnyInBundle) const
Return true if this is a branch which may fall through to the next instruction or may transfer contro...
Iterator for intrusive lists based on ilist_node.
void addSuccessor(MachineBasicBlock *Succ, BranchProbability Prob=BranchProbability::getUnknown())
Add Succ as a successor of this MachineBasicBlock.
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small...
void updateTerminator()
Update the terminator instructions in block to account for changes to the layout. ...
unsigned Size
Size - Size of the basic block in bytes.
unsigned insertBranch(MachineBasicBlock &MBB, MachineBasicBlock *TBB, MachineBasicBlock *FBB, ArrayRef< MachineOperand > Cond, const DebugLoc &DL, int *BytesAdded=nullptr) const override
Insert branch code into the end of the specified MachineBasicBlock.
void sortUniqueLiveIns()
Sorts and uniques the LiveIns vector.
raw_ostream & dbgs()
dbgs() - This returns a reference to a raw_ostream for debugging messages.
void replaceSuccessor(MachineBasicBlock *Old, MachineBasicBlock *New)
Replace successor OLD with NEW and update probability info.
unsigned removeBranch(MachineBasicBlock &MBB, int *BytesRemoved=nullptr) const override
Remove the branching code at the end of the specific MBB.
void computeAndAddLiveIns(LivePhysRegs &LiveRegs, MachineBasicBlock &MBB)
Convenience function combining computeLiveIns() and addLiveIns().
const MachineBasicBlock * getParent() const
TargetSubtargetInfo - Generic base class for all target subtargets.
Representation of each machine instruction.
const MachineFunction * getParent() const
Return the MachineFunction containing this basic block.
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 '...
A set of physical registers with utility functions to track liveness when walking backward/forward th...
Pair of physical register and lane mask.
const BasicBlock * getBasicBlock() const
Return the LLVM basic block that this instance corresponded to originally.
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
#define BRANCH_RELAX_NAME
uint64_t OffsetToAlignment(uint64_t Value, uint64_t Align)
Returns the offset to the next integer (mod 2**64) that is greater than or equal to Value and is a mu...
StringRef - Represent a constant reference to a string, i.e.
static cl::opt< bool > BranchRelaxation("aarch64-enable-branch-relax", cl::Hidden, cl::init(true), cl::desc("Relax out of range conditional branches"))