61#define DEBUG_TYPE "loop-unroll-and-jam" 
   63STATISTIC(NumUnrolledAndJammed, 
"Number of loops unroll and jammed");
 
   64STATISTIC(NumCompletelyUnrolledAndJammed, 
"Number of loops unroll and jammed");
 
   72  Loop *SubLoop = L.getSubLoops()[0];
 
   88    if (BB == SubLoopPreHeader)
 
   92      if (!ForeBlocks.
count(Succ))
 
 
  143    if (!VisitedInstr.
insert(
I).second)
 
  146    if (AftBlocks.
count(
I->getParent()))
 
  147      for (
auto &U : 
I->operands())
 
  149          if (!ProcessInstr(
II))
 
  155  for (
auto &Phi : Header->phis()) {
 
  156    Value *V = Phi.getIncomingValueForBlock(Latch);
 
  158      if (!ProcessInstr(
I))
 
 
  174                             if (AftBlocks.
count(
I->getParent()))
 
  175                               I->moveBefore(InsertLoc);
 
 
  216                       unsigned TripMultiple, 
bool UnrollRemainder,
 
  223  assert(Header && 
"No header.");
 
  224  assert(L->getSubLoops().size() == 1);
 
  225  Loop *SubLoop = *L->begin();
 
  228  if (TripCount == 0 && 
Count < 2) {
 
  229    LLVM_DEBUG(
dbgs() << 
"Won't unroll-and-jam; almost nothing to do\n");
 
  235  assert(TripCount == 0 || TripCount % TripMultiple == 0);
 
  238  bool CompletelyUnroll = (
Count == TripCount);
 
  241  if (TripMultiple % 
Count != 0) {
 
  244                                    UnrollRemainder,  
false,
 
  245                                    LI, SE, DT, AC, 
TTI, 
true,
 
  247      LLVM_DEBUG(
dbgs() << 
"Won't unroll-and-jam; remainder loop could not be " 
  248                           "generated when assuming runtime trip count\n");
 
  262  if (CompletelyUnroll) {
 
  264                      << Header->getName() << 
" with trip count " << TripCount
 
  268              << 
"completely unroll and jammed loop with " 
  269              << NV(
"UnrollCount", TripCount) << 
" iterations");
 
  271    auto DiagBuilder = [&]() {
 
  274      return Diag << 
"unroll and jammed loop by a factor of " 
  275                  << NV(
"UnrollCount", 
Count);
 
  278    LLVM_DEBUG(
dbgs() << 
"UNROLL AND JAMMING loop %" << Header->getName()
 
  280    if (TripMultiple != 1) {
 
  281      LLVM_DEBUG(
dbgs() << 
" with " << TripMultiple << 
" trips per branch");
 
  283        return DiagBuilder() << 
" with " << NV(
"TripMultiple", TripMultiple)
 
  284                             << 
" trips per branch";
 
  288      ORE->
emit([&]() { 
return DiagBuilder() << 
" with run-time trip count"; });
 
  293  BasicBlock *Preheader = L->getLoopPreheader();
 
  295  assert(Preheader && 
"No preheader");
 
  296  assert(LatchBlock && 
"No latch block");
 
  301  bool SubLoopContinueOnTrue = SubLoop->
contains(
 
  315  std::vector<BasicBlock *> ForeBlocksFirst;
 
  316  std::vector<BasicBlock *> ForeBlocksLast;
 
  317  std::vector<BasicBlock *> SubLoopBlocksFirst;
 
  318  std::vector<BasicBlock *> SubLoopBlocksLast;
 
  319  std::vector<BasicBlock *> AftBlocksFirst;
 
  320  std::vector<BasicBlock *> AftBlocksLast;
 
  321  ForeBlocksFirst.push_back(Header);
 
  323  SubLoopBlocksFirst.push_back(SubLoop->
getHeader());
 
  326  AftBlocksLast.push_back(L->getExitingBlock());
 
  332      Header, LatchBlock, ForeBlocksLast[0]->getTerminator()->getIterator(),
 
  346  if (Header->getParent()->shouldEmitDebugInfoForProfiling() &&
 
  350        if (!
I.isDebugOrPseudoInst())
 
  352            auto NewDIL = DIL->cloneByMultiplyingDuplicationFactor(
Count);
 
  354              I.setDebugLoc(*NewDIL);
 
  357                         << 
"Failed to create new discriminator: " 
  358                         << DIL->getFilename() << 
" Line: " << DIL->getLine());
 
  362  for (
unsigned It = 1; It != 
Count; ++It) {
 
  368    NewLoops[SubLoop] = SubLoop;
 
  373      Header->getParent()->insert(Header->getParent()->end(), New);
 
  378      if (ForeBlocks.
count(*BB)) {
 
  379        if (*BB == ForeBlocksFirst[0])
 
  380          ForeBlocksFirst.push_back(New);
 
  381        if (*BB == ForeBlocksLast[0])
 
  382          ForeBlocksLast.push_back(New);
 
  383      } 
else if (SubLoopBlocks.
count(*BB)) {
 
  384        if (*BB == SubLoopBlocksFirst[0])
 
  385          SubLoopBlocksFirst.push_back(New);
 
  386        if (*BB == SubLoopBlocksLast[0])
 
  387          SubLoopBlocksLast.push_back(New);
 
  388      } 
else if (AftBlocks.
count(*BB)) {
 
  389        if (*BB == AftBlocksFirst[0])
 
  390          AftBlocksFirst.push_back(New);
 
  391        if (*BB == AftBlocksLast[0])
 
  392          AftBlocksLast.push_back(New);
 
  398      auto &
Last = LastValueMap[*BB];
 
  399      PrevItValueMap[New] = (It == 1 ? *BB : 
Last);
 
  403        auto &LVM = LastValueMap[VI->first];
 
  404        PrevItValueMap[VI->second] =
 
  405            const_cast<Value *
>(It == 1 ? VI->first : LVM);
 
  412      if (*BB == ForeBlocksFirst[0])
 
  414      else if (*BB == SubLoopBlocksFirst[0])
 
  416      else if (*BB == AftBlocksFirst[0])
 
  421        auto BBDomNode = DT->
getNode(*BB);
 
  422        auto BBIDom = BBDomNode->
getIDom();
 
  423        BasicBlock *OriginalBBIDom = BBIDom->getBlock();
 
  442    for (
PHINode &Phi : ForeBlocksFirst[It]->phis()) {
 
  443      Value *OldValue = Phi.getIncomingValueForBlock(AftBlocksLast[It]);
 
  444      assert(OldValue && 
"should have incoming edge from Aft[It]");
 
  445      Value *NewValue = OldValue;
 
  446      if (
Value *PrevValue = PrevItValueMap[OldValue])
 
  447        NewValue = PrevValue;
 
  449      assert(Phi.getNumOperands() == 2);
 
  450      Phi.setIncomingBlock(0, ForeBlocksLast[It - 1]);
 
  451      Phi.setIncomingValue(0, NewValue);
 
  452      Phi.removeIncomingValue(1);
 
  465    for (
PHINode &Phi : BB->phis()) {
 
  466      for (
unsigned b = 0; b < Phi.getNumIncomingValues(); ++b) {
 
  467        if (Phi.getIncomingBlock(b) == OldBB) {
 
  468          Value *OldValue = Phi.getIncomingValue(b);
 
  469          if (
Value *LastValue = LastValueMap[OldValue])
 
  470            Phi.setIncomingValue(b, LastValue);
 
  471          Phi.setIncomingBlock(b, NewBB);
 
  481      Phi->moveBefore(*Dest, insertPoint);
 
  485  updatePHIBlocksAndValues(LoopExit, AftBlocksLast[0], AftBlocksLast.back(),
 
  494  if (CompletelyUnroll) {
 
  496      Phi->replaceAllUsesWith(Phi->getIncomingValueForBlock(Preheader));
 
  497      Phi->eraseFromParent();
 
  501    updatePHIBlocksAndValues(ForeBlocksFirst[0], AftBlocksLast[0],
 
  502                             AftBlocksLast.back(), LastValueMap);
 
  505  for (
unsigned It = 1; It != 
Count; It++) {
 
  516  SubTerm->
setSuccessor(!SubLoopContinueOnTrue, SubLoopBlocksFirst[0]);
 
  517  SubTerm->
setSuccessor(SubLoopContinueOnTrue, AftBlocksFirst[0]);
 
  518  SubLoopBlocksFirst[0]->replacePhiUsesWith(ForeBlocksLast[0],
 
  519                                            ForeBlocksLast.back());
 
  520  SubLoopBlocksFirst[0]->replacePhiUsesWith(SubLoopBlocksLast[0],
 
  521                                            SubLoopBlocksLast.back());
 
  523  for (
unsigned It = 1; It != 
Count; It++) {
 
  531    SubLoopBlocksFirst[It]->replacePhiUsesWith(ForeBlocksLast[It],
 
  532                                               ForeBlocksLast.back());
 
  533    SubLoopBlocksFirst[It]->replacePhiUsesWith(SubLoopBlocksLast[It],
 
  534                                               SubLoopBlocksLast.back());
 
  535    movePHIs(SubLoopBlocksFirst[It], SubLoopBlocksFirst[0]);
 
  540  if (CompletelyUnroll) {
 
  544    AftTerm->
setSuccessor(!ContinueOnTrue, ForeBlocksFirst[0]);
 
  546           "Expecting the ContinueOnTrue successor of AftTerm to be LoopExit");
 
  548  AftBlocksFirst[0]->replacePhiUsesWith(SubLoopBlocksLast[0],
 
  549                                        SubLoopBlocksLast.back());
 
  551  for (
unsigned It = 1; It != 
Count; It++) {
 
  559    AftBlocksFirst[It]->replacePhiUsesWith(SubLoopBlocksLast[It],
 
  560                                           SubLoopBlocksLast.back());
 
  561    movePHIs(AftBlocksFirst[It], AftBlocksFirst[0]);
 
  569    DTUpdates.
emplace_back(DominatorTree::UpdateKind::Delete, ForeBlocksLast[0],
 
  570                           SubLoopBlocksFirst[0]);
 
  571    DTUpdates.
emplace_back(DominatorTree::UpdateKind::Delete,
 
  572                           SubLoopBlocksLast[0], AftBlocksFirst[0]);
 
  574    DTUpdates.
emplace_back(DominatorTree::UpdateKind::Insert,
 
  575                           ForeBlocksLast.back(), SubLoopBlocksFirst[0]);
 
  576    DTUpdates.
emplace_back(DominatorTree::UpdateKind::Insert,
 
  577                           SubLoopBlocksLast.back(), AftBlocksFirst[0]);
 
  599  NumCompletelyUnrolledAndJammed += CompletelyUnroll;
 
  600  ++NumUnrolledAndJammed;
 
  603  if (CompletelyUnroll)
 
  616  if (!CompletelyUnroll)
 
  617    assert(L->isLoopSimplifyForm());
 
 
  640      } 
else if (
I.mayReadOrWriteMemory()) {
 
 
  649                                       unsigned UnrollLevel, 
unsigned JamLevel,
 
  653  for (
unsigned CurLoopDepth = UnrollLevel + 1; CurLoopDepth <= JamLevel;
 
  655    auto JammedDir = 
D->getDirection(CurLoopDepth);
 
 
  667                                        unsigned UnrollLevel, 
unsigned JamLevel,
 
  670  for (
unsigned CurLoopDepth = UnrollLevel + 1; CurLoopDepth <= JamLevel;
 
  672    auto JammedDir = 
D->getDirection(CurLoopDepth);
 
  681  return Sequentialized;
 
 
  693                            unsigned UnrollLevel, 
unsigned JamLevel,
 
  695  assert(UnrollLevel <= JamLevel &&
 
  696         "Expecting JamLevel to be at least UnrollLevel");
 
  714  std::unique_ptr<Dependence> 
D = DI.
depends(Src, Dst);
 
  717  assert(
D->isOrdered() && 
"Expected an output, flow or anti dep.");
 
  719  if (
D->isConfused()) {
 
  721                      << 
"  " << *Src << 
"\n" 
  722                      << 
"  " << *Dst << 
"\n");
 
  730  for (
unsigned CurLoopDepth = 1; CurLoopDepth < UnrollLevel; ++CurLoopDepth)
 
  734  auto UnrollDirection = 
D->getDirection(UnrollLevel);
 
  744                                  Sequentialized, 
D.get()))
 
  749                                   Sequentialized, 
D.get()))
 
 
  773    CurrentLoadsAndStores.
clear();
 
  777    Loop *CurLoop = LI.
getLoopFor((*Blocks.begin())->front().getParent());
 
  780    for (
auto *Earlier : EarlierLoadsAndStores) {
 
  783      unsigned CommonLoopDepth = std::min(EarlierDepth, CurLoopDepth);
 
  784      for (
auto *Later : CurrentLoadsAndStores) {
 
  785        if (!
checkDependency(Earlier, Later, LoopDepth, CommonLoopDepth, 
false,
 
  791    size_t NumInsts = CurrentLoadsAndStores.
size();
 
  792    for (
size_t I = 0; 
I < NumInsts; ++
I) {
 
  793      for (
size_t J = 
I; J < NumInsts; ++J) {
 
  795                             LoopDepth, CurLoopDepth, 
true, DI))
 
  800    EarlierLoadsAndStores.append(CurrentLoadsAndStores.
begin(),
 
  801                                 CurrentLoadsAndStores.
end());
 
 
  811  const Loop *L = &Root;
 
  814    if (!L->isLoopSimplifyForm())
 
  817    if (!L->isRotatedForm())
 
  820    if (L->getHeader()->hasAddressTaken()) {
 
  825    unsigned SubLoopsSize = L->getSubLoops().size();
 
  826    if (SubLoopsSize == 0)
 
  830    if (SubLoopsSize != 1)
 
  837    if (!L->getExitBlock()) {
 
  838      LLVM_DEBUG(
dbgs() << 
"Won't unroll-and-jam; only loops with single exit " 
  839                           "blocks can be unrolled and jammed.\n");
 
  844    if (!L->getExitingBlock()) {
 
  845      LLVM_DEBUG(
dbgs() << 
"Won't unroll-and-jam; only loops with single " 
  846                           "exiting blocks can be unrolled and jammed.\n");
 
  850    L = L->getSubLoops()[0];
 
 
  857  while (!L->getSubLoops().empty())
 
  858    L = L->getSubLoops()[0];
 
 
  865    LLVM_DEBUG(
dbgs() << 
"Won't unroll-and-jam; Ineligible loop form\n");
 
  927    LLVM_DEBUG(
dbgs() << 
"Won't unroll-and-jam; Incompatible loop layout\n");
 
  934  if (AftBlocksMap[L].
size() != 1) {
 
  935    LLVM_DEBUG(
dbgs() << 
"Won't unroll-and-jam; Can't currently handle " 
  936                         "multiple blocks after the loop\n");
 
  942  if (
any_of(L->getLoopsInPreorder(), [&SE](
Loop *SubLoop) {
 
  943        return !hasIterationCountInvariantInParent(SubLoop, SE);
 
  945    LLVM_DEBUG(
dbgs() << 
"Won't unroll-and-jam; Inner loop iteration count is " 
  946                         "not consistent on each iteration\n");
 
  954    LLVM_DEBUG(
dbgs() << 
"Won't unroll-and-jam; Something may throw\n");
 
  968  Loop *SubLoop = L->getSubLoops()[0];
 
  970          Header, Latch, AftBlocks, [&AftBlocks, &SubLoop](
Instruction *
I) {
 
  973            if (AftBlocks.
count(
I->getParent())) {
 
  980              if (
I->mayHaveSideEffects() || 
I->mayReadOrWriteMemory())
 
  987                         "instructions after subloop to before it\n");
 
  996    LLVM_DEBUG(
dbgs() << 
"Won't unroll-and-jam; failed dependency check\n");
 
 
assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")
 
static GCRegistry::Add< StatepointGC > D("statepoint-example", "an example strategy for statepoint")
 
This file defines the DenseMap class.
 
This file defines a set of templates that efficiently compute a dominator tree over a generic graph.
 
SmallPtrSet< BasicBlock *, 4 > BasicBlockSet
 
static bool partitionLoopBlocks(Loop &L, BasicBlockSet &ForeBlocks, BasicBlockSet &AftBlocks, DominatorTree &DT)
 
static void moveHeaderPhiOperandsToForeBlocks(BasicBlock *Header, BasicBlock *Latch, BasicBlock::iterator InsertLoc, BasicBlockSet &AftBlocks)
 
static Loop * getInnerMostLoop(Loop *L)
 
static bool getLoadsAndStores(BasicBlockSet &Blocks, SmallVector< Instruction *, 4 > &MemInstr)
 
static bool preservesForwardDependence(Instruction *Src, Instruction *Dst, unsigned UnrollLevel, unsigned JamLevel, bool Sequentialized, Dependence *D)
 
static bool partitionOuterLoopBlocks(Loop &Root, Loop &JamLoop, BasicBlockSet &JamLoopBlocks, DenseMap< Loop *, BasicBlockSet > &ForeBlocksMap, DenseMap< Loop *, BasicBlockSet > &AftBlocksMap, DominatorTree &DT)
Partition blocks in a loop nest into blocks before and after each inner loop.
 
static bool isEligibleLoopForm(const Loop &Root)
 
static bool preservesBackwardDependence(Instruction *Src, Instruction *Dst, unsigned UnrollLevel, unsigned JamLevel, bool Sequentialized, Dependence *D)
 
static bool checkDependencies(Loop &Root, const BasicBlockSet &SubLoopBlocks, const DenseMap< Loop *, BasicBlockSet > &ForeBlocksMap, const DenseMap< Loop *, BasicBlockSet > &AftBlocksMap, DependenceInfo &DI, LoopInfo &LI)
 
static bool processHeaderPhiOperands(BasicBlock *Header, BasicBlock *Latch, BasicBlockSet &AftBlocks, T Visit)
 
static bool checkDependency(Instruction *Src, Instruction *Dst, unsigned UnrollLevel, unsigned JamLevel, bool Sequentialized, DependenceInfo &DI)
 
Contains a collection of routines for determining if a given instruction is guaranteed to execute if ...
 
uint64_t IntrinsicInst * II
 
This file defines the SmallPtrSet 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)
 
A cache of @llvm.assume calls within a function.
 
LLVM_ABI void registerAssumption(AssumeInst *CI)
Add an @llvm.assume intrinsic to this function's cache.
 
LLVM Basic Block Representation.
 
InstListType::iterator iterator
Instruction iterators...
 
const Instruction * getTerminator() const LLVM_READONLY
Returns the terminator instruction if the block is well formed or null if the block is not well forme...
 
Conditional or Unconditional Branch instruction.
 
unsigned getNumSuccessors() const
 
static BranchInst * Create(BasicBlock *IfTrue, InsertPosition InsertBefore=nullptr)
 
BasicBlock * getSuccessor(unsigned i) const
 
bool isUnconditional() const
 
void setSuccessor(unsigned idx, BasicBlock *NewSucc)
 
ValueT lookup(const_arg_type_t< KeyT > Val) const
lookup - Return the entry for the specified key, or a default constructed value if no such entry exis...
 
bool contains(const_arg_type_t< KeyT > Val) const
Return true if the specified key is in the map, false otherwise.
 
DependenceInfo - This class is the main dependence-analysis driver.
 
LLVM_ABI std::unique_ptr< Dependence > depends(Instruction *Src, Instruction *Dst, bool UnderRuntimeAssumptions=false)
depends - Tests for a dependence between the Src and Dst instructions.
 
Dependence - This class represents a dependence between two memory memory references in a function.
 
DomTreeNodeBase * getIDom() const
 
bool verify(VerificationLevel VL=VerificationLevel::Full) const
verify - checks if the tree is correct.
 
DomTreeNodeBase< NodeT > * addNewBlock(NodeT *BB, NodeT *DomBB)
Add a new node to the dominator tree information.
 
DomTreeNodeBase< NodeT > * getNode(const NodeT *BB) const
getNode - return the (Post)DominatorTree node for the specified basic block.
 
Concrete subclass of DominatorTreeBase that is used to compute a normal dominator tree.
 
LLVM_ABI bool dominates(const BasicBlock *BB, const Use &U) const
Return true if the (end of the) basic block BB dominates the use U.
 
DomTreeT & getDomTree()
Flush DomTree updates and return DomTree.
 
void applyUpdatesPermissive(ArrayRef< UpdateT > Updates)
Submit updates to all available trees.
 
LLVM_ABI InstListType::iterator eraseFromParent()
This method unlinks 'this' from the containing basic block and deletes it.
 
LLVM_ABI BasicBlock * getSuccessor(unsigned Idx) const LLVM_READONLY
Return the specified successor. This instruction must be a terminator.
 
bool contains(const LoopT *L) const
Return true if the specified loop is contained within in this loop.
 
BlockT * getLoopLatch() const
If there is a single latch block for this loop, return it.
 
SmallVector< const LoopT *, 4 > getLoopsInPreorder() const
Return all loops in the loop nest rooted by the loop in preorder, with siblings in forward program or...
 
const std::vector< LoopT * > & getSubLoops() const
Return the loops contained entirely within this loop.
 
BlockT * getHeader() const
 
unsigned getLoopDepth() const
Return the nesting level of this loop.
 
iterator_range< block_iterator > blocks() const
 
BlockT * getExitBlock() const
If getExitBlocks would return exactly one block, return that block.
 
BlockT * getLoopPreheader() const
If there is a preheader for this loop, return it.
 
BlockT * getExitingBlock() const
If getExitingBlocks would return exactly one block, return that block.
 
LoopT * getParentLoop() const
Return the parent loop if it exists or nullptr for top level loops.
 
Store the result of a depth first search within basic blocks contained by a single loop.
 
RPOIterator beginRPO() const
Reverse iterate over the cached postorder blocks.
 
std::vector< BasicBlock * >::const_reverse_iterator RPOIterator
 
void perform(const LoopInfo *LI)
Traverse the loop blocks and store the DFS result.
 
RPOIterator endRPO() const
 
void verify(const DominatorTreeBase< BlockT, false > &DomTree) const
 
LoopT * getLoopFor(const BlockT *BB) const
Return the inner most loop that BB lives in.
 
LLVM_ABI void erase(Loop *L)
Update LoopInfo after removing the last backedge from a loop.
 
Represents a single loop in the control flow graph.
 
bool isLoopSimplifyForm() const
Return true if the Loop is in the form that the LoopSimplify form transforms loops to,...
 
bool isRecursivelyLCSSAForm(const DominatorTree &DT, const LoopInfo &LI, bool IgnoreTokens=true) const
Return true if this Loop and all inner subloops are in LCSSA form.
 
The main scalar evolution driver.
 
LLVM_ABI void forgetLoop(const Loop *L)
This method should be called by the client when it has changed a loop in a way that may effect Scalar...
 
LLVM_ABI void forgetBlockAndLoopDispositions(Value *V=nullptr)
Called when the client has changed the disposition of values in a loop or block.
 
LLVM_ABI void verify() const
 
Simple and conservative implementation of LoopSafetyInfo that can give false-positive answers to its ...
 
void computeLoopSafetyInfo(const Loop *CurLoop) override
Computes safety information for a loop checks loop body & header for the possibility of may throw exc...
 
bool anyBlockMayThrow() const override
Returns true iff any block of the loop for which this info is contains an instruction that may throw ...
 
size_type count(ConstPtrType Ptr) const
count - Return 1 if the specified pointer is in the set, 0 otherwise.
 
void insert_range(Range &&R)
 
std::pair< iterator, bool > insert(PtrType Ptr)
Inserts Ptr if and only if there is no element in the container equal to Ptr.
 
SmallPtrSet - This class implements a set which is optimized for holding SmallSize or less elements.
 
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.
 
Twine - A lightweight data structure for efficiently representing the concatenation of temporary valu...
 
ValueMapIteratorImpl< MapT, const Value *, false > iterator
 
LLVM Value Representation.
 
self_iterator getIterator()
 
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
 
Add a small namespace to avoid name clashes with the classes used in the streaming interface.
 
This is an optimization pass for GlobalISel generic memory operations.
 
LLVM_ABI bool isSafeToUnrollAndJam(Loop *L, ScalarEvolution &SE, DominatorTree &DT, DependenceInfo &DI, LoopInfo &LI)
 
LLVM_ABI void simplifyLoopAfterUnroll(Loop *L, bool SimplifyIVs, LoopInfo *LI, ScalarEvolution *SE, DominatorTree *DT, AssumptionCache *AC, const TargetTransformInfo *TTI, AAResults *AA=nullptr)
Perform some cleanup and simplifications on loops after unrolling.
 
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.
 
LLVM_ABI BasicBlock * CloneBasicBlock(const BasicBlock *BB, ValueToValueMapTy &VMap, const Twine &NameSuffix="", Function *F=nullptr, ClonedCodeInfo *CodeInfo=nullptr, bool MapAtoms=true)
Return a copy of the specified basic block, but without embedding the block into a particular functio...
 
decltype(auto) dyn_cast(const From &Val)
dyn_cast<X> - Return the argument parameter cast to the specified type.
 
auto successors(const MachineBasicBlock *BB)
 
LLVM_ABI cl::opt< bool > EnableFSDiscriminator
 
bool any_of(R &&range, UnaryPredicate P)
Provide wrappers to std::any_of which take ranges instead of having to pass begin/end explicitly.
 
LLVM_ABI bool MergeBlockSuccessorsIntoGivenBlocks(SmallPtrSetImpl< BasicBlock * > &MergeBlocks, Loop *L=nullptr, DomTreeUpdater *DTU=nullptr, LoopInfo *LI=nullptr)
Merge block(s) sucessors, if possible.
 
LLVM_ABI raw_ostream & dbgs()
dbgs() - This returns a reference to a raw_ostream for debugging messages.
 
LLVM_ABI cl::opt< unsigned > SCEVCheapExpansionBudget
 
FunctionAddr VTableAddr Count
 
LoopUnrollResult
Represents the result of a UnrollLoop invocation.
 
@ PartiallyUnrolled
The loop was partially unrolled – we still have a loop, but with a smaller trip count.
 
@ Unmodified
The loop was not modified.
 
@ FullyUnrolled
The loop was fully unrolled into straight-line code.
 
bool isa(const From &Val)
isa<X> - Return true if the parameter to the template is an instance of one of the template type argu...
 
LLVM_ABI void remapInstructionsInBlocks(ArrayRef< BasicBlock * > Blocks, ValueToValueMapTy &VMap)
Remaps instructions in Blocks using the mapping in VMap.
 
ValueMap< const Value *, WeakTrackingVH > ValueToValueMapTy
 
LLVM_ABI const Loop * addClonedBlockToLoopInfo(BasicBlock *OriginalBB, BasicBlock *ClonedBB, LoopInfo *LI, NewLoopsMap &NewLoops)
Adds ClonedBB to LoopInfo, creates a new loop for ClonedBB if necessary and adds a mapping from the o...
 
decltype(auto) cast(const From &Val)
cast<X> - Return the argument parameter cast to the specified type.
 
LLVM_ABI bool UnrollRuntimeLoopRemainder(Loop *L, unsigned Count, bool AllowExpensiveTripCount, bool UseEpilogRemainder, bool UnrollRemainder, bool ForgetAllSCEV, LoopInfo *LI, ScalarEvolution *SE, DominatorTree *DT, AssumptionCache *AC, const TargetTransformInfo *TTI, bool PreserveLCSSA, unsigned SCEVExpansionBudget, bool RuntimeUnrollMultiExit, Loop **ResultLoop=nullptr, std::optional< unsigned > OriginalTripCount=std::nullopt, BranchProbability OriginalLoopProb=BranchProbability::getUnknown())
Insert code in the prolog/epilog code when unrolling a loop with a run-time trip-count.
 
LLVM_ABI LoopUnrollResult UnrollAndJamLoop(Loop *L, unsigned Count, unsigned TripCount, unsigned TripMultiple, bool UnrollRemainder, LoopInfo *LI, ScalarEvolution *SE, DominatorTree *DT, AssumptionCache *AC, const TargetTransformInfo *TTI, OptimizationRemarkEmitter *ORE, Loop **EpilogueLoop=nullptr)