llvm.org GIT mirror llvm / 7d160f7
IR printing improvement for function passes - introducing -print-module-scope Summary: When debugging function passes it happens to be rather useful to dump the whole module before the transformation and then use this dump to analyze this single transformation by running it separately on that particular module state. Introducing -print-module-scope debugging option that forces all the function-level IR dumps to become whole-module dumps. This option builds on top of normal dumping controls like -print-before/after -filter-print-funcs The plan is to eventually extend this option to cover other local passes (at least loop passes) but that should go as a separate change. Reviewers: sanjoy, weimingz, silvas, fedor.sergeev Reviewed By: weimingz Subscribers: apilipenko, skatkov, llvm-commits, mehdi_amini Differential Revision: https://reviews.llvm.org/D40245 git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@319561 91177308-0d34-0410-b5e6-96231b3b80d8 Fedor Sergeev 1 year, 9 months ago
4 changed file(s) with 73 addition(s) and 1 deletion(s). Raw diff Collapse all Expand all
360360 // @brief Tells if the function IR should be printed by PrinterPass.
361361 extern bool isFunctionInPrintList(StringRef FunctionName);
362362
363 /// forcePrintModuleIR - returns true if IR printing passes should
364 // be printing module IR (even for local-pass printers e.g. function-pass)
365 // to provide more context, as enabled by debugging option -print-module-scope
366 // @brief Tells if IR printer should be printing module IR
367 extern bool forcePrintModuleIR();
368
363369 } // end namespace llvm
364370
365371 // Include support files that contain important APIs commonly used by Passes,
4444 PreservedAnalyses PrintFunctionPass::run(Function &F,
4545 FunctionAnalysisManager &) {
4646 if (isFunctionInPrintList(F.getName()))
47 OS << Banner << static_cast(F);
47 if (forcePrintModuleIR())
48 OS << Banner << " (function: " << F.getName() << ")\n" << *F.getParent();
49 else
50 OS << Banner << static_cast(F);
4851 return PreservedAnalyses::all();
4952 }
5053
8181 llvm::cl::desc("Print IR after each pass"),
8282 cl::init(false), cl::Hidden);
8383
84 static cl::opt
85 PrintModuleScope("print-module-scope",
86 cl::desc("When printing IR for print-[before|after]{-all} "
87 "always print a module IR"),
88 cl::init(false));
89
8490 static cl::list
8591 PrintFuncsList("filter-print-funcs", cl::value_desc("function names"),
8692 cl::desc("Only print IR for functions whose name "
113119 static bool ShouldPrintAfterPass(const PassInfo *PI) {
114120 return PrintAfterAll || ShouldPrintBeforeOrAfterPass(PI, PrintAfter);
115121 }
122
123 bool llvm::forcePrintModuleIR() { return PrintModuleScope; }
116124
117125 bool llvm::isFunctionInPrintList(StringRef FunctionName) {
118126 static std::unordered_set PrintFuncNames(PrintFuncsList.begin(),
0 ; This test is checking basic properties of -print-module-scope options:
1 ; - dumps all the module IR at once
2 ; - all the function attributes are shown, including those of declarations
3 ; - works on top of -print-after and -filter-print-funcs
4 ;
5 ; RUN: opt < %s 2>&1 -disable-output \
6 ; RUN: -simplifycfg -print-after=simplifycfg -print-module-scope \
7 ; RUN: | FileCheck %s -check-prefix=CFG
8 ; RUN: opt < %s 2>&1 -disable-output \
9 ; RUN: -simplifycfg -print-after=simplifycfg -filter-print-funcs=foo -print-module-scope \
10 ; RUN: | FileCheck %s -check-prefix=FOO
11
12 ; CFG: IR Dump After
13 ; CFG-SAME: function: foo
14 ; CFG-NEXT: ModuleID =
15 ; CFG: define void @foo
16 ; CFG: define void @bar
17 ; CFG: declare void @baz
18 ; CFG: IR Dump After
19 ; CFG-SAME: function: bar
20 ; CFG-NEXT: ModuleID =
21 ; CFG: define void @foo
22 ; CFG: define void @bar
23 ; CFG: declare void @baz
24
25 ; FOO: IR Dump After
26 ; FOO-NOT: function: bar
27 ; FOO-SAME: function: foo
28 ; FOO-NEXT: ModuleID =
29 ; FOO: Function Attrs: nounwind ssp
30 ; FOO: define void @foo
31 ; FOO: Function Attrs: nounwind
32 ; FOO: define void @bar
33 ; FOO: Function Attrs: nounwind readnone ssp
34 ; FOO: declare void @baz
35
36 define void @foo() nounwind ssp {
37 call void @baz()
38 ret void
39 }
40
41 define void @bar() #0 {
42 ret void
43 }
44
45 declare void @baz() #1
46
47 attributes #0 = { nounwind "no-frame-pointer-elim"="true" }
48
49 attributes #1 = { nounwind readnone ssp "use-soft-float"="false" }
50 ; FOO: attributes #{{[0-9]}} = { nounwind "no-frame-pointer-elim"="true" }
51
52 ; FOO: attributes #{{[0-9]}} = { nounwind readnone ssp "use-soft-float"="false" }
53
54 ; FOO-NOT: IR Dump