LCOV - code coverage report
Current view: top level - lib/Analysis - RegionPass.cpp (source / functions) Hit Total Coverage
Test: llvm-toolchain.info Lines: 70 106 66.0 %
Date: 2018-07-13 00:08:38 Functions: 7 14 50.0 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : //===- RegionPass.cpp - Region Pass and Region Pass Manager ---------------===//
       2             : //
       3             : //                     The LLVM Compiler Infrastructure
       4             : //
       5             : // This file is distributed under the University of Illinois Open Source
       6             : // License. See LICENSE.TXT for details.
       7             : //
       8             : //===----------------------------------------------------------------------===//
       9             : //
      10             : // This file implements RegionPass and RGPassManager. All region optimization
      11             : // and transformation passes are derived from RegionPass. RGPassManager is
      12             : // responsible for managing RegionPasses.
      13             : // Most of this code has been COPIED from LoopPass.cpp
      14             : //
      15             : //===----------------------------------------------------------------------===//
      16             : #include "llvm/Analysis/RegionPass.h"
      17             : #include "llvm/IR/OptBisect.h"
      18             : #include "llvm/Support/Debug.h"
      19             : #include "llvm/Support/Timer.h"
      20             : #include "llvm/Support/raw_ostream.h"
      21             : using namespace llvm;
      22             : 
      23             : #define DEBUG_TYPE "regionpassmgr"
      24             : 
      25             : //===----------------------------------------------------------------------===//
      26             : // RGPassManager
      27             : //
      28             : 
      29             : char RGPassManager::ID = 0;
      30             : 
      31        4321 : RGPassManager::RGPassManager()
      32        4321 :   : FunctionPass(ID), PMDataManager() {
      33        4321 :   skipThisRegion = false;
      34        4321 :   redoThisRegion = false;
      35        4321 :   RI = nullptr;
      36        4321 :   CurrentRegion = nullptr;
      37        4321 : }
      38             : 
      39             : // Recurse through all subregions and all regions  into RQ.
      40       29257 : static void addRegionIntoQueue(Region &R, std::deque<Region *> &RQ) {
      41       58514 :   RQ.push_back(&R);
      42       36022 :   for (const auto &E : R)
      43        6765 :     addRegionIntoQueue(*E, RQ);
      44       29257 : }
      45             : 
      46             : /// Pass Manager itself does not invalidate any analysis info.
      47        4321 : void RGPassManager::getAnalysisUsage(AnalysisUsage &Info) const {
      48             :   Info.addRequired<RegionInfoPass>();
      49             :   Info.setPreservesAll();
      50        4321 : }
      51             : 
      52             : /// run - Execute all of the passes scheduled for execution.  Keep track of
      53             : /// whether any of the passes modifies the function, and if so, return true.
      54       22492 : bool RGPassManager::runOnFunction(Function &F) {
      55       44984 :   RI = &getAnalysis<RegionInfoPass>().getRegionInfo();
      56             :   bool Changed = false;
      57             : 
      58             :   // Collect inherited analysis from Module level pass manager.
      59       22492 :   populateInheritedAnalysis(TPM->activeStack);
      60             : 
      61       22492 :   addRegionIntoQueue(*RI->getTopLevelRegion(), RQ);
      62             : 
      63       22492 :   if (RQ.empty()) // No regions, skip calling finalizers
      64             :     return false;
      65             : 
      66             :   // Initialization
      67       51749 :   for (Region *R : RQ) {
      68      126167 :     for (unsigned Index = 0; Index < getNumContainedPasses(); ++Index) {
      69             :       RegionPass *RP = (RegionPass *)getContainedPass(Index);
      70       48455 :       Changed |= RP->doInitialization(R, *this);
      71             :     }
      72             :   }
      73             : 
      74             :   // Walk Regions
      75       51660 :   while (!RQ.empty()) {
      76             : 
      77       29213 :     CurrentRegion  = RQ.back();
      78       29213 :     skipThisRegion = false;
      79       29213 :     redoThisRegion = false;
      80             : 
      81             :     // Run all passes on the current Region.
      82      125557 :     for (unsigned Index = 0; Index < getNumContainedPasses(); ++Index) {
      83             :       RegionPass *P = (RegionPass*)getContainedPass(Index);
      84             : 
      85       48217 :       if (isPassDebuggingExecutionsOrMore()) {
      86           0 :         dumpPassInfo(P, EXECUTION_MSG, ON_REGION_MSG,
      87           0 :                      CurrentRegion->getNameStr());
      88           0 :         dumpRequiredSet(P);
      89             :       }
      90             : 
      91       48217 :       initializeAnalysisImpl(P);
      92             : 
      93             :       {
      94       96434 :         PassManagerPrettyStackEntry X(P, *CurrentRegion->getEntry());
      95             : 
      96       48217 :         TimeRegion PassTimer(getPassTimer(P));
      97       48217 :         Changed |= P->runOnRegion(CurrentRegion, *this);
      98             :       }
      99             : 
     100       48173 :       if (isPassDebuggingExecutionsOrMore()) {
     101           0 :         if (Changed)
     102           0 :           dumpPassInfo(P, MODIFICATION_MSG, ON_REGION_MSG,
     103           0 :                        skipThisRegion ? "<deleted>" :
     104           0 :                                       CurrentRegion->getNameStr());
     105           0 :         dumpPreservedSet(P);
     106             :       }
     107             : 
     108       48173 :       if (!skipThisRegion) {
     109             :         // Manually check that this region is still healthy. This is done
     110             :         // instead of relying on RegionInfo::verifyRegion since RegionInfo
     111             :         // is a function pass and it's really expensive to verify every
     112             :         // Region in the function every time. That level of checking can be
     113             :         // enabled with the -verify-region-info option.
     114             :         {
     115       48173 :           TimeRegion PassTimer(getPassTimer(P));
     116       48173 :           CurrentRegion->verifyRegion();
     117             :         }
     118             : 
     119             :         // Then call the regular verifyAnalysis functions.
     120       48172 :         verifyPreservedAnalysis(P);
     121             :       }
     122             : 
     123       48172 :       removeNotPreservedAnalysis(P);
     124       48172 :       recordAvailableAnalysis(P);
     125       48172 :       removeDeadPasses(P,
     126       96344 :                        (!isPassDebuggingExecutionsOrMore() || skipThisRegion) ?
     127           0 :                        "<deleted>" :  CurrentRegion->getNameStr(),
     128             :                        ON_REGION_MSG);
     129             : 
     130       48172 :       if (skipThisRegion)
     131             :         // Do not run other passes on this region.
     132             :         break;
     133             :     }
     134             : 
     135             :     // If the region was deleted, release all the region passes. This frees up
     136             :     // some memory, and avoids trouble with the pass manager trying to call
     137             :     // verifyAnalysis on them.
     138       29168 :     if (skipThisRegion)
     139           0 :       for (unsigned Index = 0; Index < getNumContainedPasses(); ++Index) {
     140             :         Pass *P = getContainedPass(Index);
     141           0 :         freePass(P, "<deleted>", ON_REGION_MSG);
     142             :       }
     143             : 
     144             :     // Pop the region from queue after running all passes.
     145       29168 :     RQ.pop_back();
     146             : 
     147       29168 :     if (redoThisRegion)
     148           0 :       RQ.push_back(CurrentRegion);
     149             : 
     150             :     // Free all region nodes created in region passes.
     151       29168 :     RI->clearNodeCache();
     152             :   }
     153             : 
     154             :   // Finalization
     155       78533 :   for (unsigned Index = 0; Index < getNumContainedPasses(); ++Index) {
     156             :     RegionPass *P = (RegionPass*)getContainedPass(Index);
     157       28043 :     Changed |= P->doFinalization();
     158             :   }
     159             : 
     160             :   // Print the region tree after all pass.
     161             :   LLVM_DEBUG(dbgs() << "\nRegion tree of function " << F.getName()
     162             :                     << " after all region Pass:\n";
     163             :              RI->dump(); dbgs() << "\n";);
     164             : 
     165             :   return Changed;
     166             : }
     167             : 
     168             : /// Print passes managed by this manager
     169           0 : void RGPassManager::dumpPassStructure(unsigned Offset) {
     170           0 :   errs().indent(Offset*2) << "Region Pass Manager\n";
     171           0 :   for (unsigned Index = 0; Index < getNumContainedPasses(); ++Index) {
     172             :     Pass *P = getContainedPass(Index);
     173           0 :     P->dumpPassStructure(Offset + 1);
     174           0 :     dumpLastUses(P, Offset+1);
     175             :   }
     176           0 : }
     177             : 
     178             : namespace {
     179             : //===----------------------------------------------------------------------===//
     180             : // PrintRegionPass
     181           0 : class PrintRegionPass : public RegionPass {
     182             : private:
     183             :   std::string Banner;
     184             :   raw_ostream &Out;       // raw_ostream to print on.
     185             : 
     186             : public:
     187             :   static char ID;
     188             :   PrintRegionPass(const std::string &B, raw_ostream &o)
     189           0 :       : RegionPass(ID), Banner(B), Out(o) {}
     190             : 
     191           0 :   void getAnalysisUsage(AnalysisUsage &AU) const override {
     192             :     AU.setPreservesAll();
     193           0 :   }
     194             : 
     195           0 :   bool runOnRegion(Region *R, RGPassManager &RGM) override {
     196           0 :     Out << Banner;
     197           0 :     for (const auto *BB : R->blocks()) {
     198           0 :       if (BB)
     199           0 :         BB->print(Out);
     200             :       else
     201           0 :         Out << "Printing <null> Block";
     202             :     }
     203             : 
     204           0 :     return false;
     205             :   }
     206             : 
     207           0 :   StringRef getPassName() const override { return "Print Region IR"; }
     208             : };
     209             : 
     210             : char PrintRegionPass::ID = 0;
     211             : }  //end anonymous namespace
     212             : 
     213             : //===----------------------------------------------------------------------===//
     214             : // RegionPass
     215             : 
     216             : // Check if this pass is suitable for the current RGPassManager, if
     217             : // available. This pass P is not suitable for a RGPassManager if P
     218             : // is not preserving higher level analysis info used by other
     219             : // RGPassManager passes. In such case, pop RGPassManager from the
     220             : // stack. This will force assignPassManager() to create new
     221             : // LPPassManger as expected.
     222        9491 : void RegionPass::preparePassManager(PMStack &PMS) {
     223             : 
     224             :   // Find RGPassManager
     225       18982 :   while (!PMS.empty() &&
     226        9491 :          PMS.top()->getPassManagerType() > PMT_RegionPassManager)
     227           0 :     PMS.pop();
     228             : 
     229             : 
     230             :   // If this pass is destroying high level information that is used
     231             :   // by other passes that are managed by LPM then do not insert
     232             :   // this pass in current LPM. Use new RGPassManager.
     233       13333 :   if (PMS.top()->getPassManagerType() == PMT_RegionPassManager &&
     234        3842 :     !PMS.top()->preserveHigherLevelAnalysis(this))
     235           0 :     PMS.pop();
     236        9491 : }
     237             : 
     238             : /// Assign pass manager to manage this pass.
     239        9491 : void RegionPass::assignPassManager(PMStack &PMS,
     240             :                                  PassManagerType PreferredType) {
     241             :   // Find RGPassManager
     242       18982 :   while (!PMS.empty() &&
     243        9491 :          PMS.top()->getPassManagerType() > PMT_RegionPassManager)
     244           0 :     PMS.pop();
     245             : 
     246             :   RGPassManager *RGPM;
     247             : 
     248             :   // Create new Region Pass Manager if it does not exist.
     249        9491 :   if (PMS.top()->getPassManagerType() == PMT_RegionPassManager)
     250        5170 :     RGPM = (RGPassManager*)PMS.top();
     251             :   else {
     252             : 
     253             :     assert (!PMS.empty() && "Unable to create Region Pass Manager");
     254             :     PMDataManager *PMD = PMS.top();
     255             : 
     256             :     // [1] Create new Region Pass Manager
     257        4321 :     RGPM = new RGPassManager();
     258             :     RGPM->populateInheritedAnalysis(PMS);
     259             : 
     260             :     // [2] Set up new manager's top level manager
     261        4321 :     PMTopLevelManager *TPM = PMD->getTopLevelManager();
     262        4321 :     TPM->addIndirectPassManager(RGPM);
     263             : 
     264             :     // [3] Assign manager to manage this new manager. This may create
     265             :     // and push new managers into PMS
     266        4321 :     TPM->schedulePass(RGPM);
     267             : 
     268             :     // [4] Push new manager into PMS
     269        4321 :     PMS.push(RGPM);
     270             :   }
     271             : 
     272        9491 :   RGPM->add(this);
     273        9491 : }
     274             : 
     275             : /// Get the printer pass
     276           0 : Pass *RegionPass::createPrinterPass(raw_ostream &O,
     277             :                                   const std::string &Banner) const {
     278           0 :   return new PrintRegionPass(Banner, O);
     279             : }
     280             : 
     281       12518 : bool RegionPass::skipRegion(Region &R) const {
     282       12518 :   Function &F = *R.getEntry()->getParent();
     283       12518 :   if (!F.getContext().getOptPassGate().shouldRunPass(this, R))
     284             :     return true;
     285             : 
     286       12518 :   if (F.hasFnAttribute(Attribute::OptimizeNone)) {
     287             :     // Report this only once per function.
     288             :     if (R.getEntry() == &F.getEntryBlock())
     289             :       LLVM_DEBUG(dbgs() << "Skipping pass '" << getPassName()
     290             :                         << "' on function " << F.getName() << "\n");
     291           0 :     return true;
     292             :   }
     293             :   return false;
     294             : }

Generated by: LCOV version 1.13