• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // RUN: %clang_cc1 %s -triple=thumbv7-apple-darwin3.0.0-iphoneos -fno-use-cxa-atexit -target-abi apcs-gnu -emit-llvm -o - -fexceptions | FileCheck %s
2 
3 // CHECK: @_ZZN5test74testEvE1x = internal global i32 0, align 4
4 // CHECK: @_ZGVZN5test74testEvE1x = internal global i32 0
5 // CHECK: @_ZZN5test84testEvE1x = internal global [[TEST8A:.*]] zeroinitializer, align 1
6 // CHECK: @_ZGVZN5test84testEvE1x = internal global i32 0
7 
8 typedef typeof(sizeof(int)) size_t;
9 
10 class foo {
11 public:
12     foo();
13     virtual ~foo();
14 };
15 
16 class bar : public foo {
17 public:
18 	bar();
19 };
20 
21 // The global dtor needs the right calling conv with -fno-use-cxa-atexit
22 // rdar://7817590
23 // Checked at end of file.
24 bar baz;
25 
26 // Destructors and constructors must return this.
27 namespace test1 {
28   void foo();
29 
30   struct A {
Atest1::A31     A(int i) { foo(); }
~Atest1::A32     ~A() { foo(); }
bartest1::A33     void bar() { foo(); }
34   };
35 
36   // CHECK: define void @_ZN5test14testEv()
test()37   void test() {
38     // CHECK: [[AV:%.*]] = alloca [[A:%.*]], align 1
39     // CHECK: call [[A]]* @_ZN5test11AC1Ei([[A]]* [[AV]], i32 10)
40     // CHECK: invoke void @_ZN5test11A3barEv([[A]]* [[AV]])
41     // CHECK: call [[A]]* @_ZN5test11AD1Ev([[A]]* [[AV]])
42     // CHECK: ret void
43     A a = 10;
44     a.bar();
45   }
46 
47   // CHECK: define linkonce_odr [[A]]* @_ZN5test11AC1Ei([[A]]* %this, i32 %i) unnamed_addr
48   // CHECK:   [[RET:%.*]] = alloca [[A]]*, align 4
49   // CHECK:   [[THIS:%.*]] = alloca [[A]]*, align 4
50   // CHECK:   store [[A]]* {{.*}}, [[A]]** [[THIS]]
51   // CHECK:   [[THIS1:%.*]] = load [[A]]** [[THIS]]
52   // CHECK:   store [[A]]* [[THIS1]], [[A]]** [[RET]]
53   // CHECK:   call [[A]]* @_ZN5test11AC2Ei(
54   // CHECK:   [[THIS2:%.*]] = load [[A]]** [[RET]]
55   // CHECK:   ret [[A]]* [[THIS2]]
56 
57   // CHECK: define linkonce_odr [[A]]* @_ZN5test11AD1Ev([[A]]* %this) unnamed_addr
58   // CHECK:   [[RET:%.*]] = alloca [[A]]*, align 4
59   // CHECK:   [[THIS:%.*]] = alloca [[A]]*, align 4
60   // CHECK:   store [[A]]* {{.*}}, [[A]]** [[THIS]]
61   // CHECK:   [[THIS1:%.*]] = load [[A]]** [[THIS]]
62   // CHECK:   store [[A]]* [[THIS1]], [[A]]** [[RET]]
63   // CHECK:   call [[A]]* @_ZN5test11AD2Ev(
64   // CHECK:   [[THIS2:%.*]] = load [[A]]** [[RET]]
65   // CHECK:   ret [[A]]* [[THIS2]]
66 }
67 
68 // Awkward virtual cases.
69 namespace test2 {
70   void foo();
71 
72   struct A {
73     int x;
74 
75     A(int);
~Atest2::A76     virtual ~A() { foo(); }
77   };
78 
79   struct B {
80     int y;
81     int z;
82 
83     B(int);
~Btest2::B84     virtual ~B() { foo(); }
85   };
86 
87   struct C : A, virtual B {
88     int q;
89 
Ctest2::C90     C(int i) : A(i), B(i) { foo(); }
~Ctest2::C91     ~C() { foo(); }
92   };
93 
test()94   void test() {
95     C c = 10;
96   }
97 
98   // Tests at eof
99 }
100 
101 namespace test3 {
102   struct A {
103     int x;
104     ~A();
105   };
106 
a()107   void a() {
108     // CHECK: define void @_ZN5test31aEv()
109     // CHECK: call noalias i8* @_Znam(i32 48)
110     // CHECK: store i32 4
111     // CHECK: store i32 10
112     A *x = new A[10];
113   }
114 
b(int n)115   void b(int n) {
116     // CHECK: define void @_ZN5test31bEi(
117     // CHECK: [[N:%.*]] = load i32*
118     // CHECK: @llvm.umul.with.overflow.i32(i32 [[N]], i32 4)
119     // CHECK: @llvm.uadd.with.overflow.i32(i32 {{.*}}, i32 8)
120     // CHECK: [[OR:%.*]] = or i1
121     // CHECK: [[SZ:%.*]] = select i1 [[OR]]
122     // CHECK: call noalias i8* @_Znam(i32 [[SZ]])
123     // CHECK: store i32 4
124     // CHECK: store i32 [[N]]
125     A *x = new A[n];
126   }
127 
c()128   void c() {
129     // CHECK: define void @_ZN5test31cEv()
130     // CHECK: call  noalias i8* @_Znam(i32 808)
131     // CHECK: store i32 4
132     // CHECK: store i32 200
133     A (*x)[20] = new A[10][20];
134   }
135 
d(int n)136   void d(int n) {
137     // CHECK: define void @_ZN5test31dEi(
138     // CHECK: [[N:%.*]] = load i32*
139     // CHECK: @llvm.umul.with.overflow.i32(i32 [[N]], i32 80)
140     // CHECK: [[NE:%.*]] = mul i32 [[N]], 20
141     // CHECK: @llvm.uadd.with.overflow.i32(i32 {{.*}}, i32 8)
142     // CHECK: [[SZ:%.*]] = select
143     // CHECK: call noalias i8* @_Znam(i32 [[SZ]])
144     // CHECK: store i32 4
145     // CHECK: store i32 [[NE]]
146     A (*x)[20] = new A[n][20];
147   }
148 
e(A * x)149   void e(A *x) {
150     // CHECK: define void @_ZN5test31eEPNS_1AE(
151     // CHECK: icmp eq {{.*}}, null
152     // CHECK: getelementptr {{.*}}, i64 -8
153     // CHECK: getelementptr {{.*}}, i64 4
154     // CHECK: bitcast {{.*}} to i32*
155     // CHECK: load
156     // CHECK: invoke {{.*}} @_ZN5test31AD1Ev
157     // CHECK: call void @_ZdaPv
158     delete [] x;
159   }
160 
f(A (* x)[20])161   void f(A (*x)[20]) {
162     // CHECK: define void @_ZN5test31fEPA20_NS_1AE(
163     // CHECK: icmp eq {{.*}}, null
164     // CHECK: getelementptr {{.*}}, i64 -8
165     // CHECK: getelementptr {{.*}}, i64 4
166     // CHECK: bitcast {{.*}} to i32*
167     // CHECK: load
168     // CHECK: invoke {{.*}} @_ZN5test31AD1Ev
169     // CHECK: call void @_ZdaPv
170     delete [] x;
171   }
172 }
173 
174 namespace test4 {
175   struct A {
176     int x;
177     void operator delete[](void *, size_t sz);
178   };
179 
a()180   void a() {
181     // CHECK: define void @_ZN5test41aEv()
182     // CHECK: call noalias i8* @_Znam(i32 48)
183     // CHECK: store i32 4
184     // CHECK: store i32 10
185     A *x = new A[10];
186   }
187 
b(int n)188   void b(int n) {
189     // CHECK: define void @_ZN5test41bEi(
190     // CHECK: [[N:%.*]] = load i32*
191     // CHECK: @llvm.umul.with.overflow.i32(i32 [[N]], i32 4)
192     // CHECK: @llvm.uadd.with.overflow.i32(i32 {{.*}}, i32 8)
193     // CHECK: [[SZ:%.*]] = select
194     // CHECK: call noalias i8* @_Znam(i32 [[SZ]])
195     // CHECK: store i32 4
196     // CHECK: store i32 [[N]]
197     A *x = new A[n];
198   }
199 
c()200   void c() {
201     // CHECK: define void @_ZN5test41cEv()
202     // CHECK: call  noalias i8* @_Znam(i32 808)
203     // CHECK: store i32 4
204     // CHECK: store i32 200
205     A (*x)[20] = new A[10][20];
206   }
207 
d(int n)208   void d(int n) {
209     // CHECK: define void @_ZN5test41dEi(
210     // CHECK: [[N:%.*]] = load i32*
211     // CHECK: @llvm.umul.with.overflow.i32(i32 [[N]], i32 80)
212     // CHECK: [[NE:%.*]] = mul i32 [[N]], 20
213     // CHECK: @llvm.uadd.with.overflow.i32(i32 {{.*}}, i32 8)
214     // CHECK: [[SZ:%.*]] = select
215     // CHECK: call noalias i8* @_Znam(i32 [[SZ]])
216     // CHECK: store i32 4
217     // CHECK: store i32 [[NE]]
218     A (*x)[20] = new A[n][20];
219   }
220 
e(A * x)221   void e(A *x) {
222     // CHECK: define void @_ZN5test41eEPNS_1AE(
223     // CHECK: [[ALLOC:%.*]] = getelementptr inbounds {{.*}}, i64 -8
224     // CHECK: getelementptr inbounds {{.*}}, i64 4
225     // CHECK: bitcast
226     // CHECK: [[T0:%.*]] = load i32*
227     // CHECK: [[T1:%.*]] = mul i32 4, [[T0]]
228     // CHECK: [[T2:%.*]] = add i32 [[T1]], 8
229     // CHECK: call void @_ZN5test41AdaEPvm(i8* [[ALLOC]], i32 [[T2]])
230     delete [] x;
231   }
232 
f(A (* x)[20])233   void f(A (*x)[20]) {
234     // CHECK: define void @_ZN5test41fEPA20_NS_1AE(
235     // CHECK: [[ALLOC:%.*]] = getelementptr inbounds {{.*}}, i64 -8
236     // CHECK: getelementptr inbounds {{.*}}, i64 4
237     // CHECK: bitcast
238     // CHECK: [[T0:%.*]] = load i32*
239     // CHECK: [[T1:%.*]] = mul i32 4, [[T0]]
240     // CHECK: [[T2:%.*]] = add i32 [[T1]], 8
241     // CHECK: call void @_ZN5test41AdaEPvm(i8* [[ALLOC]], i32 [[T2]])
242     delete [] x;
243   }
244 }
245 
246 // <rdar://problem/8386802>: don't crash
247 namespace test5 {
248   struct A {
249     ~A();
250   };
251 
252   // CHECK: define void @_ZN5test54testEPNS_1AE
test(A * a)253   void test(A *a) {
254     // CHECK:      [[PTR:%.*]] = alloca [[A:%.*]]*, align 4
255     // CHECK-NEXT: store [[A]]* {{.*}}, [[A]]** [[PTR]], align 4
256     // CHECK-NEXT: [[TMP:%.*]] = load [[A]]** [[PTR]], align 4
257     // CHECK-NEXT: call [[A]]* @_ZN5test51AD1Ev([[A]]* [[TMP]])
258     // CHECK-NEXT: ret void
259     a->~A();
260   }
261 }
262 
263 namespace test6 {
264   struct A {
265     virtual ~A();
266   };
267 
268   // CHECK: define void @_ZN5test64testEPNS_1AE
test(A * a)269   void test(A *a) {
270     // CHECK:      [[AVAR:%.*]] = alloca [[A:%.*]]*, align 4
271     // CHECK-NEXT: store [[A]]* {{.*}}, [[A]]** [[AVAR]], align 4
272     // CHECK-NEXT: [[V:%.*]] = load [[A]]** [[AVAR]], align 4
273     // CHECK-NEXT: [[ISNULL:%.*]] = icmp eq [[A]]* [[V]], null
274     // CHECK-NEXT: br i1 [[ISNULL]]
275     // CHECK:      [[T0:%.*]] = bitcast [[A]]* [[V]] to [[A]]* ([[A]]*)***
276     // CHECK-NEXT: [[T1:%.*]] = load [[A]]* ([[A]]*)*** [[T0]]
277     // CHECK-NEXT: [[T2:%.*]] = getelementptr inbounds [[A]]* ([[A]]*)** [[T1]], i64 1
278     // CHECK-NEXT: [[T3:%.*]] = load [[A]]* ([[A]]*)** [[T2]]
279     // CHECK-NEXT: call [[A]]* [[T3]]([[A]]* [[V]])
280     // CHECK-NEXT: br label
281     // CHECK:      ret void
282     delete a;
283   }
284 }
285 
286 namespace test7 {
287   int foo();
288 
289   // Static and guard tested at top of file
290 
291   // CHECK: define void @_ZN5test74testEv()
test()292   void test() {
293     // CHECK:      [[T0:%.*]] = load i32* @_ZGVZN5test74testEvE1x
294     // CHECK-NEXT: [[T1:%.*]] = and i32 [[T0]], 1
295     // CHECK-NEXT: [[T2:%.*]] = icmp eq i32 [[T1]], 0
296     // CHECK-NEXT: br i1 [[T2]]
297     //   -> fallthrough, end
298     // CHECK:      [[T3:%.*]] = call i32 @__cxa_guard_acquire(i32* @_ZGVZN5test74testEvE1x)
299     // CHECK-NEXT: [[T4:%.*]] = icmp ne i32 [[T3]], 0
300     // CHECK-NEXT: br i1 [[T4]]
301     //   -> fallthrough, end
302     // CHECK:      [[INIT:%.*]] = invoke i32 @_ZN5test73fooEv()
303     // CHECK:      store i32 [[INIT]], i32* @_ZZN5test74testEvE1x, align 4
304     // CHECK-NEXT: call void @__cxa_guard_release(i32* @_ZGVZN5test74testEvE1x)
305     // CHECK-NEXT: br label
306     //   -> end
307     // end:
308     // CHECK:      ret void
309     static int x = foo();
310 
311     // CHECK:      call i8* @llvm.eh.exception()
312     // CHECK:      call void @__cxa_guard_abort(i32* @_ZGVZN5test74testEvE1x)
313     // CHECK:      call void @llvm.eh.resume(
314   }
315 }
316 
317 namespace test8 {
318   struct A {
319     A();
320     ~A();
321   };
322 
323   // Static and guard tested at top of file
324 
325   // CHECK: define void @_ZN5test84testEv()
test()326   void test() {
327     // CHECK:      [[T0:%.*]] = load i32* @_ZGVZN5test84testEvE1x
328     // CHECK-NEXT: [[T1:%.*]] = and i32 [[T0]], 1
329     // CHECK-NEXT: [[T2:%.*]] = icmp eq i32 [[T1]], 0
330     // CHECK-NEXT: br i1 [[T2]]
331     //   -> fallthrough, end
332     // CHECK:      [[T3:%.*]] = call i32 @__cxa_guard_acquire(i32* @_ZGVZN5test84testEvE1x)
333     // CHECK-NEXT: [[T4:%.*]] = icmp ne i32 [[T3]], 0
334     // CHECK-NEXT: br i1 [[T4]]
335     //   -> fallthrough, end
336     // CHECK:      [[INIT:%.*]] = invoke [[TEST8A]]* @_ZN5test81AC1Ev([[TEST8A]]* @_ZZN5test84testEvE1x)
337 
338     // FIXME: Here we register a global destructor that
339     // unconditionally calls the destructor.  That's what we've always
340     // done for -fno-use-cxa-atexit here, but that's really not
341     // semantically correct at all.
342 
343     // CHECK:      call void @__cxa_guard_release(i32* @_ZGVZN5test84testEvE1x)
344     // CHECK-NEXT: br label
345     //   -> end
346     // end:
347     // CHECK:      ret void
348     static A x;
349 
350     // CHECK:      call i8* @llvm.eh.exception()
351     // CHECK:      call void @__cxa_guard_abort(i32* @_ZGVZN5test84testEvE1x)
352     // CHECK:      call void @llvm.eh.resume(
353   }
354 }
355 
356   // CHECK: define linkonce_odr [[C:%.*]]* @_ZTv0_n12_N5test21CD1Ev(
357   // CHECK:   call [[C]]* @_ZN5test21CD1Ev(
358   // CHECK:   ret [[C]]* undef
359 
360   // CHECK: define linkonce_odr void @_ZTv0_n12_N5test21CD0Ev(
361   // CHECK:   call void @_ZN5test21CD0Ev(
362   // CHECK:   ret void
363 
364 // CHECK: @_GLOBAL__D_a()
365 // CHECK: call %class.bar* @_ZN3barD1Ev(%class.bar* @baz)
366