diff options
Diffstat (limited to 'lib/CodeGen/MachineBasicBlock.cpp')
| -rw-r--r-- | lib/CodeGen/MachineBasicBlock.cpp | 57 | 
1 files changed, 44 insertions, 13 deletions
diff --git a/lib/CodeGen/MachineBasicBlock.cpp b/lib/CodeGen/MachineBasicBlock.cpp index 3869f976854d..06112723497b 100644 --- a/lib/CodeGen/MachineBasicBlock.cpp +++ b/lib/CodeGen/MachineBasicBlock.cpp @@ -23,6 +23,7 @@  #include "llvm/CodeGen/SlotIndexes.h"  #include "llvm/IR/BasicBlock.h"  #include "llvm/IR/DataLayout.h" +#include "llvm/IR/DebugInfoMetadata.h"  #include "llvm/IR/ModuleSlotTracker.h"  #include "llvm/MC/MCAsmInfo.h"  #include "llvm/MC/MCContext.h" @@ -148,8 +149,11 @@ MachineBasicBlock::iterator MachineBasicBlock::getFirstNonPHI() {  MachineBasicBlock::iterator  MachineBasicBlock::SkipPHIsAndLabels(MachineBasicBlock::iterator I) { +  const TargetInstrInfo *TII = getParent()->getSubtarget().getInstrInfo(); +    iterator E = end(); -  while (I != E && (I->isPHI() || I->isPosition())) +  while (I != E && (I->isPHI() || I->isPosition() || +                    TII->isBasicBlockPrologue(*I)))      ++I;    // FIXME: This needs to change if we wish to bundle labels    // inside the bundle. @@ -160,8 +164,11 @@ MachineBasicBlock::SkipPHIsAndLabels(MachineBasicBlock::iterator I) {  MachineBasicBlock::iterator  MachineBasicBlock::SkipPHIsLabelsAndDebug(MachineBasicBlock::iterator I) { +  const TargetInstrInfo *TII = getParent()->getSubtarget().getInstrInfo(); +    iterator E = end(); -  while (I != E && (I->isPHI() || I->isPosition() || I->isDebugValue())) +  while (I != E && (I->isPHI() || I->isPosition() || I->isDebugValue() || +                    TII->isBasicBlockPrologue(*I)))      ++I;    // FIXME: This needs to change if we wish to bundle labels / dbg_values    // inside the bundle. @@ -225,7 +232,7 @@ StringRef MachineBasicBlock::getName() const {    if (const BasicBlock *LBB = getBasicBlock())      return LBB->getName();    else -    return "(null)"; +    return StringRef("", 0);  }  /// Return a hopefully unique identifier for this block. @@ -417,7 +424,7 @@ void MachineBasicBlock::updateTerminator() {    MachineBasicBlock *TBB = nullptr, *FBB = nullptr;    SmallVector<MachineOperand, 4> Cond; -  DebugLoc DL;  // FIXME: this is nowhere +  DebugLoc DL = findBranchDebugLoc();    bool B = TII->analyzeBranch(*this, TBB, FBB, Cond);    (void) B;    assert(!B && "UpdateTerminators requires analyzable predecessors!"); @@ -485,7 +492,7 @@ void MachineBasicBlock::updateTerminator() {        // FIXME: This does not seem like a reasonable pattern to support, but it        // has been seen in the wild coming out of degenerate ARM test cases.        TII->removeBranch(*this); -   +        // Finally update the unconditional successor to be reached via a branch if        // it would not be reached by fallthrough.        if (!isLayoutSuccessor(TBB)) @@ -681,16 +688,16 @@ bool MachineBasicBlock::isLayoutSuccessor(const MachineBasicBlock *MBB) const {    return std::next(I) == MachineFunction::const_iterator(MBB);  } -bool MachineBasicBlock::canFallThrough() { +MachineBasicBlock *MachineBasicBlock::getFallThrough() {    MachineFunction::iterator Fallthrough = getIterator();    ++Fallthrough;    // If FallthroughBlock is off the end of the function, it can't fall through.    if (Fallthrough == getParent()->end()) -    return false; +    return nullptr;    // If FallthroughBlock isn't a successor, no fallthrough is possible.    if (!isSuccessor(&*Fallthrough)) -    return false; +    return nullptr;    // Analyze the branches, if any, at the end of the block.    MachineBasicBlock *TBB = nullptr, *FBB = nullptr; @@ -702,25 +709,31 @@ bool MachineBasicBlock::canFallThrough() {      // is possible. The isPredicated check is needed because this code can be      // called during IfConversion, where an instruction which is normally a      // Barrier is predicated and thus no longer an actual control barrier. -    return empty() || !back().isBarrier() || TII->isPredicated(back()); +    return (empty() || !back().isBarrier() || TII->isPredicated(back())) +               ? &*Fallthrough +               : nullptr;    }    // If there is no branch, control always falls through. -  if (!TBB) return true; +  if (!TBB) return &*Fallthrough;    // If there is some explicit branch to the fallthrough block, it can obviously    // reach, even though the branch should get folded to fall through implicitly.    if (MachineFunction::iterator(TBB) == Fallthrough ||        MachineFunction::iterator(FBB) == Fallthrough) -    return true; +    return &*Fallthrough;    // If it's an unconditional branch to some block not the fall through, it    // doesn't fall through. -  if (Cond.empty()) return false; +  if (Cond.empty()) return nullptr;    // Otherwise, if it is conditional and has no explicit false block, it falls    // through. -  return FBB == nullptr; +  return (FBB == nullptr) ? &*Fallthrough : nullptr; +} + +bool MachineBasicBlock::canFallThrough() { +  return getFallThrough() != nullptr;  }  MachineBasicBlock *MachineBasicBlock::SplitCriticalEdge(MachineBasicBlock *Succ, @@ -1144,6 +1157,24 @@ MachineBasicBlock::findDebugLoc(instr_iterator MBBI) {    return {};  } +/// Find and return the merged DebugLoc of the branch instructions of the block. +/// Return UnknownLoc if there is none. +DebugLoc +MachineBasicBlock::findBranchDebugLoc() { +  DebugLoc DL; +  auto TI = getFirstTerminator(); +  while (TI != end() && !TI->isBranch()) +    ++TI; + +  if (TI != end()) { +    DL = TI->getDebugLoc(); +    for (++TI ; TI != end() ; ++TI) +      if (TI->isBranch()) +        DL = DILocation::getMergedLocation(DL, TI->getDebugLoc()); +  } +  return DL; +} +  /// Return probability of the edge from this block to MBB.  BranchProbability  MachineBasicBlock::getSuccProbability(const_succ_iterator Succ) const {  | 
