1//===- PassPrinters.cpp - Utilities to print analysis info for passes -----===// 2// 3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4// See https://llvm.org/LICENSE.txt for license information. 5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6// 7//===----------------------------------------------------------------------===// 8/// 9/// \file 10/// Utilities to print analysis info for various kinds of passes. 11/// 12//===----------------------------------------------------------------------===// 13 14#include "PassPrinters.h" 15#include "llvm/Analysis/CallGraph.h" 16#include "llvm/Analysis/CallGraphSCCPass.h" 17#include "llvm/Analysis/LoopInfo.h" 18#include "llvm/Analysis/LoopPass.h" 19#include "llvm/Analysis/RegionInfo.h" 20#include "llvm/Analysis/RegionPass.h" 21#include "llvm/IR/BasicBlock.h" 22#include "llvm/IR/Function.h" 23#include "llvm/Pass.h" 24#include "llvm/Support/raw_ostream.h" 25#include <string> 26 27using namespace llvm; 28 29namespace { 30 31struct FunctionPassPrinter : public FunctionPass { 32 const PassInfo *PassToPrint; 33 raw_ostream &Out; 34 static char ID; 35 std::string PassName; 36 37 FunctionPassPrinter(const PassInfo *PI, raw_ostream &out) 38 : FunctionPass(ID), PassToPrint(PI), Out(out) { 39 std::string PassToPrintName = std::string(PassToPrint->getPassName()); 40 PassName = "FunctionPass Printer: " + PassToPrintName; 41 } 42 43 bool runOnFunction(Function &F) override { 44 Out << "Printing analysis '" << PassToPrint->getPassName() 45 << "' for function '" << F.getName() << "':\n"; 46 47 // Get and print pass... 48 getAnalysisID<Pass>(PassToPrint->getTypeInfo()).print(Out, F.getParent()); 49 return false; 50 } 51 52 StringRef getPassName() const override { return PassName; } 53 54 void getAnalysisUsage(AnalysisUsage &AU) const override { 55 AU.addRequiredID(PassToPrint->getTypeInfo()); 56 AU.setPreservesAll(); 57 } 58}; 59 60char FunctionPassPrinter::ID = 0; 61 62struct CallGraphSCCPassPrinter : public CallGraphSCCPass { 63 static char ID; 64 const PassInfo *PassToPrint; 65 raw_ostream &Out; 66 std::string PassName; 67 68 CallGraphSCCPassPrinter(const PassInfo *PI, raw_ostream &out) 69 : CallGraphSCCPass(ID), PassToPrint(PI), Out(out) { 70 std::string PassToPrintName = std::string(PassToPrint->getPassName()); 71 PassName = "CallGraphSCCPass Printer: " + PassToPrintName; 72 } 73 74 bool runOnSCC(CallGraphSCC &SCC) override { 75 Out << "Printing analysis '" << PassToPrint->getPassName() << "':\n"; 76 77 // Get and print pass... 78 for (CallGraphSCC::iterator I = SCC.begin(), E = SCC.end(); I != E; ++I) { 79 Function *F = (*I)->getFunction(); 80 if (F) 81 getAnalysisID<Pass>(PassToPrint->getTypeInfo()) 82 .print(Out, F->getParent()); 83 } 84 return false; 85 } 86 87 StringRef getPassName() const override { return PassName; } 88 89 void getAnalysisUsage(AnalysisUsage &AU) const override { 90 AU.addRequiredID(PassToPrint->getTypeInfo()); 91 AU.setPreservesAll(); 92 } 93}; 94 95char CallGraphSCCPassPrinter::ID = 0; 96 97struct ModulePassPrinter : public ModulePass { 98 static char ID; 99 const PassInfo *PassToPrint; 100 raw_ostream &Out; 101 std::string PassName; 102 103 ModulePassPrinter(const PassInfo *PI, raw_ostream &out) 104 : ModulePass(ID), PassToPrint(PI), Out(out) { 105 std::string PassToPrintName = std::string(PassToPrint->getPassName()); 106 PassName = "ModulePass Printer: " + PassToPrintName; 107 } 108 109 bool runOnModule(Module &M) override { 110 Out << "Printing analysis '" << PassToPrint->getPassName() << "':\n"; 111 112 // Get and print pass... 113 getAnalysisID<Pass>(PassToPrint->getTypeInfo()).print(Out, &M); 114 return false; 115 } 116 117 StringRef getPassName() const override { return PassName; } 118 119 void getAnalysisUsage(AnalysisUsage &AU) const override { 120 AU.addRequiredID(PassToPrint->getTypeInfo()); 121 AU.setPreservesAll(); 122 } 123}; 124 125char ModulePassPrinter::ID = 0; 126 127struct LoopPassPrinter : public LoopPass { 128 static char ID; 129 const PassInfo *PassToPrint; 130 raw_ostream &Out; 131 std::string PassName; 132 133 LoopPassPrinter(const PassInfo *PI, raw_ostream &out) 134 : LoopPass(ID), PassToPrint(PI), Out(out) { 135 std::string PassToPrintName = std::string(PassToPrint->getPassName()); 136 PassName = "LoopPass Printer: " + PassToPrintName; 137 } 138 139 bool runOnLoop(Loop *L, LPPassManager &LPM) override { 140 Out << "Printing analysis '" << PassToPrint->getPassName() << "':\n"; 141 142 // Get and print pass... 143 getAnalysisID<Pass>(PassToPrint->getTypeInfo()) 144 .print(Out, L->getHeader()->getParent()->getParent()); 145 return false; 146 } 147 148 StringRef getPassName() const override { return PassName; } 149 150 void getAnalysisUsage(AnalysisUsage &AU) const override { 151 AU.addRequiredID(PassToPrint->getTypeInfo()); 152 AU.setPreservesAll(); 153 } 154}; 155 156char LoopPassPrinter::ID = 0; 157 158struct RegionPassPrinter : public RegionPass { 159 static char ID; 160 const PassInfo *PassToPrint; 161 raw_ostream &Out; 162 std::string PassName; 163 164 RegionPassPrinter(const PassInfo *PI, raw_ostream &out) 165 : RegionPass(ID), PassToPrint(PI), Out(out) { 166 std::string PassToPrintName = std::string(PassToPrint->getPassName()); 167 PassName = "RegionPass Printer: " + PassToPrintName; 168 } 169 170 bool runOnRegion(Region *R, RGPassManager &RGM) override { 171 Out << "Printing analysis '" << PassToPrint->getPassName() << "' for " 172 << "region: '" << R->getNameStr() << "' in function '" 173 << R->getEntry()->getParent()->getName() << "':\n"; 174 // Get and print pass... 175 getAnalysisID<Pass>(PassToPrint->getTypeInfo()) 176 .print(Out, R->getEntry()->getParent()->getParent()); 177 return false; 178 } 179 180 StringRef getPassName() const override { return PassName; } 181 182 void getAnalysisUsage(AnalysisUsage &AU) const override { 183 AU.addRequiredID(PassToPrint->getTypeInfo()); 184 AU.setPreservesAll(); 185 } 186}; 187 188char RegionPassPrinter::ID = 0; 189 190} // end anonymous namespace 191 192FunctionPass *llvm::createFunctionPassPrinter(const PassInfo *PI, 193 raw_ostream &OS) { 194 return new FunctionPassPrinter(PI, OS); 195} 196 197CallGraphSCCPass *llvm::createCallGraphPassPrinter(const PassInfo *PI, 198 raw_ostream &OS) { 199 return new CallGraphSCCPassPrinter(PI, OS); 200} 201 202ModulePass *llvm::createModulePassPrinter(const PassInfo *PI, raw_ostream &OS) { 203 return new ModulePassPrinter(PI, OS); 204} 205 206LoopPass *llvm::createLoopPassPrinter(const PassInfo *PI, raw_ostream &OS) { 207 return new LoopPassPrinter(PI, OS); 208} 209 210RegionPass *llvm::createRegionPassPrinter(const PassInfo *PI, raw_ostream &OS) { 211 return new RegionPassPrinter(PI, OS); 212} 213