annotate clang/test/CodeGenCXX/global-init.cpp @ 206:f17a3b42b08b

Added tag before-12 for changeset b7591485f4cd
author Shinji KONO <kono@ie.u-ryukyu.ac.jp>
date Mon, 07 Jun 2021 21:25:57 +0900
parents 1d019706d866
children 2e18cbf3894f
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
150
anatofuz
parents:
diff changeset
1 // RUN: %clang_cc1 -triple=x86_64-apple-darwin10 -emit-llvm -fexceptions %s -o - |FileCheck %s
anatofuz
parents:
diff changeset
2 // RUN: %clang_cc1 -triple=x86_64-apple-darwin10 -emit-llvm %s -o - |FileCheck -check-prefix CHECK-NOEXC %s
anatofuz
parents:
diff changeset
3 // RUN: %clang_cc1 -triple=x86_64-apple-darwin10 -emit-llvm -mframe-pointer=non-leaf %s -o - \
anatofuz
parents:
diff changeset
4 // RUN: | FileCheck -check-prefix CHECK-FP %s
anatofuz
parents:
diff changeset
5 // RUN: %clang_cc1 -triple=x86_64-apple-darwin10 -emit-llvm %s -o - -fno-builtin \
anatofuz
parents:
diff changeset
6 // RUN: | FileCheck -check-prefix CHECK-NOBUILTIN %s
anatofuz
parents:
diff changeset
7
anatofuz
parents:
diff changeset
8 struct A {
anatofuz
parents:
diff changeset
9 A();
anatofuz
parents:
diff changeset
10 ~A();
anatofuz
parents:
diff changeset
11 };
anatofuz
parents:
diff changeset
12
anatofuz
parents:
diff changeset
13 struct B { B(); ~B(); };
anatofuz
parents:
diff changeset
14
anatofuz
parents:
diff changeset
15 struct C { void *field; };
anatofuz
parents:
diff changeset
16
anatofuz
parents:
diff changeset
17 struct D { ~D(); };
anatofuz
parents:
diff changeset
18
anatofuz
parents:
diff changeset
19 // CHECK: @__dso_handle = external hidden global i8
anatofuz
parents:
diff changeset
20 // CHECK: @c = global %struct.C zeroinitializer, align 8
anatofuz
parents:
diff changeset
21
anatofuz
parents:
diff changeset
22 // PR6205: The casts should not require global initializers
anatofuz
parents:
diff changeset
23 // CHECK: @_ZN6PR59741cE = external global %"struct.PR5974::C"
anatofuz
parents:
diff changeset
24 // CHECK: @_ZN6PR59741aE = global %"struct.PR5974::A"* getelementptr inbounds (%"struct.PR5974::C", %"struct.PR5974::C"* @_ZN6PR59741cE, i32 0, i32 0)
anatofuz
parents:
diff changeset
25 // CHECK: @_ZN6PR59741bE = global %"struct.PR5974::B"* bitcast (i8* getelementptr (i8, i8* bitcast (%"struct.PR5974::C"* @_ZN6PR59741cE to i8*), i64 4) to %"struct.PR5974::B"*), align 8
anatofuz
parents:
diff changeset
26
anatofuz
parents:
diff changeset
27 // CHECK: call void @_ZN1AC1Ev(%struct.A* @a)
anatofuz
parents:
diff changeset
28 // CHECK: call i32 @__cxa_atexit(void (i8*)* bitcast (void (%struct.A*)* @_ZN1AD1Ev to void (i8*)*), i8* getelementptr inbounds (%struct.A, %struct.A* @a, i32 0, i32 0), i8* @__dso_handle)
anatofuz
parents:
diff changeset
29 A a;
anatofuz
parents:
diff changeset
30
anatofuz
parents:
diff changeset
31 // CHECK: call void @_ZN1BC1Ev(%struct.B* @b)
anatofuz
parents:
diff changeset
32 // CHECK: call i32 @__cxa_atexit(void (i8*)* bitcast (void (%struct.B*)* @_ZN1BD1Ev to void (i8*)*), i8* getelementptr inbounds (%struct.B, %struct.B* @b, i32 0, i32 0), i8* @__dso_handle)
anatofuz
parents:
diff changeset
33 B b;
anatofuz
parents:
diff changeset
34
anatofuz
parents:
diff changeset
35 // PR6205: this should not require a global initializer
anatofuz
parents:
diff changeset
36 // CHECK-NOT: call void @_ZN1CC1Ev(%struct.C* @c)
anatofuz
parents:
diff changeset
37 C c;
anatofuz
parents:
diff changeset
38
anatofuz
parents:
diff changeset
39 // CHECK: call i32 @__cxa_atexit(void (i8*)* bitcast (void (%struct.D*)* @_ZN1DD1Ev to void (i8*)*), i8* getelementptr inbounds (%struct.D, %struct.D* @d, i32 0, i32 0), i8* @__dso_handle)
anatofuz
parents:
diff changeset
40 D d;
anatofuz
parents:
diff changeset
41
anatofuz
parents:
diff changeset
42 // <rdar://problem/7458115>
anatofuz
parents:
diff changeset
43 namespace test1 {
anatofuz
parents:
diff changeset
44 int f();
anatofuz
parents:
diff changeset
45 const int x = f(); // This has side-effects and gets emitted immediately.
anatofuz
parents:
diff changeset
46 const int y = x - 1; // This gets deferred.
anatofuz
parents:
diff changeset
47 const int z = ~y; // This also gets deferred, but gets "undeferred" before y.
anatofuz
parents:
diff changeset
48 int test() { return z; }
anatofuz
parents:
diff changeset
49 // CHECK-LABEL: define i32 @_ZN5test14testEv()
anatofuz
parents:
diff changeset
50
anatofuz
parents:
diff changeset
51 // All of these initializers end up delayed, so we check them later.
anatofuz
parents:
diff changeset
52 }
anatofuz
parents:
diff changeset
53
anatofuz
parents:
diff changeset
54 // <rdar://problem/8246444>
anatofuz
parents:
diff changeset
55 namespace test2 {
anatofuz
parents:
diff changeset
56 struct allocator { allocator(); ~allocator(); };
anatofuz
parents:
diff changeset
57 struct A { A(const allocator &a = allocator()); ~A(); };
anatofuz
parents:
diff changeset
58
anatofuz
parents:
diff changeset
59 A a;
anatofuz
parents:
diff changeset
60 // CHECK: call void @_ZN5test29allocatorC1Ev(
anatofuz
parents:
diff changeset
61 // CHECK: invoke void @_ZN5test21AC1ERKNS_9allocatorE(
anatofuz
parents:
diff changeset
62 // CHECK: call void @_ZN5test29allocatorD1Ev(
anatofuz
parents:
diff changeset
63 // CHECK: call i32 @__cxa_atexit({{.*}} @_ZN5test21AD1Ev {{.*}} @_ZN5test21aE
anatofuz
parents:
diff changeset
64 }
anatofuz
parents:
diff changeset
65
anatofuz
parents:
diff changeset
66 namespace test3 {
anatofuz
parents:
diff changeset
67 // Tested at the beginning of the file.
anatofuz
parents:
diff changeset
68 const char * const var = "string";
anatofuz
parents:
diff changeset
69 extern const char * const var;
anatofuz
parents:
diff changeset
70
anatofuz
parents:
diff changeset
71 const char *test() { return var; }
anatofuz
parents:
diff changeset
72 }
anatofuz
parents:
diff changeset
73
anatofuz
parents:
diff changeset
74 namespace test4 {
anatofuz
parents:
diff changeset
75 struct A {
anatofuz
parents:
diff changeset
76 A();
anatofuz
parents:
diff changeset
77 };
anatofuz
parents:
diff changeset
78 extern int foo();
anatofuz
parents:
diff changeset
79
anatofuz
parents:
diff changeset
80 // This needs an initialization function and guard variables.
anatofuz
parents:
diff changeset
81 // CHECK: load i8, i8* bitcast (i64* @_ZGVN5test41xE
anatofuz
parents:
diff changeset
82 // CHECK: [[CALL:%.*]] = call i32 @_ZN5test43fooEv
anatofuz
parents:
diff changeset
83 // CHECK-NEXT: store i32 [[CALL]], i32* @_ZN5test41xE
anatofuz
parents:
diff changeset
84 // CHECK-NEXT: store i64 1, i64* @_ZGVN5test41xE
anatofuz
parents:
diff changeset
85 __attribute__((weak)) int x = foo();
anatofuz
parents:
diff changeset
86 }
anatofuz
parents:
diff changeset
87
anatofuz
parents:
diff changeset
88 namespace PR5974 {
anatofuz
parents:
diff changeset
89 struct A { int a; };
anatofuz
parents:
diff changeset
90 struct B { int b; };
anatofuz
parents:
diff changeset
91 struct C : A, B { int c; };
anatofuz
parents:
diff changeset
92
anatofuz
parents:
diff changeset
93 extern C c;
anatofuz
parents:
diff changeset
94
anatofuz
parents:
diff changeset
95 // These should not require global initializers.
anatofuz
parents:
diff changeset
96 A* a = &c;
anatofuz
parents:
diff changeset
97 B* b = &c;
anatofuz
parents:
diff changeset
98 }
anatofuz
parents:
diff changeset
99
anatofuz
parents:
diff changeset
100 // PR9570: the indirect field shouldn't crash IR gen.
anatofuz
parents:
diff changeset
101 namespace test5 {
anatofuz
parents:
diff changeset
102 static union {
anatofuz
parents:
diff changeset
103 unsigned bar[4096] __attribute__((aligned(128)));
anatofuz
parents:
diff changeset
104 };
anatofuz
parents:
diff changeset
105 }
anatofuz
parents:
diff changeset
106
anatofuz
parents:
diff changeset
107 namespace std { struct type_info; }
anatofuz
parents:
diff changeset
108
anatofuz
parents:
diff changeset
109 namespace test6 {
anatofuz
parents:
diff changeset
110 struct A { virtual ~A(); };
anatofuz
parents:
diff changeset
111 struct B : A {};
anatofuz
parents:
diff changeset
112 extern A *p;
anatofuz
parents:
diff changeset
113
anatofuz
parents:
diff changeset
114 // We must emit a dynamic initializer for 'q', because it could throw.
anatofuz
parents:
diff changeset
115 B *const q = &dynamic_cast<B&>(*p);
anatofuz
parents:
diff changeset
116 // CHECK: call void @__cxa_bad_cast()
anatofuz
parents:
diff changeset
117 // CHECK: store {{.*}} @_ZN5test6L1qE
anatofuz
parents:
diff changeset
118
anatofuz
parents:
diff changeset
119 // We don't need to emit 'r' at all, because it has internal linkage, is
anatofuz
parents:
diff changeset
120 // unused, and its initialization has no side-effects.
anatofuz
parents:
diff changeset
121 B *const r = dynamic_cast<B*>(p);
anatofuz
parents:
diff changeset
122 // CHECK-NOT: call void @__cxa_bad_cast()
anatofuz
parents:
diff changeset
123 // CHECK-NOT: store {{.*}} @_ZN5test6L1rE
anatofuz
parents:
diff changeset
124
anatofuz
parents:
diff changeset
125 // This can throw, so we need to emit it.
anatofuz
parents:
diff changeset
126 const std::type_info *const s = &typeid(*p);
anatofuz
parents:
diff changeset
127 // CHECK: store {{.*}} @_ZN5test6L1sE
anatofuz
parents:
diff changeset
128
anatofuz
parents:
diff changeset
129 // This can't throw, so we don't.
anatofuz
parents:
diff changeset
130 const std::type_info *const t = &typeid(p);
anatofuz
parents:
diff changeset
131 // CHECK-NOT: @_ZN5test6L1tE
anatofuz
parents:
diff changeset
132
anatofuz
parents:
diff changeset
133 extern B *volatile v;
anatofuz
parents:
diff changeset
134 // CHECK: store {{.*}} @_ZN5test6L1wE
anatofuz
parents:
diff changeset
135 B *const w = dynamic_cast<B*>(v);
anatofuz
parents:
diff changeset
136
anatofuz
parents:
diff changeset
137 // CHECK: load volatile
anatofuz
parents:
diff changeset
138 // CHECK: store {{.*}} @_ZN5test6L1xE
anatofuz
parents:
diff changeset
139 const int x = *(volatile int*)0x1234;
anatofuz
parents:
diff changeset
140
anatofuz
parents:
diff changeset
141 namespace {
anatofuz
parents:
diff changeset
142 int a = int();
anatofuz
parents:
diff changeset
143 volatile int b = int();
anatofuz
parents:
diff changeset
144 int c = a;
anatofuz
parents:
diff changeset
145 int d = b;
anatofuz
parents:
diff changeset
146 // CHECK-NOT: store {{.*}} @_ZN5test6{{[A-Za-z0-9_]*}}1aE
anatofuz
parents:
diff changeset
147 // CHECK-NOT: store {{.*}} @_ZN5test6{{[A-Za-z0-9_]*}}1bE
anatofuz
parents:
diff changeset
148 // CHECK-NOT: store {{.*}} @_ZN5test6{{[A-Za-z0-9_]*}}1cE
anatofuz
parents:
diff changeset
149 // CHECK: load volatile {{.*}} @_ZN5test6{{[A-Za-z0-9_]*}}1bE
anatofuz
parents:
diff changeset
150 // CHECK: store {{.*}} @_ZN5test6{{[A-Za-z0-9_]*}}1dE
anatofuz
parents:
diff changeset
151 }
anatofuz
parents:
diff changeset
152 }
anatofuz
parents:
diff changeset
153
anatofuz
parents:
diff changeset
154 namespace test7 {
anatofuz
parents:
diff changeset
155 struct A { A(); };
anatofuz
parents:
diff changeset
156 struct B { ~B(); int n; };
anatofuz
parents:
diff changeset
157 struct C { C() = default; C(const C&); int n; };
anatofuz
parents:
diff changeset
158 struct D {};
anatofuz
parents:
diff changeset
159
anatofuz
parents:
diff changeset
160 // CHECK: call void @_ZN5test71AC1Ev({{.*}}@_ZN5test7L1aE)
anatofuz
parents:
diff changeset
161 const A a = A();
anatofuz
parents:
diff changeset
162
anatofuz
parents:
diff changeset
163 // CHECK: call i32 @__cxa_atexit({{.*}} @_ZN5test71BD1Ev{{.*}} @_ZN5test7L2b1E
anatofuz
parents:
diff changeset
164 // CHECK: call i32 @__cxa_atexit({{.*}} @_ZN5test71BD1Ev{{.*}} @_ZGRN5test72b2E
anatofuz
parents:
diff changeset
165 // CHECK: call void @_ZN5test71BD1Ev(
anatofuz
parents:
diff changeset
166 // CHECK: store {{.*}} @_ZN5test7L2b3E
anatofuz
parents:
diff changeset
167 const B b1 = B();
anatofuz
parents:
diff changeset
168 const B &b2 = B();
anatofuz
parents:
diff changeset
169 const int b3 = B().n;
anatofuz
parents:
diff changeset
170
anatofuz
parents:
diff changeset
171 // CHECK-NOT: @_ZN5test7L2c1E
anatofuz
parents:
diff changeset
172 // CHECK: call void @llvm.memset{{.*}} @_ZN5test7L2c1E
anatofuz
parents:
diff changeset
173 // CHECK-NOT: @_ZN5test7L2c1E
anatofuz
parents:
diff changeset
174 // CHECK: @_ZN5test7L2c2E
anatofuz
parents:
diff changeset
175 // CHECK-NOT: @_ZN5test7L2c3E
anatofuz
parents:
diff changeset
176 // CHECK: @_ZN5test7L2c4E
anatofuz
parents:
diff changeset
177 const C c1 = C();
anatofuz
parents:
diff changeset
178 const C c2 = static_cast<const C&>(C());
anatofuz
parents:
diff changeset
179 const int c3 = C().n;
anatofuz
parents:
diff changeset
180 const int c4 = C(C()).n;
anatofuz
parents:
diff changeset
181
anatofuz
parents:
diff changeset
182 // CHECK-NOT: @_ZN5test7L1dE
anatofuz
parents:
diff changeset
183 const D d = D();
anatofuz
parents:
diff changeset
184
anatofuz
parents:
diff changeset
185 // CHECK: store {{.*}} @_ZN5test71eE
anatofuz
parents:
diff changeset
186 int f(), e = f();
anatofuz
parents:
diff changeset
187 }
anatofuz
parents:
diff changeset
188
anatofuz
parents:
diff changeset
189
anatofuz
parents:
diff changeset
190 // At the end of the file, we check that y is initialized before z.
anatofuz
parents:
diff changeset
191
anatofuz
parents:
diff changeset
192 // CHECK: define internal void [[TEST1_Z_INIT:@.*]]()
anatofuz
parents:
diff changeset
193 // CHECK: load i32, i32* @_ZN5test1L1yE
anatofuz
parents:
diff changeset
194 // CHECK-NEXT: xor
anatofuz
parents:
diff changeset
195 // CHECK-NEXT: store i32 {{.*}}, i32* @_ZN5test1L1zE
anatofuz
parents:
diff changeset
196 // CHECK: define internal void [[TEST1_Y_INIT:@.*]]()
anatofuz
parents:
diff changeset
197 // CHECK: load i32, i32* @_ZN5test1L1xE
anatofuz
parents:
diff changeset
198 // CHECK-NEXT: sub
anatofuz
parents:
diff changeset
199 // CHECK-NEXT: store i32 {{.*}}, i32* @_ZN5test1L1yE
anatofuz
parents:
diff changeset
200
anatofuz
parents:
diff changeset
201 // CHECK: define internal void @_GLOBAL__sub_I_global_init.cpp() #{{[0-9]+}} section "__TEXT,__StaticInit,regular,pure_instructions" {
anatofuz
parents:
diff changeset
202 // CHECK: call void [[TEST1_Y_INIT]]
anatofuz
parents:
diff changeset
203 // CHECK: call void [[TEST1_Z_INIT]]
anatofuz
parents:
diff changeset
204
anatofuz
parents:
diff changeset
205 // rdar://problem/8090834: this should be nounwind
anatofuz
parents:
diff changeset
206 // CHECK-NOEXC: define internal void @_GLOBAL__sub_I_global_init.cpp() [[NUW:#[0-9]+]] section "__TEXT,__StaticInit,regular,pure_instructions" {
anatofuz
parents:
diff changeset
207 // CHECK-NOEXC: attributes [[NUW]] = { noinline nounwind{{.*}} }
anatofuz
parents:
diff changeset
208
anatofuz
parents:
diff changeset
209 // Make sure we mark global initializers with the no-builtins attribute.
anatofuz
parents:
diff changeset
210 // CHECK-NOBUILTIN: define internal void @_GLOBAL__sub_I_global_init.cpp() [[NUW:#[0-9]+]] section "__TEXT,__StaticInit,regular,pure_instructions" {
anatofuz
parents:
diff changeset
211 // CHECK-NOBUILTIN: attributes [[NUW]] = { noinline nounwind{{.*}}"no-builtins"{{.*}} }
anatofuz
parents:
diff changeset
212
anatofuz
parents:
diff changeset
213 // PR21811: attach the appropriate attribute to the global init function
anatofuz
parents:
diff changeset
214 // CHECK-FP: define internal void @_GLOBAL__sub_I_global_init.cpp() [[NUX:#[0-9]+]] section "__TEXT,__StaticInit,regular,pure_instructions" {
anatofuz
parents:
diff changeset
215 // CHECK-FP: attributes [[NUX]] = { noinline nounwind {{.*}}"frame-pointer"="non-leaf"{{.*}} }