xref: /llvm-project/clang/test/Analysis/nonreturn-destructors-cfg-output.cpp (revision d937836ead34030f4ac016a8eb8a179bd5be10f3)
1 // RUN: %clang_analyze_cc1 -std=c++11 -fcxx-exceptions -fexceptions -analyzer-checker=debug.DumpCFG -analyzer-config cfg-rich-constructors=true,cfg-implicit-dtors=true,cfg-lifetime=true,cfg-scopes=true %s > %t 2>&1
2 // RUN: FileCheck --input-file=%t -check-prefixes=CHECK %s
3 
4 class A {
5 public:
6   int x;
7   [[noreturn]] ~A();
8 };
9 
10 void foo();
11 extern const bool UV;
12 
13 // CHECK:       [B3 (ENTRY)]
14 // CHECK-NEXT:    Succs (1): B2
15 //
16 // CHECK:       [B1]
17 // CHECK-NEXT:    1: CFGScopeEnd(a)
18 // CHECK-NEXT:    2: foo
19 // CHECK-NEXT:    3: [B1.2] (ImplicitCastExpr, FunctionToPointerDecay, void (*)(void))
20 // CHECK-NEXT:    4: [B1.3]()
21 // CHECK-NEXT:    Succs (1): B0
22 //
23 // CHECK:       [B2 (NORETURN)]
24 // CHECK-NEXT:    1: CFGScopeBegin(a)
25 // CHECK-NEXT:    2:  (CXXConstructExpr, [B2.3], A)
26 // CHECK-NEXT:    3: A a;
27 // CHECK-NEXT:    4: [B2.3].~A() (Implicit destructor)
28 // CHECK-NEXT:    5: [B2.3] (Lifetime ends)
29 // CHECK-NEXT:    Preds (1): B3
30 // CHECK-NEXT:    Succs (1): B0
31 //
32 // CHECK:       [B0 (EXIT)]
33 // CHECK-NEXT:    Preds (2): B1 B2
test_single_decl()34 void test_single_decl() {
35   {
36     A a;
37   }
38   foo();
39 }
40 
41 // CHECK:       [B6 (ENTRY)]
42 // CHECK-NEXT:    Succs (1): B5
43 //
44 // CHECK:       [B1]
45 // CHECK-NEXT:   label:
46 // CHECK-NEXT:    1: foo
47 // CHECK-NEXT:    2: [B1.1] (ImplicitCastExpr, FunctionToPointerDecay, void (*)(void))
48 // CHECK-NEXT:    3: [B1.2]()
49 // CHECK-NEXT:    Preds (4): B2 B3(Unreachable) B4 B5(Unreachable)
50 // CHECK-NEXT:    Succs (1): B0
51 //
52 // CHECK:       [B2]
53 // CHECK-NEXT:    1: CFGScopeEnd(a)
54 // CHECK-NEXT:    Succs (1): B1
55 //
56 // CHECK:       [B3 (NORETURN)]
57 // CHECK-NEXT:    1: [B5.3].~A() (Implicit destructor)
58 // CHECK-NEXT:    2: [B5.3] (Lifetime ends)
59 // CHECK-NEXT:    Succs (1): B0
60 //
61 // CHECK:       [B4]
62 // CHECK-NEXT:    1: CFGScopeEnd(a)
63 // CHECK-NEXT:    T: goto label;
64 // CHECK-NEXT:    Succs (1): B1
65 //
66 // CHECK:       [B5 (NORETURN)]
67 // CHECK-NEXT:    1: CFGScopeBegin(a)
68 // CHECK-NEXT:    2:  (CXXConstructExpr, [B5.3], A)
69 // CHECK-NEXT:    3: A a;
70 // CHECK-NEXT:    4: [B5.3].~A() (Implicit destructor)
71 // CHECK-NEXT:    5: [B5.3] (Lifetime ends)
72 // CHECK-NEXT:    Preds (1): B6
73 // CHECK-NEXT:    Succs (1): B0
74 //
75 // CHECK:       [B0 (EXIT)]
76 // CHECK-NEXT:    Preds (3): B1 B3 B5
test_forward_goto()77 void test_forward_goto() {
78   {
79     A a;
80     goto label;
81   }
82 label:
83   foo();
84 }
85 
86 
87 // The blocks B3 and B5, are inserted during backpatching goto stmt, to handle
88 // scope changes.
89 // CHECK:       [B6 (ENTRY)]
90 // CHECK-NEXT:    Succs (1): B3
91 //
92 // CHECK:       [B1]
93 // CHECK-NEXT:    1: CFGScopeEnd(a)
94 // CHECK-NEXT:    2: foo
95 // CHECK-NEXT:    3: [B1.2] (ImplicitCastExpr, FunctionToPointerDecay, void (*)(void))
96 // CHECK-NEXT:    4: [B1.3]()
97 // CHECK-NEXT:    Succs (1): B0
98 //
99 // CHECK:       [B2 (NORETURN)]
100 // CHECK-NEXT:    1: [B3.3].~A() (Implicit destructor)
101 // CHECK-NEXT:    2: [B3.3] (Lifetime ends)
102 // CHECK-NEXT:    Succs (1): B0
103 //
104 // CHECK:       [B3]
105 // CHECK-NEXT:   label:
106 // CHECK-NEXT:    1: CFGScopeBegin(a)
107 // CHECK-NEXT:    2:  (CXXConstructExpr, [B3.3], A)
108 // CHECK-NEXT:    3: A a;
109 // CHECK-NEXT:    Preds (3): B4 B5(Unreachable) B6
110 // CHECK-NEXT:    Succs (1): B5
111 //
112 // CHECK:       [B4]
113 // CHECK-NEXT:    1: CFGScopeEnd(a)
114 // CHECK-NEXT:    T: goto label;
115 // CHECK-NEXT:    Succs (1): B3
116 //
117 // CHECK:       [B5 (NORETURN)]
118 // CHECK-NEXT:    1: [B3.3].~A() (Implicit destructor)
119 // CHECK-NEXT:    2: [B3.3] (Lifetime ends)
120 // CHECK-NEXT:    Preds (1): B3
121 // CHECK-NEXT:    Succs (1): B0
122 //
123 // CHECK:       [B0 (EXIT)]
124 // CHECK-NEXT:    Preds (3): B1 B2 B5
test_backward_goto()125 void test_backward_goto() {
126 label:
127   {
128     A a;
129     goto label;
130   }
131   foo();
132 }
133