1 // RUN: %clang_cc1 %s -emit-llvm -triple %itanium_abi_triple -std=c++11 -o - | FileCheck %s 2 // RUN: %clang_cc1 %s -emit-llvm -triple i686-linux-gnu -std=c++11 -o - | FileCheck %s 3 // RUN: %clang_cc1 %s -emit-llvm -triple x86_64-linux-gnu -std=c++11 -o - | FileCheck %s 4 // RUN: %clang_cc1 %s -emit-llvm -triple powerpc64le-unknown-linux-gnu -std=c++11 -o - | FileCheck %s 5 6 struct __attribute__((abi_tag("A", "B"))) A { }; 7 8 struct B: A { }; 9 10 template<class T> 11 12 struct C { 13 }; 14 15 struct D { A* p; }; 16 17 template<class T> 18 struct __attribute__((abi_tag("C", "D"))) E { 19 }; 20 21 struct __attribute__((abi_tag("A", "B"))) F { }; 22 23 A a1; 24 // CHECK-DAG: @_Z2a1B1AB1B = 25 26 __attribute__((abi_tag("C", "D"))) 27 A a2; 28 // CHECK-DAG: @_Z2a2B1AB1BB1CB1D = 29 30 B a3; 31 // CHECK-DAG: @a3 = 32 33 C<A> a4; 34 // CHECK-DAG: @_Z2a4B1AB1B = 35 36 D a5; 37 // CHECK-DAG: @a5 = 38 39 E<int> a6; 40 // CHECK-DAG: @_Z2a6B1CB1D = 41 42 E<A> a7; 43 // CHECK-DAG: @_Z2a7B1AB1BB1CB1D = 44 45 template<> 46 struct E<float> { 47 static float a8; 48 }; 49 float E<float>::a8; 50 // CHECK-DAG: @_ZN1EB1CB1DIfE2a8E = 51 52 template<> 53 struct E<F> { 54 static bool a9; 55 }; 56 bool E<F>::a9; 57 // CHECK-DAG: @_ZN1EB1CB1DI1FB1AB1BE2a9E = 58 59 struct __attribute__((abi_tag("A", "B"))) A10 { ~A10A1060 virtual ~A10() {} 61 } a10; 62 // vtable 63 // CHECK-DAG: @_ZTV3A10B1AB1B = 64 // typeinfo 65 // CHECK-DAG: @_ZTI3A10B1AB1B = 66 67 struct __attribute__((abi_tag("A"))) B11 { 68 static A10 b; 69 }; 70 A10 B11::b; 71 // B11[abi:A]::b[abi:B] 72 // CHECK-DAG: @_ZN3B11B1A1bB1BE = 73 74 __attribute__ ((abi_tag("C", "D"))) f1()75void* f1() { 76 return 0; 77 } 78 // CHECK-DAG: define {{.*}} @_Z2f1B1CB1Dv( 79 80 __attribute__ ((abi_tag("C", "D"))) f2()81A* f2() { 82 return 0; 83 } 84 // CHECK-DAG: define {{.*}} @_Z2f2B1AB1BB1CB1Dv( 85 f3()86B* f3() { 87 return 0; 88 } 89 // CHECK-DAG: define {{.*}} @_Z2f3v( 90 f4()91C<A>* f4() { 92 return 0; 93 } 94 // CHECK-DAG: define {{.*}} @_Z2f4B1AB1Bv( 95 f5()96D* f5() { 97 return 0; 98 } 99 // CHECK-DAG: define {{.*}} @_Z2f5v( 100 f6()101E<char>* f6() { 102 return 0; 103 } 104 // CHECK-DAG: define {{.*}} @_Z2f6B1CB1Dv( 105 f7()106E<A>* f7() { 107 return 0; 108 } 109 // CHECK-DAG: define {{.*}} @_Z2f7B1AB1BB1CB1Dv( 110 f8(E<A> *)111void f8(E<A>*) { 112 } 113 // CHECK-DAG: define {{.*}} @_Z2f8P1EB1CB1DI1AB1AB1BE( 114 115 inline namespace Names1 __attribute__((__abi_tag__)) { 116 class C1 {}; 117 } f9()118C1 f9() { return C1(); } 119 // CHECK-DAG: @_Z2f9B6Names1v( 120 121 inline namespace Names2 __attribute__((__abi_tag__("Tag1", "Tag2"))) { 122 class C2 {}; 123 } f10()124C2 f10() { return C2(); } 125 // CHECK-DAG: @_Z3f10B4Tag1B4Tag2v( 126 f11(A)127void __attribute__((abi_tag("A"))) f11(A) {} 128 // f11[abi:A](A[abi:A][abi:B]) 129 // CHECK-DAG: define {{.*}} @_Z3f11B1A1AB1AB1B( 130 f12(A)131A f12(A) { return A(); } 132 // f12(A[abi:A][abi:B]) 133 // CHECK-DAG: define {{.*}} @_Z3f121AB1AB1B( 134 f13()135inline void f13() { 136 struct L { 137 static E<int>* foo() { 138 static A10 a; 139 return 0; 140 } 141 }; 142 L::foo(); 143 } f13_test()144void f13_test() { 145 f13(); 146 } 147 // f13()::L::foo[abi:C][abi:D]() 148 // CHECK-DAG: define linkonce_odr %struct.E* @_ZZ3f13vEN1L3fooB1CB1DEv( 149 150 // f13()::L::foo[abi:C][abi:D]()::a[abi:A][abi:B] 151 // CHECK-DAG: @_ZZZ3f13vEN1L3fooB1CB1DEvE1aB1AB1B = 152 153 // guard variable for f13()::L::foo[abi:C][abi:D]()::a[abi:A][abi:B] 154 // CHECK-DAG: @_ZGVZZ3f13vEN1L3fooB1CB1DEvE1aB1AB1B = 155 156 struct __attribute__((abi_tag("TAG"))) A14 { 157 A14 f14(); 158 }; f14()159A14 A14::f14() { 160 return A14(); 161 } 162 // A14[abi:TAG]::f14() 163 // CHECK-DAG: define {{.+}} @_ZN3A14B3TAG3f14Ev( 164 165 template<class T> f15()166T f15() { 167 return T(); 168 } f15_test()169void f15_test() { 170 f15<A14>(); 171 } 172 // A14[abi:TAG] f15<A14[abi:TAG]>() 173 // CHECK-DAG: define linkonce_odr {{.+}} @_Z3f15I3A14B3TAGET_v( 174 175 template<class T> f16()176A14 f16() { 177 return A14(); 178 } f16_test()179void f16_test() { 180 f16<int>(); 181 } 182 // A14[abi:TAG] f16<int>() 183 // CHECK-DAG: define linkonce_odr {{.+}} @_Z3f16IiE3A14B3TAGv( 184 185 template<class T> 186 struct __attribute__((abi_tag("TAG"))) A17 { operator +A17187 A17 operator+(const A17& a) { 188 return a; 189 } 190 }; f17_test()191void f17_test() { 192 A17<int> a, b; 193 a + b; 194 } 195 // A17[abi:TAG]<int>::operator+(A17[abi:TAG]<int> const&) 196 // CHECK-DAG: define linkonce_odr {{.+}} @_ZN3A17B3TAGIiEplERKS0_( 197 198 struct A18 { operator AA18199 operator A() { return A(); } 200 }; f18_test()201void f18_test() { 202 A a = A18(); 203 } 204 // A18::operator A[abi:A][abi:B]() but GCC adds the same tags twice! 205 // CHECK-DAG: define linkonce_odr {{.+}} @_ZN3A18cv1AB1AB1BEv( 206