1*0a6a1f1dSLionel Sambuc // RUN: %clang_cc1 %s -triple=thumbv7-apple-ios6.0 -fno-use-cxa-atexit -target-abi apcs-gnu -emit-llvm -o - -fexceptions | FileCheck %s 2f4a2713aSLionel Sambuc 3f4a2713aSLionel Sambuc // CHECK: @_ZZN5test74testEvE1x = internal global i32 0, align 4 4f4a2713aSLionel Sambuc // CHECK: @_ZGVZN5test74testEvE1x = internal global i32 0 5f4a2713aSLionel Sambuc // CHECK: @_ZZN5test84testEvE1x = internal global [[TEST8A:.*]] zeroinitializer, align 1 6f4a2713aSLionel Sambuc // CHECK: @_ZGVZN5test84testEvE1x = internal global i32 0 7f4a2713aSLionel Sambuc 8f4a2713aSLionel Sambuc typedef typeof(sizeof(int)) size_t; 9f4a2713aSLionel Sambuc 10f4a2713aSLionel Sambuc class foo { 11f4a2713aSLionel Sambuc public: 12f4a2713aSLionel Sambuc foo(); 13f4a2713aSLionel Sambuc virtual ~foo(); 14f4a2713aSLionel Sambuc }; 15f4a2713aSLionel Sambuc 16f4a2713aSLionel Sambuc class bar : public foo { 17f4a2713aSLionel Sambuc public: 18f4a2713aSLionel Sambuc bar(); 19f4a2713aSLionel Sambuc }; 20f4a2713aSLionel Sambuc 21f4a2713aSLionel Sambuc // The global dtor needs the right calling conv with -fno-use-cxa-atexit 22f4a2713aSLionel Sambuc // rdar://7817590 23f4a2713aSLionel Sambuc bar baz; 24f4a2713aSLionel Sambuc 25f4a2713aSLionel Sambuc // PR9593 26f4a2713aSLionel Sambuc // Make sure atexit(3) is used for global dtors. 27f4a2713aSLionel Sambuc 28f4a2713aSLionel Sambuc // CHECK: call [[BAR:%.*]]* @_ZN3barC1Ev( 29f4a2713aSLionel Sambuc // CHECK-NEXT: call i32 @atexit(void ()* @__dtor_baz) 30f4a2713aSLionel Sambuc 31*0a6a1f1dSLionel Sambuc // CHECK-NOT: @_GLOBAL__D_a() 32f4a2713aSLionel Sambuc // CHECK-LABEL: define internal void @__dtor_baz() 33f4a2713aSLionel Sambuc // CHECK: call [[BAR]]* @_ZN3barD1Ev([[BAR]]* @baz) 34f4a2713aSLionel Sambuc 35f4a2713aSLionel Sambuc // Destructors and constructors must return this. 36f4a2713aSLionel Sambuc namespace test1 { 37f4a2713aSLionel Sambuc void foo(); 38f4a2713aSLionel Sambuc 39f4a2713aSLionel Sambuc struct A { Atest1::A40f4a2713aSLionel Sambuc A(int i) { foo(); } ~Atest1::A41f4a2713aSLionel Sambuc ~A() { foo(); } bartest1::A42f4a2713aSLionel Sambuc void bar() { foo(); } 43f4a2713aSLionel Sambuc }; 44f4a2713aSLionel Sambuc 45f4a2713aSLionel Sambuc // CHECK-LABEL: define void @_ZN5test14testEv() test()46f4a2713aSLionel Sambuc void test() { 47f4a2713aSLionel Sambuc // CHECK: [[AV:%.*]] = alloca [[A:%.*]], align 1 48f4a2713aSLionel Sambuc // CHECK: call [[A]]* @_ZN5test11AC1Ei([[A]]* [[AV]], i32 10) 49f4a2713aSLionel Sambuc // CHECK: invoke void @_ZN5test11A3barEv([[A]]* [[AV]]) 50f4a2713aSLionel Sambuc // CHECK: call [[A]]* @_ZN5test11AD1Ev([[A]]* [[AV]]) 51f4a2713aSLionel Sambuc // CHECK: ret void 52f4a2713aSLionel Sambuc A a = 10; 53f4a2713aSLionel Sambuc a.bar(); 54f4a2713aSLionel Sambuc } 55f4a2713aSLionel Sambuc 56f4a2713aSLionel Sambuc // CHECK: define linkonce_odr [[A]]* @_ZN5test11AC1Ei([[A]]* returned %this, i32 %i) unnamed_addr 57f4a2713aSLionel Sambuc // CHECK: [[THIS:%.*]] = alloca [[A]]*, align 4 58f4a2713aSLionel Sambuc // CHECK: store [[A]]* {{.*}}, [[A]]** [[THIS]] 59f4a2713aSLionel Sambuc // CHECK: [[THIS1:%.*]] = load [[A]]** [[THIS]] 60f4a2713aSLionel Sambuc // CHECK: {{%.*}} = call [[A]]* @_ZN5test11AC2Ei( 61f4a2713aSLionel Sambuc // CHECK: ret [[A]]* [[THIS1]] 62f4a2713aSLionel Sambuc 63f4a2713aSLionel Sambuc // CHECK: define linkonce_odr [[A]]* @_ZN5test11AD1Ev([[A]]* returned %this) unnamed_addr 64f4a2713aSLionel Sambuc // CHECK: [[THIS:%.*]] = alloca [[A]]*, align 4 65f4a2713aSLionel Sambuc // CHECK: store [[A]]* {{.*}}, [[A]]** [[THIS]] 66f4a2713aSLionel Sambuc // CHECK: [[THIS1:%.*]] = load [[A]]** [[THIS]] 67f4a2713aSLionel Sambuc // CHECK: {{%.*}} = call [[A]]* @_ZN5test11AD2Ev( 68f4a2713aSLionel Sambuc // CHECK: ret [[A]]* [[THIS1]] 69f4a2713aSLionel Sambuc } 70f4a2713aSLionel Sambuc 71f4a2713aSLionel Sambuc // Awkward virtual cases. 72f4a2713aSLionel Sambuc namespace test2 { 73f4a2713aSLionel Sambuc void foo(); 74f4a2713aSLionel Sambuc 75f4a2713aSLionel Sambuc struct A { 76f4a2713aSLionel Sambuc int x; 77f4a2713aSLionel Sambuc 78f4a2713aSLionel Sambuc A(int); ~Atest2::A79f4a2713aSLionel Sambuc virtual ~A() { foo(); } 80f4a2713aSLionel Sambuc }; 81f4a2713aSLionel Sambuc 82f4a2713aSLionel Sambuc struct B { 83f4a2713aSLionel Sambuc int y; 84f4a2713aSLionel Sambuc int z; 85f4a2713aSLionel Sambuc 86f4a2713aSLionel Sambuc B(int); ~Btest2::B87f4a2713aSLionel Sambuc virtual ~B() { foo(); } 88f4a2713aSLionel Sambuc }; 89f4a2713aSLionel Sambuc 90f4a2713aSLionel Sambuc struct C : A, virtual B { 91f4a2713aSLionel Sambuc int q; 92f4a2713aSLionel Sambuc Ctest2::C93f4a2713aSLionel Sambuc C(int i) : A(i), B(i) { foo(); } ~Ctest2::C94f4a2713aSLionel Sambuc ~C() { foo(); } 95f4a2713aSLionel Sambuc }; 96f4a2713aSLionel Sambuc test()97f4a2713aSLionel Sambuc void test() { 98f4a2713aSLionel Sambuc C c = 10; 99f4a2713aSLionel Sambuc } 100f4a2713aSLionel Sambuc 101f4a2713aSLionel Sambuc // Tests at eof 102f4a2713aSLionel Sambuc } 103f4a2713aSLionel Sambuc 104f4a2713aSLionel Sambuc namespace test3 { 105f4a2713aSLionel Sambuc struct A { 106f4a2713aSLionel Sambuc int x; 107f4a2713aSLionel Sambuc ~A(); 108f4a2713aSLionel Sambuc }; 109f4a2713aSLionel Sambuc a()110f4a2713aSLionel Sambuc void a() { 111f4a2713aSLionel Sambuc // CHECK-LABEL: define void @_ZN5test31aEv() 112f4a2713aSLionel Sambuc // CHECK: call noalias i8* @_Znam(i32 48) 113f4a2713aSLionel Sambuc // CHECK: store i32 4 114f4a2713aSLionel Sambuc // CHECK: store i32 10 115f4a2713aSLionel Sambuc A *x = new A[10]; 116f4a2713aSLionel Sambuc } 117f4a2713aSLionel Sambuc b(int n)118f4a2713aSLionel Sambuc void b(int n) { 119f4a2713aSLionel Sambuc // CHECK-LABEL: define void @_ZN5test31bEi( 120f4a2713aSLionel Sambuc // CHECK: [[N:%.*]] = load i32* 121f4a2713aSLionel Sambuc // CHECK: @llvm.umul.with.overflow.i32(i32 [[N]], i32 4) 122f4a2713aSLionel Sambuc // CHECK: @llvm.uadd.with.overflow.i32(i32 {{.*}}, i32 8) 123f4a2713aSLionel Sambuc // CHECK: [[OR:%.*]] = or i1 124f4a2713aSLionel Sambuc // CHECK: [[SZ:%.*]] = select i1 [[OR]] 125f4a2713aSLionel Sambuc // CHECK: call noalias i8* @_Znam(i32 [[SZ]]) 126f4a2713aSLionel Sambuc // CHECK: store i32 4 127f4a2713aSLionel Sambuc // CHECK: store i32 [[N]] 128f4a2713aSLionel Sambuc A *x = new A[n]; 129f4a2713aSLionel Sambuc } 130f4a2713aSLionel Sambuc c()131f4a2713aSLionel Sambuc void c() { 132f4a2713aSLionel Sambuc // CHECK-LABEL: define void @_ZN5test31cEv() 133f4a2713aSLionel Sambuc // CHECK: call noalias i8* @_Znam(i32 808) 134f4a2713aSLionel Sambuc // CHECK: store i32 4 135f4a2713aSLionel Sambuc // CHECK: store i32 200 136f4a2713aSLionel Sambuc A (*x)[20] = new A[10][20]; 137f4a2713aSLionel Sambuc } 138f4a2713aSLionel Sambuc d(int n)139f4a2713aSLionel Sambuc void d(int n) { 140f4a2713aSLionel Sambuc // CHECK-LABEL: define void @_ZN5test31dEi( 141f4a2713aSLionel Sambuc // CHECK: [[N:%.*]] = load i32* 142f4a2713aSLionel Sambuc // CHECK: @llvm.umul.with.overflow.i32(i32 [[N]], i32 80) 143f4a2713aSLionel Sambuc // CHECK: [[NE:%.*]] = mul i32 [[N]], 20 144f4a2713aSLionel Sambuc // CHECK: @llvm.uadd.with.overflow.i32(i32 {{.*}}, i32 8) 145f4a2713aSLionel Sambuc // CHECK: [[SZ:%.*]] = select 146f4a2713aSLionel Sambuc // CHECK: call noalias i8* @_Znam(i32 [[SZ]]) 147f4a2713aSLionel Sambuc // CHECK: store i32 4 148f4a2713aSLionel Sambuc // CHECK: store i32 [[NE]] 149f4a2713aSLionel Sambuc A (*x)[20] = new A[n][20]; 150f4a2713aSLionel Sambuc } 151f4a2713aSLionel Sambuc e(A * x)152f4a2713aSLionel Sambuc void e(A *x) { 153f4a2713aSLionel Sambuc // CHECK-LABEL: define void @_ZN5test31eEPNS_1AE( 154f4a2713aSLionel Sambuc // CHECK: icmp eq {{.*}}, null 155f4a2713aSLionel Sambuc // CHECK: getelementptr {{.*}}, i64 -8 156f4a2713aSLionel Sambuc // CHECK: getelementptr {{.*}}, i64 4 157f4a2713aSLionel Sambuc // CHECK: bitcast {{.*}} to i32* 158f4a2713aSLionel Sambuc // CHECK: load 159f4a2713aSLionel Sambuc // CHECK: invoke {{.*}} @_ZN5test31AD1Ev 160f4a2713aSLionel Sambuc // CHECK: call void @_ZdaPv 161f4a2713aSLionel Sambuc delete [] x; 162f4a2713aSLionel Sambuc } 163f4a2713aSLionel Sambuc f(A (* x)[20])164f4a2713aSLionel Sambuc void f(A (*x)[20]) { 165f4a2713aSLionel Sambuc // CHECK-LABEL: define void @_ZN5test31fEPA20_NS_1AE( 166f4a2713aSLionel Sambuc // CHECK: icmp eq {{.*}}, null 167f4a2713aSLionel Sambuc // CHECK: getelementptr {{.*}}, i64 -8 168f4a2713aSLionel Sambuc // CHECK: getelementptr {{.*}}, i64 4 169f4a2713aSLionel Sambuc // CHECK: bitcast {{.*}} to i32* 170f4a2713aSLionel Sambuc // CHECK: load 171f4a2713aSLionel Sambuc // CHECK: invoke {{.*}} @_ZN5test31AD1Ev 172f4a2713aSLionel Sambuc // CHECK: call void @_ZdaPv 173f4a2713aSLionel Sambuc delete [] x; 174f4a2713aSLionel Sambuc } 175f4a2713aSLionel Sambuc } 176f4a2713aSLionel Sambuc 177f4a2713aSLionel Sambuc namespace test4 { 178f4a2713aSLionel Sambuc struct A { 179f4a2713aSLionel Sambuc int x; 180f4a2713aSLionel Sambuc void operator delete[](void *, size_t sz); 181f4a2713aSLionel Sambuc }; 182f4a2713aSLionel Sambuc a()183f4a2713aSLionel Sambuc void a() { 184f4a2713aSLionel Sambuc // CHECK-LABEL: define void @_ZN5test41aEv() 185f4a2713aSLionel Sambuc // CHECK: call noalias i8* @_Znam(i32 48) 186f4a2713aSLionel Sambuc // CHECK: store i32 4 187f4a2713aSLionel Sambuc // CHECK: store i32 10 188f4a2713aSLionel Sambuc A *x = new A[10]; 189f4a2713aSLionel Sambuc } 190f4a2713aSLionel Sambuc b(int n)191f4a2713aSLionel Sambuc void b(int n) { 192f4a2713aSLionel Sambuc // CHECK-LABEL: define void @_ZN5test41bEi( 193f4a2713aSLionel Sambuc // CHECK: [[N:%.*]] = load i32* 194f4a2713aSLionel Sambuc // CHECK: @llvm.umul.with.overflow.i32(i32 [[N]], i32 4) 195f4a2713aSLionel Sambuc // CHECK: @llvm.uadd.with.overflow.i32(i32 {{.*}}, i32 8) 196f4a2713aSLionel Sambuc // CHECK: [[SZ:%.*]] = select 197f4a2713aSLionel Sambuc // CHECK: call noalias i8* @_Znam(i32 [[SZ]]) 198f4a2713aSLionel Sambuc // CHECK: store i32 4 199f4a2713aSLionel Sambuc // CHECK: store i32 [[N]] 200f4a2713aSLionel Sambuc A *x = new A[n]; 201f4a2713aSLionel Sambuc } 202f4a2713aSLionel Sambuc c()203f4a2713aSLionel Sambuc void c() { 204f4a2713aSLionel Sambuc // CHECK-LABEL: define void @_ZN5test41cEv() 205f4a2713aSLionel Sambuc // CHECK: call noalias i8* @_Znam(i32 808) 206f4a2713aSLionel Sambuc // CHECK: store i32 4 207f4a2713aSLionel Sambuc // CHECK: store i32 200 208f4a2713aSLionel Sambuc A (*x)[20] = new A[10][20]; 209f4a2713aSLionel Sambuc } 210f4a2713aSLionel Sambuc d(int n)211f4a2713aSLionel Sambuc void d(int n) { 212f4a2713aSLionel Sambuc // CHECK-LABEL: define void @_ZN5test41dEi( 213f4a2713aSLionel Sambuc // CHECK: [[N:%.*]] = load i32* 214f4a2713aSLionel Sambuc // CHECK: @llvm.umul.with.overflow.i32(i32 [[N]], i32 80) 215f4a2713aSLionel Sambuc // CHECK: [[NE:%.*]] = mul i32 [[N]], 20 216f4a2713aSLionel Sambuc // CHECK: @llvm.uadd.with.overflow.i32(i32 {{.*}}, i32 8) 217f4a2713aSLionel Sambuc // CHECK: [[SZ:%.*]] = select 218f4a2713aSLionel Sambuc // CHECK: call noalias i8* @_Znam(i32 [[SZ]]) 219f4a2713aSLionel Sambuc // CHECK: store i32 4 220f4a2713aSLionel Sambuc // CHECK: store i32 [[NE]] 221f4a2713aSLionel Sambuc A (*x)[20] = new A[n][20]; 222f4a2713aSLionel Sambuc } 223f4a2713aSLionel Sambuc e(A * x)224f4a2713aSLionel Sambuc void e(A *x) { 225f4a2713aSLionel Sambuc // CHECK-LABEL: define void @_ZN5test41eEPNS_1AE( 226f4a2713aSLionel Sambuc // CHECK: [[ALLOC:%.*]] = getelementptr inbounds {{.*}}, i64 -8 227f4a2713aSLionel Sambuc // CHECK: getelementptr inbounds {{.*}}, i64 4 228f4a2713aSLionel Sambuc // CHECK: bitcast 229f4a2713aSLionel Sambuc // CHECK: [[T0:%.*]] = load i32* 230f4a2713aSLionel Sambuc // CHECK: [[T1:%.*]] = mul i32 4, [[T0]] 231f4a2713aSLionel Sambuc // CHECK: [[T2:%.*]] = add i32 [[T1]], 8 232f4a2713aSLionel Sambuc // CHECK: call void @_ZN5test41AdaEPvm(i8* [[ALLOC]], i32 [[T2]]) 233f4a2713aSLionel Sambuc delete [] x; 234f4a2713aSLionel Sambuc } 235f4a2713aSLionel Sambuc f(A (* x)[20])236f4a2713aSLionel Sambuc void f(A (*x)[20]) { 237f4a2713aSLionel Sambuc // CHECK-LABEL: define void @_ZN5test41fEPA20_NS_1AE( 238f4a2713aSLionel Sambuc // CHECK: [[ALLOC:%.*]] = getelementptr inbounds {{.*}}, i64 -8 239f4a2713aSLionel Sambuc // CHECK: getelementptr inbounds {{.*}}, i64 4 240f4a2713aSLionel Sambuc // CHECK: bitcast 241f4a2713aSLionel Sambuc // CHECK: [[T0:%.*]] = load i32* 242f4a2713aSLionel Sambuc // CHECK: [[T1:%.*]] = mul i32 4, [[T0]] 243f4a2713aSLionel Sambuc // CHECK: [[T2:%.*]] = add i32 [[T1]], 8 244f4a2713aSLionel Sambuc // CHECK: call void @_ZN5test41AdaEPvm(i8* [[ALLOC]], i32 [[T2]]) 245f4a2713aSLionel Sambuc delete [] x; 246f4a2713aSLionel Sambuc } 247f4a2713aSLionel Sambuc } 248f4a2713aSLionel Sambuc 249f4a2713aSLionel Sambuc // <rdar://problem/8386802>: don't crash 250f4a2713aSLionel Sambuc namespace test5 { 251f4a2713aSLionel Sambuc struct A { 252f4a2713aSLionel Sambuc ~A(); 253f4a2713aSLionel Sambuc }; 254f4a2713aSLionel Sambuc 255f4a2713aSLionel Sambuc // CHECK-LABEL: define void @_ZN5test54testEPNS_1AE test(A * a)256f4a2713aSLionel Sambuc void test(A *a) { 257f4a2713aSLionel Sambuc // CHECK: [[PTR:%.*]] = alloca [[A:%.*]]*, align 4 258f4a2713aSLionel Sambuc // CHECK-NEXT: store [[A]]* {{.*}}, [[A]]** [[PTR]], align 4 259f4a2713aSLionel Sambuc // CHECK-NEXT: [[TMP:%.*]] = load [[A]]** [[PTR]], align 4 260f4a2713aSLionel Sambuc // CHECK-NEXT: call [[A]]* @_ZN5test51AD1Ev([[A]]* [[TMP]]) 261f4a2713aSLionel Sambuc // CHECK-NEXT: ret void 262f4a2713aSLionel Sambuc a->~A(); 263f4a2713aSLionel Sambuc } 264f4a2713aSLionel Sambuc } 265f4a2713aSLionel Sambuc 266f4a2713aSLionel Sambuc namespace test6 { 267f4a2713aSLionel Sambuc struct A { 268f4a2713aSLionel Sambuc virtual ~A(); 269f4a2713aSLionel Sambuc }; 270f4a2713aSLionel Sambuc 271f4a2713aSLionel Sambuc // CHECK-LABEL: define void @_ZN5test64testEPNS_1AE test(A * a)272f4a2713aSLionel Sambuc void test(A *a) { 273f4a2713aSLionel Sambuc // CHECK: [[AVAR:%.*]] = alloca [[A:%.*]]*, align 4 274f4a2713aSLionel Sambuc // CHECK-NEXT: store [[A]]* {{.*}}, [[A]]** [[AVAR]], align 4 275f4a2713aSLionel Sambuc // CHECK-NEXT: [[V:%.*]] = load [[A]]** [[AVAR]], align 4 276f4a2713aSLionel Sambuc // CHECK-NEXT: [[ISNULL:%.*]] = icmp eq [[A]]* [[V]], null 277f4a2713aSLionel Sambuc // CHECK-NEXT: br i1 [[ISNULL]] 278f4a2713aSLionel Sambuc // CHECK: [[T0:%.*]] = bitcast [[A]]* [[V]] to void ([[A]]*)*** 279f4a2713aSLionel Sambuc // CHECK-NEXT: [[T1:%.*]] = load void ([[A]]*)*** [[T0]] 280f4a2713aSLionel Sambuc // CHECK-NEXT: [[T2:%.*]] = getelementptr inbounds void ([[A]]*)** [[T1]], i64 1 281f4a2713aSLionel Sambuc // CHECK-NEXT: [[T3:%.*]] = load void ([[A]]*)** [[T2]] 282f4a2713aSLionel Sambuc // CHECK-NEXT: call void [[T3]]([[A]]* [[V]]) 283f4a2713aSLionel Sambuc // CHECK-NEXT: br label 284f4a2713aSLionel Sambuc // CHECK: ret void 285f4a2713aSLionel Sambuc delete a; 286f4a2713aSLionel Sambuc } 287f4a2713aSLionel Sambuc } 288f4a2713aSLionel Sambuc 289f4a2713aSLionel Sambuc namespace test7 { 290f4a2713aSLionel Sambuc int foo(); 291f4a2713aSLionel Sambuc 292f4a2713aSLionel Sambuc // Static and guard tested at top of file 293f4a2713aSLionel Sambuc 294f4a2713aSLionel Sambuc // CHECK-LABEL: define void @_ZN5test74testEv() test()295f4a2713aSLionel Sambuc void test() { 296*0a6a1f1dSLionel Sambuc // CHECK: [[T0:%.*]] = load atomic i8* bitcast (i32* @_ZGVZN5test74testEvE1x to i8*) acquire, align 1 297*0a6a1f1dSLionel Sambuc // CHECK-NEXT: [[T1:%.*]] = and i8 [[T0]], 1 298*0a6a1f1dSLionel Sambuc // CHECK-NEXT: [[T2:%.*]] = icmp eq i8 [[T1]], 0 299f4a2713aSLionel Sambuc // CHECK-NEXT: br i1 [[T2]] 300f4a2713aSLionel Sambuc // -> fallthrough, end 301f4a2713aSLionel Sambuc // CHECK: [[T3:%.*]] = call i32 @__cxa_guard_acquire(i32* @_ZGVZN5test74testEvE1x) 302f4a2713aSLionel Sambuc // CHECK-NEXT: [[T4:%.*]] = icmp ne i32 [[T3]], 0 303f4a2713aSLionel Sambuc // CHECK-NEXT: br i1 [[T4]] 304f4a2713aSLionel Sambuc // -> fallthrough, end 305f4a2713aSLionel Sambuc // CHECK: [[INIT:%.*]] = invoke i32 @_ZN5test73fooEv() 306f4a2713aSLionel Sambuc // CHECK: store i32 [[INIT]], i32* @_ZZN5test74testEvE1x, align 4 307f4a2713aSLionel Sambuc // CHECK-NEXT: call void @__cxa_guard_release(i32* @_ZGVZN5test74testEvE1x) 308f4a2713aSLionel Sambuc // CHECK-NEXT: br label 309f4a2713aSLionel Sambuc // -> end 310f4a2713aSLionel Sambuc // end: 311f4a2713aSLionel Sambuc // CHECK: ret void 312f4a2713aSLionel Sambuc static int x = foo(); 313f4a2713aSLionel Sambuc 314f4a2713aSLionel Sambuc // CHECK: landingpad { i8*, i32 } personality i8* bitcast (i32 (...)* @__gxx_personality_v0 to i8*) 315f4a2713aSLionel Sambuc // CHECK-NEXT: cleanup 316f4a2713aSLionel Sambuc // CHECK: call void @__cxa_guard_abort(i32* @_ZGVZN5test74testEvE1x) 317f4a2713aSLionel Sambuc // CHECK: resume { i8*, i32 } 318f4a2713aSLionel Sambuc } 319f4a2713aSLionel Sambuc } 320f4a2713aSLionel Sambuc 321f4a2713aSLionel Sambuc namespace test8 { 322f4a2713aSLionel Sambuc struct A { 323f4a2713aSLionel Sambuc A(); 324f4a2713aSLionel Sambuc ~A(); 325f4a2713aSLionel Sambuc }; 326f4a2713aSLionel Sambuc 327f4a2713aSLionel Sambuc // Static and guard tested at top of file 328f4a2713aSLionel Sambuc 329f4a2713aSLionel Sambuc // CHECK-LABEL: define void @_ZN5test84testEv() test()330f4a2713aSLionel Sambuc void test() { 331*0a6a1f1dSLionel Sambuc // CHECK: [[T0:%.*]] = load atomic i8* bitcast (i32* @_ZGVZN5test84testEvE1x to i8*) acquire, align 1 332*0a6a1f1dSLionel Sambuc // CHECK-NEXT: [[T1:%.*]] = and i8 [[T0]], 1 333*0a6a1f1dSLionel Sambuc // CHECK-NEXT: [[T2:%.*]] = icmp eq i8 [[T1]], 0 334f4a2713aSLionel Sambuc // CHECK-NEXT: br i1 [[T2]] 335f4a2713aSLionel Sambuc // -> fallthrough, end 336f4a2713aSLionel Sambuc // CHECK: [[T3:%.*]] = call i32 @__cxa_guard_acquire(i32* @_ZGVZN5test84testEvE1x) 337f4a2713aSLionel Sambuc // CHECK-NEXT: [[T4:%.*]] = icmp ne i32 [[T3]], 0 338f4a2713aSLionel Sambuc // CHECK-NEXT: br i1 [[T4]] 339f4a2713aSLionel Sambuc // -> fallthrough, end 340f4a2713aSLionel Sambuc // CHECK: [[INIT:%.*]] = invoke [[TEST8A]]* @_ZN5test81AC1Ev([[TEST8A]]* @_ZZN5test84testEvE1x) 341f4a2713aSLionel Sambuc 342f4a2713aSLionel Sambuc // FIXME: Here we register a global destructor that 343f4a2713aSLionel Sambuc // unconditionally calls the destructor. That's what we've always 344f4a2713aSLionel Sambuc // done for -fno-use-cxa-atexit here, but that's really not 345f4a2713aSLionel Sambuc // semantically correct at all. 346f4a2713aSLionel Sambuc 347f4a2713aSLionel Sambuc // CHECK: call void @__cxa_guard_release(i32* @_ZGVZN5test84testEvE1x) 348f4a2713aSLionel Sambuc // CHECK-NEXT: br label 349f4a2713aSLionel Sambuc // -> end 350f4a2713aSLionel Sambuc // end: 351f4a2713aSLionel Sambuc // CHECK: ret void 352f4a2713aSLionel Sambuc static A x; 353f4a2713aSLionel Sambuc 354f4a2713aSLionel Sambuc // CHECK: landingpad { i8*, i32 } personality i8* bitcast (i32 (...)* @__gxx_personality_v0 to i8*) 355f4a2713aSLionel Sambuc // CHECK-NEXT: cleanup 356f4a2713aSLionel Sambuc // CHECK: call void @__cxa_guard_abort(i32* @_ZGVZN5test84testEvE1x) 357f4a2713aSLionel Sambuc // CHECK: resume { i8*, i32 } 358f4a2713aSLionel Sambuc } 359f4a2713aSLionel Sambuc } 360f4a2713aSLionel Sambuc 361f4a2713aSLionel Sambuc // rdar://12836470 362f4a2713aSLionel Sambuc // Use a larger-than-mandated array cookie when allocating an 363f4a2713aSLionel Sambuc // array whose type is overaligned. 364f4a2713aSLionel Sambuc namespace test9 { 365f4a2713aSLionel Sambuc class __attribute__((aligned(16))) A { 366f4a2713aSLionel Sambuc float data[4]; 367f4a2713aSLionel Sambuc public: 368f4a2713aSLionel Sambuc A(); 369f4a2713aSLionel Sambuc ~A(); 370f4a2713aSLionel Sambuc }; 371f4a2713aSLionel Sambuc testNew(unsigned n)372f4a2713aSLionel Sambuc A *testNew(unsigned n) { 373f4a2713aSLionel Sambuc return new A[n]; 374f4a2713aSLionel Sambuc } 375f4a2713aSLionel Sambuc // CHECK: define [[TEST9:%.*]]* @_ZN5test97testNewEj(i32 376f4a2713aSLionel Sambuc // CHECK: [[N_VAR:%.*]] = alloca i32, align 4 377f4a2713aSLionel Sambuc // CHECK: [[N:%.*]] = load i32* [[N_VAR]], align 4 378f4a2713aSLionel Sambuc // CHECK-NEXT: [[T0:%.*]] = call { i32, i1 } @llvm.umul.with.overflow.i32(i32 [[N]], i32 16) 379f4a2713aSLionel Sambuc // CHECK-NEXT: [[O0:%.*]] = extractvalue { i32, i1 } [[T0]], 1 380f4a2713aSLionel Sambuc // CHECK-NEXT: [[T1:%.*]] = extractvalue { i32, i1 } [[T0]], 0 381f4a2713aSLionel Sambuc // CHECK-NEXT: [[T2:%.*]] = call { i32, i1 } @llvm.uadd.with.overflow.i32(i32 [[T1]], i32 16) 382f4a2713aSLionel Sambuc // CHECK-NEXT: [[O1:%.*]] = extractvalue { i32, i1 } [[T2]], 1 383f4a2713aSLionel Sambuc // CHECK-NEXT: [[OVERFLOW:%.*]] = or i1 [[O0]], [[O1]] 384f4a2713aSLionel Sambuc // CHECK-NEXT: [[T3:%.*]] = extractvalue { i32, i1 } [[T2]], 0 385f4a2713aSLionel Sambuc // CHECK-NEXT: [[T4:%.*]] = select i1 [[OVERFLOW]], i32 -1, i32 [[T3]] 386f4a2713aSLionel Sambuc // CHECK-NEXT: [[ALLOC:%.*]] = call noalias i8* @_Znam(i32 [[T4]]) 387f4a2713aSLionel Sambuc // CHECK-NEXT: [[T0:%.*]] = bitcast i8* [[ALLOC]] to i32* 388f4a2713aSLionel Sambuc // CHECK-NEXT: store i32 16, i32* [[T0]] 389f4a2713aSLionel Sambuc // CHECK-NEXT: [[T1:%.*]] = getelementptr inbounds i32* [[T0]], i32 1 390f4a2713aSLionel Sambuc // CHECK-NEXT: store i32 [[N]], i32* [[T1]] 391f4a2713aSLionel Sambuc // CHECK-NEXT: [[T0:%.*]] = getelementptr inbounds i8* [[ALLOC]], i64 16 392f4a2713aSLionel Sambuc // CHECK-NEXT: bitcast i8* [[T0]] to [[TEST9]]* 393f4a2713aSLionel Sambuc // Array allocation follows. 394f4a2713aSLionel Sambuc testDelete(A * array)395f4a2713aSLionel Sambuc void testDelete(A *array) { 396f4a2713aSLionel Sambuc delete[] array; 397f4a2713aSLionel Sambuc } 398f4a2713aSLionel Sambuc // CHECK-LABEL: define void @_ZN5test910testDeleteEPNS_1AE( 399f4a2713aSLionel Sambuc // CHECK: [[BEGIN:%.*]] = load [[TEST9]]** 400f4a2713aSLionel Sambuc // CHECK-NEXT: [[T0:%.*]] = icmp eq [[TEST9]]* [[BEGIN]], null 401f4a2713aSLionel Sambuc // CHECK-NEXT: br i1 [[T0]], 402f4a2713aSLionel Sambuc // CHECK: [[T0:%.*]] = bitcast [[TEST9]]* [[BEGIN]] to i8* 403f4a2713aSLionel Sambuc // CHECK-NEXT: [[ALLOC:%.*]] = getelementptr inbounds i8* [[T0]], i64 -16 404f4a2713aSLionel Sambuc // CHECK-NEXT: [[T0:%.*]] = getelementptr inbounds i8* [[ALLOC]], i64 4 405f4a2713aSLionel Sambuc // CHECK-NEXT: [[T1:%.*]] = bitcast i8* [[T0]] to i32* 406f4a2713aSLionel Sambuc // CHECK-NEXT: [[N:%.*]] = load i32* [[T1]] 407f4a2713aSLionel Sambuc // CHECK-NEXT: [[END:%.*]] = getelementptr inbounds [[TEST9]]* [[BEGIN]], i32 [[N]] 408f4a2713aSLionel Sambuc // CHECK-NEXT: [[T0:%.*]] = icmp eq [[TEST9]]* [[BEGIN]], [[END]] 409f4a2713aSLionel Sambuc // CHECK-NEXT: br i1 [[T0]], 410f4a2713aSLionel Sambuc // Array deallocation follows. 411f4a2713aSLionel Sambuc } 412f4a2713aSLionel Sambuc 413f4a2713aSLionel Sambuc // CHECK: define linkonce_odr [[C:%.*]]* @_ZTv0_n12_N5test21CD1Ev( 414f4a2713aSLionel Sambuc // CHECK: call [[C]]* @_ZN5test21CD1Ev( 415f4a2713aSLionel Sambuc // CHECK: ret [[C]]* undef 416f4a2713aSLionel Sambuc 417f4a2713aSLionel Sambuc // CHECK-LABEL: define linkonce_odr void @_ZTv0_n12_N5test21CD0Ev( 418f4a2713aSLionel Sambuc // CHECK: call void @_ZN5test21CD0Ev( 419f4a2713aSLionel Sambuc // CHECK: ret void 420