X-Git-Url: http://plrg.eecs.uci.edu/git/?a=blobdiff_plain;f=lib%2FAnalysis%2FRegionPrinter.cpp;h=acb218d5fea08f3e22e0a7d57c43055f09d2fd45;hb=cce49eb8a630b9c5fa187d706127a91f95bd0453;hp=2b09becaac38ca2ce403decc1d53e0f036709644;hpb=cf0db29df20d9c665da7e82bb261bdd7cf7f1b2b;p=oota-llvm.git diff --git a/lib/Analysis/RegionPrinter.cpp b/lib/Analysis/RegionPrinter.cpp index 2b09becaac3..acb218d5fea 100644 --- a/lib/Analysis/RegionPrinter.cpp +++ b/lib/Analysis/RegionPrinter.cpp @@ -20,6 +20,9 @@ #include "llvm/Support/CommandLine.h" #include "llvm/Support/Debug.h" #include "llvm/Support/raw_ostream.h" +#ifndef NDEBUG +#include "llvm/IR/LegacyPassManager.h" +#endif using namespace llvm; @@ -55,25 +58,22 @@ struct DOTGraphTraits : public DefaultDOTGraphTraits { } }; -template<> -struct DOTGraphTraits : public DOTGraphTraits { +template <> +struct DOTGraphTraits : public DOTGraphTraits { DOTGraphTraits (bool isSimple = false) : DOTGraphTraits(isSimple) {} - static std::string getGraphName(RegionInfoPass *DT) { - return "Region Graph"; - } + static std::string getGraphName(const RegionInfo *) { return "Region Graph"; } - std::string getNodeLabel(RegionNode *Node, RegionInfoPass *G) { - RegionInfo &RI = G->getRegionInfo(); - return DOTGraphTraits::getNodeLabel(Node, - reinterpret_cast(RI.getTopLevelRegion())); + std::string getNodeLabel(RegionNode *Node, RegionInfo *G) { + return DOTGraphTraits::getNodeLabel( + Node, reinterpret_cast(G->getTopLevelRegion())); } std::string getEdgeAttributes(RegionNode *srcNode, - GraphTraits::ChildIteratorType CI, RegionInfoPass *G) { - RegionInfo &RI = G->getRegionInfo(); + GraphTraits::ChildIteratorType CI, + RegionInfo *G) { RegionNode *destNode = *CI; if (srcNode->isSubRegion() || destNode->isSubRegion()) @@ -83,7 +83,7 @@ struct DOTGraphTraits : public DOTGraphTraits { BasicBlock *srcBB = srcNode->getNodeAs(); BasicBlock *destBB = destNode->getNodeAs(); - Region *R = RI.getRegionFor(destBB); + Region *R = G->getRegionFor(destBB); while (R && R->getParent()) if (R->getParent()->getEntry() == destBB) @@ -91,7 +91,7 @@ struct DOTGraphTraits : public DOTGraphTraits { else break; - if (R->getEntry() == destBB && R->contains(srcBB)) + if (R && R->getEntry() == destBB && R->contains(srcBB)) return "constraint=false"; return ""; @@ -99,8 +99,7 @@ struct DOTGraphTraits : public DOTGraphTraits { // Print the cluster of the subregions. This groups the single basic blocks // and adds a different background color for each group. - static void printRegionCluster(const Region &R, - GraphWriter &GW, + static void printRegionCluster(const Region &R, GraphWriter &GW, unsigned depth = 0) { raw_ostream &O = GW.getOStream(); O.indent(2 * depth) << "subgraph cluster_" << static_cast(&R) @@ -132,50 +131,81 @@ struct DOTGraphTraits : public DOTGraphTraits { O.indent(2 * depth) << "}\n"; } - static void addCustomGraphFeatures(const RegionInfoPass* RIP, - GraphWriter &GW) { - const RegionInfo &RI = RIP->getRegionInfo(); + static void addCustomGraphFeatures(const RegionInfo *G, + GraphWriter &GW) { raw_ostream &O = GW.getOStream(); O << "\tcolorscheme = \"paired12\"\n"; - printRegionCluster(*RI.getTopLevelRegion(), GW, 4); + printRegionCluster(*G->getTopLevelRegion(), GW, 4); } }; } //end namespace llvm namespace { +struct RegionInfoPassGraphTraits { + static RegionInfo *getGraph(RegionInfoPass *RIP) { + return &RIP->getRegionInfo(); + } +}; + +struct RegionPrinter + : public DOTGraphTraitsPrinter { + static char ID; + RegionPrinter() + : DOTGraphTraitsPrinter("reg", ID) { + initializeRegionPrinterPass(*PassRegistry::getPassRegistry()); + } +}; +char RegionPrinter::ID = 0; + +struct RegionOnlyPrinter + : public DOTGraphTraitsPrinter { + static char ID; + RegionOnlyPrinter() + : DOTGraphTraitsPrinter("reg", ID) { + initializeRegionOnlyPrinterPass(*PassRegistry::getPassRegistry()); + } +}; +char RegionOnlyPrinter::ID = 0; + struct RegionViewer - : public DOTGraphTraitsViewer { + : public DOTGraphTraitsViewer { static char ID; - RegionViewer() : DOTGraphTraitsViewer("reg", ID){ + RegionViewer() + : DOTGraphTraitsViewer("reg", ID) { initializeRegionViewerPass(*PassRegistry::getPassRegistry()); } }; char RegionViewer::ID = 0; struct RegionOnlyViewer - : public DOTGraphTraitsViewer { + : public DOTGraphTraitsViewer { static char ID; - RegionOnlyViewer() : DOTGraphTraitsViewer("regonly", ID) { + RegionOnlyViewer() + : DOTGraphTraitsViewer("regonly", ID) { initializeRegionOnlyViewerPass(*PassRegistry::getPassRegistry()); } }; char RegionOnlyViewer::ID = 0; -struct RegionPrinter - : public DOTGraphTraitsPrinter { - static char ID; - RegionPrinter() : - DOTGraphTraitsPrinter("reg", ID) { - initializeRegionPrinterPass(*PassRegistry::getPassRegistry()); - } -}; -char RegionPrinter::ID = 0; } //end anonymous namespace INITIALIZE_PASS(RegionPrinter, "dot-regions", "Print regions of function to 'dot' file", true, true) +INITIALIZE_PASS( + RegionOnlyPrinter, "dot-regions-only", + "Print regions of function to 'dot' file (with no function bodies)", true, + true) + INITIALIZE_PASS(RegionViewer, "view-regions", "View regions of function", true, true) @@ -183,24 +213,11 @@ INITIALIZE_PASS(RegionOnlyViewer, "view-regions-only", "View regions of function (with no function bodies)", true, true) -namespace { +FunctionPass *llvm::createRegionPrinterPass() { return new RegionPrinter(); } -struct RegionOnlyPrinter - : public DOTGraphTraitsPrinter { - static char ID; - RegionOnlyPrinter() : - DOTGraphTraitsPrinter("reg", ID) { - initializeRegionOnlyPrinterPass(*PassRegistry::getPassRegistry()); - } -}; - -} // namespace - -char RegionOnlyPrinter::ID = 0; -INITIALIZE_PASS(RegionOnlyPrinter, "dot-regions-only", - "Print regions of function to 'dot' file " - "(with no function bodies)", - true, true) +FunctionPass *llvm::createRegionOnlyPrinterPass() { + return new RegionOnlyPrinter(); +} FunctionPass* llvm::createRegionViewerPass() { return new RegionViewer(); @@ -210,11 +227,41 @@ FunctionPass* llvm::createRegionOnlyViewerPass() { return new RegionOnlyViewer(); } -FunctionPass* llvm::createRegionPrinterPass() { - return new RegionPrinter(); +#ifndef NDEBUG +static void viewRegionInfo(RegionInfo *RI, bool ShortNames) { + assert(RI && "Argument must be non-null"); + + llvm::Function *F = RI->getTopLevelRegion()->getEntry()->getParent(); + std::string GraphName = DOTGraphTraits::getGraphName(RI); + + llvm::ViewGraph(RI, "reg", ShortNames, + Twine(GraphName) + " for '" + F->getName() + "' function"); } -FunctionPass* llvm::createRegionOnlyPrinterPass() { - return new RegionOnlyPrinter(); +static void invokeFunctionPass(const Function *F, FunctionPass *ViewerPass) { + assert(F && "Argument must be non-null"); + assert(!F->isDeclaration() && "Function must have an implementation"); + + // The viewer and analysis passes do not modify anything, so we can safely + // remove the const qualifier + auto NonConstF = const_cast(F); + + llvm::legacy::FunctionPassManager FPM(NonConstF->getParent()); + FPM.add(ViewerPass); + FPM.doInitialization(); + FPM.run(*NonConstF); + FPM.doFinalization(); } +void llvm::viewRegion(RegionInfo *RI) { viewRegionInfo(RI, false); } + +void llvm::viewRegion(const Function *F) { + invokeFunctionPass(F, createRegionViewerPass()); +} + +void llvm::viewRegionOnly(RegionInfo *RI) { viewRegionInfo(RI, true); } + +void llvm::viewRegionOnly(const Function *F) { + invokeFunctionPass(F, createRegionOnlyViewerPass()); +} +#endif