1 //===--- IRPrintingPasses.cpp - Module and Function printing 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 // PrintModulePass and PrintFunctionPass implementations.
10 //
11 //===----------------------------------------------------------------------===//
12
13 #include "llvm/IR/IRPrintingPasses.h"
14 #include "llvm/IR/Function.h"
15 #include "llvm/IR/Module.h"
16 #include "llvm/IR/PassManager.h"
17 #include "llvm/InitializePasses.h"
18 #include "llvm/Pass.h"
19 #include "llvm/Support/Debug.h"
20 #include "llvm/Support/raw_ostream.h"
21 using namespace llvm;
22
PrintModulePass()23 PrintModulePass::PrintModulePass() : OS(dbgs()) {}
PrintModulePass(raw_ostream & OS,const std::string & Banner,bool ShouldPreserveUseListOrder)24 PrintModulePass::PrintModulePass(raw_ostream &OS, const std::string &Banner,
25 bool ShouldPreserveUseListOrder)
26 : OS(OS), Banner(Banner),
27 ShouldPreserveUseListOrder(ShouldPreserveUseListOrder) {}
28
run(Module & M,ModuleAnalysisManager &)29 PreservedAnalyses PrintModulePass::run(Module &M, ModuleAnalysisManager &) {
30 if (llvm::isFunctionInPrintList("*")) {
31 if (!Banner.empty())
32 OS << Banner << "\n";
33 M.print(OS, nullptr, ShouldPreserveUseListOrder);
34 }
35 else {
36 bool BannerPrinted = false;
37 for(const auto &F : M.functions()) {
38 if (llvm::isFunctionInPrintList(F.getName())) {
39 if (!BannerPrinted && !Banner.empty()) {
40 OS << Banner << "\n";
41 BannerPrinted = true;
42 }
43 F.print(OS);
44 }
45 }
46 }
47 return PreservedAnalyses::all();
48 }
49
PrintFunctionPass()50 PrintFunctionPass::PrintFunctionPass() : OS(dbgs()) {}
PrintFunctionPass(raw_ostream & OS,const std::string & Banner)51 PrintFunctionPass::PrintFunctionPass(raw_ostream &OS, const std::string &Banner)
52 : OS(OS), Banner(Banner) {}
53
run(Function & F,FunctionAnalysisManager &)54 PreservedAnalyses PrintFunctionPass::run(Function &F,
55 FunctionAnalysisManager &) {
56 if (isFunctionInPrintList(F.getName())) {
57 if (forcePrintModuleIR())
58 OS << Banner << " (function: " << F.getName() << ")\n" << *F.getParent();
59 else
60 OS << Banner << '\n' << static_cast<Value &>(F);
61 }
62 return PreservedAnalyses::all();
63 }
64
65 namespace {
66
67 class PrintModulePassWrapper : public ModulePass {
68 PrintModulePass P;
69
70 public:
71 static char ID;
PrintModulePassWrapper()72 PrintModulePassWrapper() : ModulePass(ID) {}
PrintModulePassWrapper(raw_ostream & OS,const std::string & Banner,bool ShouldPreserveUseListOrder)73 PrintModulePassWrapper(raw_ostream &OS, const std::string &Banner,
74 bool ShouldPreserveUseListOrder)
75 : ModulePass(ID), P(OS, Banner, ShouldPreserveUseListOrder) {}
76
runOnModule(Module & M)77 bool runOnModule(Module &M) override {
78 ModuleAnalysisManager DummyMAM;
79 P.run(M, DummyMAM);
80 return false;
81 }
82
getAnalysisUsage(AnalysisUsage & AU) const83 void getAnalysisUsage(AnalysisUsage &AU) const override {
84 AU.setPreservesAll();
85 }
86
getPassName() const87 StringRef getPassName() const override { return "Print Module IR"; }
88 };
89
90 class PrintFunctionPassWrapper : public FunctionPass {
91 PrintFunctionPass P;
92
93 public:
94 static char ID;
PrintFunctionPassWrapper()95 PrintFunctionPassWrapper() : FunctionPass(ID) {}
PrintFunctionPassWrapper(raw_ostream & OS,const std::string & Banner)96 PrintFunctionPassWrapper(raw_ostream &OS, const std::string &Banner)
97 : FunctionPass(ID), P(OS, Banner) {}
98
99 // This pass just prints a banner followed by the function as it's processed.
runOnFunction(Function & F)100 bool runOnFunction(Function &F) override {
101 FunctionAnalysisManager DummyFAM;
102 P.run(F, DummyFAM);
103 return false;
104 }
105
getAnalysisUsage(AnalysisUsage & AU) const106 void getAnalysisUsage(AnalysisUsage &AU) const override {
107 AU.setPreservesAll();
108 }
109
getPassName() const110 StringRef getPassName() const override { return "Print Function IR"; }
111 };
112
113 }
114
115 char PrintModulePassWrapper::ID = 0;
116 INITIALIZE_PASS(PrintModulePassWrapper, "print-module",
117 "Print module to stderr", false, true)
118 char PrintFunctionPassWrapper::ID = 0;
119 INITIALIZE_PASS(PrintFunctionPassWrapper, "print-function",
120 "Print function to stderr", false, true)
121
createPrintModulePass(llvm::raw_ostream & OS,const std::string & Banner,bool ShouldPreserveUseListOrder)122 ModulePass *llvm::createPrintModulePass(llvm::raw_ostream &OS,
123 const std::string &Banner,
124 bool ShouldPreserveUseListOrder) {
125 return new PrintModulePassWrapper(OS, Banner, ShouldPreserveUseListOrder);
126 }
127
createPrintFunctionPass(llvm::raw_ostream & OS,const std::string & Banner)128 FunctionPass *llvm::createPrintFunctionPass(llvm::raw_ostream &OS,
129 const std::string &Banner) {
130 return new PrintFunctionPassWrapper(OS, Banner);
131 }
132
isIRPrintingPass(Pass * P)133 bool llvm::isIRPrintingPass(Pass *P) {
134 const char *PID = (const char*)P->getPassID();
135
136 return (PID == &PrintModulePassWrapper::ID) ||
137 (PID == &PrintFunctionPassWrapper::ID);
138 }
139