xref: /aosp_15_r20/external/clang/test/CodeGenCXX/visibility.cpp (revision 67e74705e28f6214e480b399dd47ea732279e315)
1*67e74705SXin Li // RUN: %clang_cc1 %s -std=c++11 -triple=x86_64-apple-darwin10 -emit-llvm -o - | FileCheck %s
2*67e74705SXin Li // RUN: %clang_cc1 %s -std=c++11 -triple=x86_64-apple-darwin10 -fvisibility hidden -emit-llvm -o - | FileCheck %s -check-prefix=CHECK-HIDDEN
3*67e74705SXin Li // For clang, "internal" is just an alias for "hidden". We could use it for some
4*67e74705SXin Li // optimization purposes on 32-bit x86, but it's not worth it.
5*67e74705SXin Li // RUN: %clang_cc1 %s -std=c++11 -triple=x86_64-apple-darwin10 -fvisibility internal -emit-llvm -o - | FileCheck %s -check-prefix=CHECK-HIDDEN
6*67e74705SXin Li 
7*67e74705SXin Li #define HIDDEN __attribute__((visibility("hidden")))
8*67e74705SXin Li #define PROTECTED __attribute__((visibility("protected")))
9*67e74705SXin Li #define DEFAULT __attribute__((visibility("default")))
10*67e74705SXin Li 
11*67e74705SXin Li namespace test30 {
12*67e74705SXin Li   // When H is hidden, it should make X hidden, even if the template argument
13*67e74705SXin Li   // is not.
14*67e74705SXin Li   struct H {
15*67e74705SXin Li   };
16*67e74705SXin Li   template<H *T>
17*67e74705SXin Li   struct X {
18*67e74705SXin Li   };
19*67e74705SXin Li   H DEFAULT a;
20*67e74705SXin Li   X<&a> b;
21*67e74705SXin Li   // CHECK: _ZN6test301bE = global
22*67e74705SXin Li   // CHECK-HIDDEN: _ZN6test301bE = hidden global
23*67e74705SXin Li }
24*67e74705SXin Li 
25*67e74705SXin Li namespace test25 {
26*67e74705SXin Li   template<typename T>
27*67e74705SXin Li   struct X {
28*67e74705SXin Li     template<typename U>
29*67e74705SXin Li     struct definition {
30*67e74705SXin Li     };
31*67e74705SXin Li   };
32*67e74705SXin Li 
33*67e74705SXin Li   class DEFAULT A { };
34*67e74705SXin Li 
35*67e74705SXin Li   X<int>::definition<A> a;
36*67e74705SXin Li   // CHECK: @_ZN6test251aE = global
37*67e74705SXin Li   // CHECK-HIDDEN: @_ZN6test251aE = hidden global
38*67e74705SXin Li }
39*67e74705SXin Li 
40*67e74705SXin Li namespace test28 {
41*67e74705SXin Li   class DEFAULT foo {
42*67e74705SXin Li   };
43*67e74705SXin Li   foo myvec;
44*67e74705SXin Li   // CHECK: @_ZN6test285myvecE = global
45*67e74705SXin Li   // CHECK-HIDDEN: @_ZN6test285myvecE = hidden global
46*67e74705SXin Li }
47*67e74705SXin Li 
48*67e74705SXin Li namespace test29 {
49*67e74705SXin Li #pragma GCC visibility push(hidden)
50*67e74705SXin Li   struct RECT {
51*67e74705SXin Li     int top;
52*67e74705SXin Li   };
53*67e74705SXin Li   DEFAULT extern RECT data_rect;
54*67e74705SXin Li   RECT data_rect = { -1};
55*67e74705SXin Li #pragma GCC visibility pop
56*67e74705SXin Li   // CHECK: @_ZN6test299data_rectE = global
57*67e74705SXin Li   // CHECK-HIDDEN: @_ZN6test299data_rectE = global
58*67e74705SXin Li }
59*67e74705SXin Li 
60*67e74705SXin Li namespace test40 {
61*67e74705SXin Li   template<typename T>
62*67e74705SXin Li   struct foo {
63*67e74705SXin Li     DEFAULT static int bar;
64*67e74705SXin Li   };
65*67e74705SXin Li   template<typename T>
66*67e74705SXin Li   int foo<T>::bar;
67*67e74705SXin Li   template struct foo<int>;
68*67e74705SXin Li   // CHECK: _ZN6test403fooIiE3barE = weak_odr global
69*67e74705SXin Li   // CHECK-HIDDEN: _ZN6test403fooIiE3barE = weak_odr global
70*67e74705SXin Li }
71*67e74705SXin Li 
72*67e74705SXin Li namespace test41 {
73*67e74705SXin Li   // Unlike gcc we propagate the information that foo not only is hidden, but
74*67e74705SXin Li   // has been explicitly marked as so. This lets us produce a hidden undefined
75*67e74705SXin Li   // reference to bar.
76*67e74705SXin Li   struct HIDDEN foo {};
77*67e74705SXin Li   extern foo bar;
zed()78*67e74705SXin Li   foo *zed() {
79*67e74705SXin Li     return &bar;
80*67e74705SXin Li   }
81*67e74705SXin Li   // CHECK: @_ZN6test413barE = external hidden global
82*67e74705SXin Li   // CHECK-HIDDEN: @_ZN6test413barE = external hidden global
83*67e74705SXin Li }
84*67e74705SXin Li 
85*67e74705SXin Li namespace test48 {
86*67e74705SXin Li   // Test that we use the visibility of struct foo when instantiating the
87*67e74705SXin Li   // template. Note that is a case where we disagree with gcc, it produces
88*67e74705SXin Li   // a default symbol.
89*67e74705SXin Li   struct HIDDEN foo {
90*67e74705SXin Li   };
91*67e74705SXin Li   DEFAULT foo x;
92*67e74705SXin Li 
93*67e74705SXin Li   struct bar {
94*67e74705SXin Li     template<foo *z>
95*67e74705SXin Li     struct zed {
96*67e74705SXin Li     };
97*67e74705SXin Li   };
98*67e74705SXin Li 
99*67e74705SXin Li   bar::zed<&x> y;
100*67e74705SXin Li   // CHECK: _ZN6test481yE = hidden global
101*67e74705SXin Li   // CHECK-HIDDEN: _ZN6test481yE = hidden global
102*67e74705SXin Li }
103*67e74705SXin Li 
104*67e74705SXin Li // CHECK: @_ZN5Test425VariableInHiddenNamespaceE = hidden global i32 10
105*67e74705SXin Li // CHECK: @_ZN5Test71aE = hidden global
106*67e74705SXin Li // CHECK: @_ZN5Test71bE = global
107*67e74705SXin Li // CHECK: @test9_var = global
108*67e74705SXin Li // CHECK-HIDDEN: @test9_var = global
109*67e74705SXin Li // CHECK: @_ZN6Test121A6hiddenE = external hidden global
110*67e74705SXin Li // CHECK: @_ZN6Test121A7visibleE = external global
111*67e74705SXin Li // CHECK-HIDDEN: @_ZN6Test121A6hiddenE = external hidden global
112*67e74705SXin Li // CHECK-HIDDEN: @_ZN6Test121A7visibleE = external global
113*67e74705SXin Li // CHECK: @_ZN6Test131B1aE = hidden global
114*67e74705SXin Li // CHECK: @_ZN6Test131C1aE = global
115*67e74705SXin Li // CHECK-HIDDEN: @_ZN6Test131B1aE = hidden global
116*67e74705SXin Li // CHECK-HIDDEN: @_ZN6Test131C1aE = global
117*67e74705SXin Li // CHECK: @_ZN6Test143varE = external global
118*67e74705SXin Li // CHECK-HIDDEN: @_ZN6Test143varE = external global
119*67e74705SXin Li // CHECK: @_ZN6Test154TempINS_1AEE5Inner6bufferE = external global [0 x i8]
120*67e74705SXin Li // CHECK-HIDDEN: @_ZN6Test154TempINS_1AEE5Inner6bufferE = external global [0 x i8]
121*67e74705SXin Li 
122*67e74705SXin Li namespace test27 {
123*67e74705SXin Li   template<typename T>
124*67e74705SXin Li   class C {
125*67e74705SXin Li     class DEFAULT D {
126*67e74705SXin Li       void f();
127*67e74705SXin Li     };
128*67e74705SXin Li   };
129*67e74705SXin Li 
130*67e74705SXin Li   template<>
131*67e74705SXin Li   class C<int>::D {
132*67e74705SXin Li     virtual void g();
133*67e74705SXin Li   };
134*67e74705SXin Li 
g()135*67e74705SXin Li   void C<int>::D::g() {
136*67e74705SXin Li   }
137*67e74705SXin Li   // CHECK: _ZTVN6test271CIiE1DE = unnamed_addr constant
138*67e74705SXin Li   // CHECK-HIDDEN: _ZTVN6test271CIiE1DE = unnamed_addr constant
139*67e74705SXin Li }
140*67e74705SXin Li 
141*67e74705SXin Li // CHECK: @_ZTVN5Test63fooE = linkonce_odr hidden unnamed_addr constant
142*67e74705SXin Li 
143*67e74705SXin Li // CHECK-HIDDEN: @_ZTVN6Test161AIcEE = external unnamed_addr constant
144*67e74705SXin Li // CHECK-HIDDEN: @_ZTTN6Test161AIcEE = external unnamed_addr constant
145*67e74705SXin Li 
146*67e74705SXin Li // CHECK: @_ZZN6test681fC1EvE4test = linkonce_odr global
147*67e74705SXin Li // CHECK-HIDDEN: @_ZZN6test681fC1EvE4test = linkonce_odr hidden global
148*67e74705SXin Li 
149*67e74705SXin Li // CHECK: @_ZGVZN6test681fC1EvE4test = linkonce_odr global
150*67e74705SXin Li // CHECK-HIDDEN: @_ZGVZN6test681fC1EvE4test = linkonce_odr hidden global
151*67e74705SXin Li 
152*67e74705SXin Li // CHECK: @_ZZN6Test193fooIiEEvvE1a = linkonce_odr global
153*67e74705SXin Li // CHECK-HIDDEN: @_ZZN6Test193fooIiEEvvE1a = linkonce_odr hidden global
154*67e74705SXin Li 
155*67e74705SXin Li // CHECK: @_ZGVZN6Test193fooIiEEvvE1a = linkonce_odr global i64
156*67e74705SXin Li // CHECK-HIDDEN: @_ZGVZN6Test193fooIiEEvvE1a = linkonce_odr hidden global i64
157*67e74705SXin Li 
158*67e74705SXin Li namespace Test1 {
159*67e74705SXin Li   // CHECK-LABEL: define hidden void @_ZN5Test11fEv
f()160*67e74705SXin Li   void HIDDEN f() { }
161*67e74705SXin Li 
162*67e74705SXin Li }
163*67e74705SXin Li 
164*67e74705SXin Li namespace Test2 {
165*67e74705SXin Li   struct HIDDEN A {
166*67e74705SXin Li     void f();
167*67e74705SXin Li   };
168*67e74705SXin Li 
169*67e74705SXin Li   // A::f is a member function of a hidden class.
170*67e74705SXin Li   // CHECK-LABEL: define hidden void @_ZN5Test21A1fEv
f()171*67e74705SXin Li   void A::f() { }
172*67e74705SXin Li }
173*67e74705SXin Li 
174*67e74705SXin Li namespace Test3 {
175*67e74705SXin Li   struct HIDDEN A {
176*67e74705SXin Li     struct B {
177*67e74705SXin Li       void f();
178*67e74705SXin Li     };
179*67e74705SXin Li   };
180*67e74705SXin Li 
181*67e74705SXin Li   // B is a nested class where its parent class is hidden.
182*67e74705SXin Li   // CHECK-LABEL: define hidden void @_ZN5Test31A1B1fEv
f()183*67e74705SXin Li   void A::B::f() { }
184*67e74705SXin Li }
185*67e74705SXin Li 
186*67e74705SXin Li namespace Test4 HIDDEN {
187*67e74705SXin Li   int VariableInHiddenNamespace = 10;
188*67e74705SXin Li 
189*67e74705SXin Li   // Test4::g is in a hidden namespace.
190*67e74705SXin Li   // CHECK-LABEL: define hidden void @_ZN5Test41gEv
g()191*67e74705SXin Li   void g() { }
192*67e74705SXin Li 
193*67e74705SXin Li   struct DEFAULT A {
194*67e74705SXin Li     void f();
195*67e74705SXin Li   };
196*67e74705SXin Li 
197*67e74705SXin Li   // A has default visibility.
198*67e74705SXin Li   // CHECK-LABEL: define void @_ZN5Test41A1fEv
f()199*67e74705SXin Li   void A::f() { }
200*67e74705SXin Li }
201*67e74705SXin Li 
202*67e74705SXin Li namespace Test5 {
203*67e74705SXin Li 
204*67e74705SXin Li   namespace NS HIDDEN {
205*67e74705SXin Li     // f is in NS which is hidden.
206*67e74705SXin Li     // CHECK-LABEL: define hidden void @_ZN5Test52NS1fEv()
f()207*67e74705SXin Li     void f() { }
208*67e74705SXin Li   }
209*67e74705SXin Li 
210*67e74705SXin Li   namespace NS {
211*67e74705SXin Li     // g is in NS, but this NS decl is not hidden.
212*67e74705SXin Li     // CHECK-LABEL: define void @_ZN5Test52NS1gEv
g()213*67e74705SXin Li     void g() { }
214*67e74705SXin Li   }
215*67e74705SXin Li }
216*67e74705SXin Li 
217*67e74705SXin Li // <rdar://problem/8091955>
218*67e74705SXin Li namespace Test6 {
219*67e74705SXin Li   struct HIDDEN foo {
fooTest6::foo220*67e74705SXin Li     foo() { }
221*67e74705SXin Li     void bonk();
222*67e74705SXin Li     virtual void bar() = 0;
223*67e74705SXin Li 
zonkTest6::foo224*67e74705SXin Li     virtual void zonk() {}
225*67e74705SXin Li   };
226*67e74705SXin Li 
227*67e74705SXin Li   struct barc : public foo {
228*67e74705SXin Li     barc();
229*67e74705SXin Li     virtual void bar();
230*67e74705SXin Li   };
231*67e74705SXin Li 
barc()232*67e74705SXin Li   barc::barc() {}
233*67e74705SXin Li }
234*67e74705SXin Li 
235*67e74705SXin Li namespace Test7 {
236*67e74705SXin Li   class HIDDEN A {};
237*67e74705SXin Li   A a; // top of file
238*67e74705SXin Li 
239*67e74705SXin Li   template <A&> struct Aref {
fooTest7::Aref240*67e74705SXin Li     static void foo() {}
241*67e74705SXin Li   };
242*67e74705SXin Li 
243*67e74705SXin Li   class B : public A {};
244*67e74705SXin Li   B b; // top of file
245*67e74705SXin Li 
246*67e74705SXin Li   // CHECK-LABEL: define linkonce_odr hidden void @_ZN5Test74ArefIL_ZNS_1aEEE3fooEv()
test()247*67e74705SXin Li   void test() {
248*67e74705SXin Li     Aref<a>::foo();
249*67e74705SXin Li   }
250*67e74705SXin Li }
251*67e74705SXin Li 
252*67e74705SXin Li namespace Test8 {
253*67e74705SXin Li   void foo();
bar()254*67e74705SXin Li   void bar() {}
255*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define hidden void @_ZN5Test83barEv()
256*67e74705SXin Li   // CHECK-HIDDEN: declare void @_ZN5Test83fooEv()
257*67e74705SXin Li 
test()258*67e74705SXin Li   void test() {
259*67e74705SXin Li     foo();
260*67e74705SXin Li     bar();
261*67e74705SXin Li   }
262*67e74705SXin Li }
263*67e74705SXin Li 
264*67e74705SXin Li // PR8457
265*67e74705SXin Li namespace Test9 {
266*67e74705SXin Li   extern "C" {
267*67e74705SXin Li     struct A { int field; };
test9_fun(struct A * a)268*67e74705SXin Li     void DEFAULT test9_fun(struct A *a) { }
269*67e74705SXin Li     struct A DEFAULT test9_var; // above
270*67e74705SXin Li   }
271*67e74705SXin Li   // CHECK-LABEL: define void @test9_fun(
272*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define void @test9_fun(
273*67e74705SXin Li 
test()274*67e74705SXin Li   void test() {
275*67e74705SXin Li     A a = test9_var;
276*67e74705SXin Li     test9_fun(&a);
277*67e74705SXin Li   }
278*67e74705SXin Li }
279*67e74705SXin Li 
280*67e74705SXin Li // PR8478
281*67e74705SXin Li namespace Test10 {
282*67e74705SXin Li   struct A;
283*67e74705SXin Li 
284*67e74705SXin Li   class DEFAULT B {
285*67e74705SXin Li     void foo(A*);
286*67e74705SXin Li   };
287*67e74705SXin Li 
288*67e74705SXin Li   // CHECK-LABEL: define void @_ZN6Test101B3fooEPNS_1AE(
289*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define void @_ZN6Test101B3fooEPNS_1AE(
foo(A *)290*67e74705SXin Li   void B::foo(A*) {}
291*67e74705SXin Li }
292*67e74705SXin Li 
293*67e74705SXin Li // PR8492
294*67e74705SXin Li namespace Test11 {
295*67e74705SXin Li   struct A {
fooTest11::A296*67e74705SXin Li     void foo() {}
barTest11::A297*67e74705SXin Li     void DEFAULT bar() {}
298*67e74705SXin Li   };
299*67e74705SXin Li 
test()300*67e74705SXin Li   void test() {
301*67e74705SXin Li     A a;
302*67e74705SXin Li     a.foo();
303*67e74705SXin Li     a.bar();
304*67e74705SXin Li   }
305*67e74705SXin Li 
306*67e74705SXin Li   // CHECK-LABEL: define linkonce_odr void @_ZN6Test111A3fooEv(
307*67e74705SXin Li   // CHECK-LABEL: define linkonce_odr void @_ZN6Test111A3barEv(
308*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define linkonce_odr hidden void @_ZN6Test111A3fooEv(
309*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define linkonce_odr void @_ZN6Test111A3barEv(
310*67e74705SXin Li }
311*67e74705SXin Li 
312*67e74705SXin Li // Tested at top of file.
313*67e74705SXin Li namespace Test12 {
314*67e74705SXin Li   struct A {
315*67e74705SXin Li     // This is hidden in all cases: the explicit attribute takes
316*67e74705SXin Li     // priority over -fvisibility on the parent.
317*67e74705SXin Li     static int hidden HIDDEN;
318*67e74705SXin Li 
319*67e74705SXin Li     // This is default in all cases because it's only a declaration.
320*67e74705SXin Li     static int visible;
321*67e74705SXin Li   };
322*67e74705SXin Li 
test()323*67e74705SXin Li   void test() {
324*67e74705SXin Li     A::hidden = 0;
325*67e74705SXin Li     A::visible = 0;
326*67e74705SXin Li   }
327*67e74705SXin Li }
328*67e74705SXin Li 
329*67e74705SXin Li // Tested at top of file.
330*67e74705SXin Li namespace Test13 {
331*67e74705SXin Li   struct HIDDEN A {};
332*67e74705SXin Li 
333*67e74705SXin Li   // Should be hidden in all cases.
334*67e74705SXin Li   struct B {
335*67e74705SXin Li     static A a;
336*67e74705SXin Li   };
337*67e74705SXin Li   A B::a;
338*67e74705SXin Li 
339*67e74705SXin Li   // Should be default in all cases.
340*67e74705SXin Li   struct DEFAULT C {
341*67e74705SXin Li     static A a;
342*67e74705SXin Li   };
343*67e74705SXin Li   A C::a;
344*67e74705SXin Li };
345*67e74705SXin Li 
346*67e74705SXin Li // Tested at top of file.
347*67e74705SXin Li namespace Test14 {
348*67e74705SXin Li   // Neither the visibility of the type nor -fvisibility=hidden should
349*67e74705SXin Li   // apply to declarations.
350*67e74705SXin Li   extern struct A *var;
351*67e74705SXin Li 
test()352*67e74705SXin Li   struct A *test() { return var; }
353*67e74705SXin Li }
354*67e74705SXin Li 
355*67e74705SXin Li // rdar://problem/8613093
356*67e74705SXin Li namespace Test15 {
357*67e74705SXin Li   struct A {};
358*67e74705SXin Li   template <class T> struct Temp {
359*67e74705SXin Li     struct Inner {
360*67e74705SXin Li       static char buffer[0];
361*67e74705SXin Li     };
362*67e74705SXin Li   };
363*67e74705SXin Li 
test()364*67e74705SXin Li   char *test() {
365*67e74705SXin Li     return Temp<A>::Inner::buffer;
366*67e74705SXin Li   }
367*67e74705SXin Li }
368*67e74705SXin Li 
369*67e74705SXin Li namespace Test16 {
370*67e74705SXin Li   struct Base1 { virtual void foo(); };
371*67e74705SXin Li   struct Base2 : virtual Base1 { virtual void foo(); };
372*67e74705SXin Li   template <class T> struct A : virtual Base1, Base2 {
373*67e74705SXin Li     virtual void foo();
374*67e74705SXin Li   };
375*67e74705SXin Li   extern template struct A<char>;
376*67e74705SXin Li 
test()377*67e74705SXin Li   void test() {
378*67e74705SXin Li     A<char> a;
379*67e74705SXin Li     a.foo();
380*67e74705SXin Li   }
381*67e74705SXin Li }
382*67e74705SXin Li 
383*67e74705SXin Li namespace Test17 {
384*67e74705SXin Li   struct HIDDEN A {
385*67e74705SXin Li     static void foo();
386*67e74705SXin Li     static void DEFAULT bar();
387*67e74705SXin Li     static void HIDDEN baz();
388*67e74705SXin Li 
389*67e74705SXin Li     struct DEFAULT B {
390*67e74705SXin Li       static void foo();
391*67e74705SXin Li       static void DEFAULT bar();
392*67e74705SXin Li       static void HIDDEN baz();
393*67e74705SXin Li     };
394*67e74705SXin Li   };
395*67e74705SXin Li 
test()396*67e74705SXin Li   void test() {
397*67e74705SXin Li     A::foo();
398*67e74705SXin Li     A::bar();
399*67e74705SXin Li     A::baz();
400*67e74705SXin Li     A::B::foo();
401*67e74705SXin Li     A::B::bar();
402*67e74705SXin Li     A::B::baz();
403*67e74705SXin Li   }
404*67e74705SXin Li   // CHECK: declare hidden void @_ZN6Test171A3fooEv()
405*67e74705SXin Li   // CHECK: declare void @_ZN6Test171A3barEv()
406*67e74705SXin Li   // CHECK: declare hidden void @_ZN6Test171A3bazEv()
407*67e74705SXin Li   // CHECK: declare void @_ZN6Test171A1B3fooEv()
408*67e74705SXin Li   // CHECK: declare void @_ZN6Test171A1B3barEv()
409*67e74705SXin Li   // CHECK: declare hidden void @_ZN6Test171A1B3bazEv()
410*67e74705SXin Li   // CHECK-HIDDEN: declare hidden void @_ZN6Test171A3fooEv()
411*67e74705SXin Li   // CHECK-HIDDEN: declare void @_ZN6Test171A3barEv()
412*67e74705SXin Li   // CHECK-HIDDEN: declare hidden void @_ZN6Test171A3bazEv()
413*67e74705SXin Li   // CHECK-HIDDEN: declare void @_ZN6Test171A1B3fooEv()
414*67e74705SXin Li   // CHECK-HIDDEN: declare void @_ZN6Test171A1B3barEv()
415*67e74705SXin Li   // CHECK-HIDDEN: declare hidden void @_ZN6Test171A1B3bazEv()
416*67e74705SXin Li }
417*67e74705SXin Li 
418*67e74705SXin Li namespace Test18 {
419*67e74705SXin Li   template <class T> struct HIDDEN A {
420*67e74705SXin Li     static void foo();
421*67e74705SXin Li     static void DEFAULT bar();
422*67e74705SXin Li     static void HIDDEN baz();
423*67e74705SXin Li 
424*67e74705SXin Li     struct DEFAULT B {
425*67e74705SXin Li       static void foo();
426*67e74705SXin Li       static void DEFAULT bar();
427*67e74705SXin Li       static void HIDDEN baz();
428*67e74705SXin Li     };
429*67e74705SXin Li   };
430*67e74705SXin Li   struct HIDDEN H;
431*67e74705SXin Li 
test()432*67e74705SXin Li   void test() {
433*67e74705SXin Li     A<int>::foo();
434*67e74705SXin Li     A<int>::bar();
435*67e74705SXin Li     A<int>::baz();
436*67e74705SXin Li     A<int>::B::foo();
437*67e74705SXin Li     A<int>::B::bar();
438*67e74705SXin Li     A<int>::B::baz();
439*67e74705SXin Li     A<H>::foo();
440*67e74705SXin Li     A<H>::bar();
441*67e74705SXin Li     A<H>::baz();
442*67e74705SXin Li     A<H>::B::foo();
443*67e74705SXin Li     A<H>::B::bar();
444*67e74705SXin Li     A<H>::B::baz();
445*67e74705SXin Li   }
446*67e74705SXin Li   // CHECK: declare hidden void @_ZN6Test181AIiE3fooEv()
447*67e74705SXin Li   // CHECK: declare void @_ZN6Test181AIiE3barEv()
448*67e74705SXin Li   // CHECK: declare hidden void @_ZN6Test181AIiE3bazEv()
449*67e74705SXin Li   // CHECK: declare void @_ZN6Test181AIiE1B3fooEv()
450*67e74705SXin Li   // CHECK: declare void @_ZN6Test181AIiE1B3barEv()
451*67e74705SXin Li   // CHECK: declare hidden void @_ZN6Test181AIiE1B3bazEv()
452*67e74705SXin Li   // CHECK: declare hidden void @_ZN6Test181AINS_1HEE3fooEv()
453*67e74705SXin Li   // CHECK: declare hidden void @_ZN6Test181AINS_1HEE3barEv()
454*67e74705SXin Li   // CHECK: declare hidden void @_ZN6Test181AINS_1HEE3bazEv()
455*67e74705SXin Li   // CHECK: declare hidden void @_ZN6Test181AINS_1HEE1B3fooEv()
456*67e74705SXin Li   // CHECK: declare hidden void @_ZN6Test181AINS_1HEE1B3barEv()
457*67e74705SXin Li   // CHECK: declare hidden void @_ZN6Test181AINS_1HEE1B3bazEv()
458*67e74705SXin Li   // CHECK-HIDDEN: declare hidden void @_ZN6Test181AIiE3fooEv()
459*67e74705SXin Li   // CHECK-HIDDEN: declare void @_ZN6Test181AIiE3barEv()
460*67e74705SXin Li   // CHECK-HIDDEN: declare hidden void @_ZN6Test181AIiE3bazEv()
461*67e74705SXin Li   // CHECK-HIDDEN: declare void @_ZN6Test181AIiE1B3fooEv()
462*67e74705SXin Li   // CHECK-HIDDEN: declare void @_ZN6Test181AIiE1B3barEv()
463*67e74705SXin Li   // CHECK-HIDDEN: declare hidden void @_ZN6Test181AIiE1B3bazEv()
464*67e74705SXin Li   // CHECK-HIDDEN: declare hidden void @_ZN6Test181AINS_1HEE3fooEv()
465*67e74705SXin Li   // CHECK-HIDDEN: declare hidden void @_ZN6Test181AINS_1HEE3barEv()
466*67e74705SXin Li   // CHECK-HIDDEN: declare hidden void @_ZN6Test181AINS_1HEE3bazEv()
467*67e74705SXin Li   // CHECK-HIDDEN: declare hidden void @_ZN6Test181AINS_1HEE1B3fooEv()
468*67e74705SXin Li   // CHECK-HIDDEN: declare hidden void @_ZN6Test181AINS_1HEE1B3barEv()
469*67e74705SXin Li   // CHECK-HIDDEN: declare hidden void @_ZN6Test181AINS_1HEE1B3bazEv()
470*67e74705SXin Li }
471*67e74705SXin Li 
472*67e74705SXin Li namespace Test19 {
473*67e74705SXin Li   struct A { A(); ~A(); };
474*67e74705SXin Li 
475*67e74705SXin Li   // Tested at top of file.
foo()476*67e74705SXin Li   template <class T> void foo() {
477*67e74705SXin Li     static A a;
478*67e74705SXin Li   }
479*67e74705SXin Li 
test()480*67e74705SXin Li   void test() {
481*67e74705SXin Li     foo<int>();
482*67e74705SXin Li   }
483*67e74705SXin Li }
484*67e74705SXin Li 
485*67e74705SXin Li // Various things with class template specializations.
486*67e74705SXin Li namespace Test20 {
487*67e74705SXin Li   template <unsigned> struct HIDDEN A {};
488*67e74705SXin Li 
489*67e74705SXin Li   // An explicit specialization inherits the explicit visibility of
490*67e74705SXin Li   // the template.
491*67e74705SXin Li   template <> struct A<0> {
492*67e74705SXin Li     static void test0();
493*67e74705SXin Li     static void test1();
494*67e74705SXin Li   };
495*67e74705SXin Li 
496*67e74705SXin Li   // CHECK-LABEL: define hidden void @_ZN6Test201AILj0EE5test0Ev()
test0()497*67e74705SXin Li   void A<0>::test0() {}
498*67e74705SXin Li 
499*67e74705SXin Li   // CHECK: declare hidden void @_ZN6Test201AILj0EE5test1Ev()
test1()500*67e74705SXin Li   void test1() {
501*67e74705SXin Li     A<0>::test1();
502*67e74705SXin Li   }
503*67e74705SXin Li 
504*67e74705SXin Li   // ...unless that's explicitly overridden.
505*67e74705SXin Li   template <> struct DEFAULT A<1> {
506*67e74705SXin Li     static void test2();
507*67e74705SXin Li     static void test3();
508*67e74705SXin Li   };
509*67e74705SXin Li 
510*67e74705SXin Li   // CHECK-LABEL: define void @_ZN6Test201AILj1EE5test2Ev()
test2()511*67e74705SXin Li   void A<1>::test2() {}
512*67e74705SXin Li 
513*67e74705SXin Li   // CHECK: declare void @_ZN6Test201AILj1EE5test3Ev()
test3()514*67e74705SXin Li   void test3() {
515*67e74705SXin Li     A<1>::test3();
516*67e74705SXin Li   }
517*67e74705SXin Li 
518*67e74705SXin Li   // <rdar://problem/8778497>
519*67e74705SXin Li   // But we should assume that an unknown specialization has the
520*67e74705SXin Li   // explicit visibility settings of the template.
521*67e74705SXin Li   template <class T> struct B {
test4Test20::B522*67e74705SXin Li     static void test4() {}
523*67e74705SXin Li     static void test5();
524*67e74705SXin Li   };
525*67e74705SXin Li 
526*67e74705SXin Li   // CHECK-LABEL: define linkonce_odr hidden void @_ZN6Test201BINS_1AILj2EEEE5test4Ev()
test4()527*67e74705SXin Li   void test4() {
528*67e74705SXin Li     B<A<2> >::test4();
529*67e74705SXin Li   }
530*67e74705SXin Li 
531*67e74705SXin Li   // CHECK: declare hidden void @_ZN6Test201BINS_1AILj2EEEE5test5Ev()
test5()532*67e74705SXin Li   void test5() {
533*67e74705SXin Li     B<A<2> >::test5();
534*67e74705SXin Li   }
535*67e74705SXin Li }
536*67e74705SXin Li 
537*67e74705SXin Li // PR9371
538*67e74705SXin Li namespace test21 {
539*67e74705SXin Li   enum En { en };
540*67e74705SXin Li   template<En> struct A {
footest21::A541*67e74705SXin Li     DEFAULT void foo() {}
542*67e74705SXin Li   };
543*67e74705SXin Li 
544*67e74705SXin Li   // CHECK-LABEL: define weak_odr void @_ZN6test211AILNS_2EnE0EE3fooEv(
545*67e74705SXin Li   template void A<en>::foo();
546*67e74705SXin Li }
547*67e74705SXin Li 
548*67e74705SXin Li // rdar://problem/9616154
549*67e74705SXin Li // Visibility on explicit specializations should take precedence.
550*67e74705SXin Li namespace test22 {
551*67e74705SXin Li   class A1 {};
552*67e74705SXin Li   class A2 {};
553*67e74705SXin Li 
554*67e74705SXin Li   template <class T> struct B {};
555*67e74705SXin Li   template <> struct DEFAULT B<A1> {
556*67e74705SXin Li     static void foo();
bartest22::B557*67e74705SXin Li     static void bar() {}
558*67e74705SXin Li   };
559*67e74705SXin Li   template <> struct B<A2> {
560*67e74705SXin Li     static void foo();
bartest22::B561*67e74705SXin Li     static void bar() {}
562*67e74705SXin Li   };
563*67e74705SXin Li 
test()564*67e74705SXin Li   void test() {
565*67e74705SXin Li     B<A1>::foo();
566*67e74705SXin Li     B<A1>::bar();
567*67e74705SXin Li     B<A2>::foo();
568*67e74705SXin Li     B<A2>::bar();
569*67e74705SXin Li   }
570*67e74705SXin Li   // CHECK: declare void @_ZN6test221BINS_2A1EE3fooEv()
571*67e74705SXin Li   // CHECK-LABEL: define linkonce_odr void @_ZN6test221BINS_2A1EE3barEv()
572*67e74705SXin Li   // CHECK: declare void @_ZN6test221BINS_2A2EE3fooEv()
573*67e74705SXin Li   // CHECK-LABEL: define linkonce_odr void @_ZN6test221BINS_2A2EE3barEv()
574*67e74705SXin Li   // CHECK-HIDDEN: declare void @_ZN6test221BINS_2A1EE3fooEv()
575*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define linkonce_odr void @_ZN6test221BINS_2A1EE3barEv()
576*67e74705SXin Li   // CHECK-HIDDEN: declare void @_ZN6test221BINS_2A2EE3fooEv()
577*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define linkonce_odr hidden void @_ZN6test221BINS_2A2EE3barEv()
578*67e74705SXin Li }
579*67e74705SXin Li 
580*67e74705SXin Li namespace PR10113 {
581*67e74705SXin Li   namespace foo DEFAULT {
582*67e74705SXin Li     template<typename T>
583*67e74705SXin Li       class bar {
zed()584*67e74705SXin Li       void zed() {}
585*67e74705SXin Li     };
586*67e74705SXin Li   }
587*67e74705SXin Li   template class foo::bar<char>;
588*67e74705SXin Li   // CHECK-LABEL: define weak_odr void @_ZN7PR101133foo3barIcE3zedEv
589*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define weak_odr void @_ZN7PR101133foo3barIcE3zedEv
590*67e74705SXin Li 
591*67e74705SXin Li   struct zed {
592*67e74705SXin Li   };
593*67e74705SXin Li   template class foo::bar<zed>;
594*67e74705SXin Li   // CHECK-LABEL: define weak_odr void @_ZN7PR101133foo3barINS_3zedEE3zedEv
595*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define weak_odr hidden void @_ZN7PR101133foo3barINS_3zedEE3zedEv
596*67e74705SXin Li }
597*67e74705SXin Li 
598*67e74705SXin Li namespace PR11690 {
599*67e74705SXin Li   template<class T> struct Class {
sizePR11690::Class600*67e74705SXin Li     void size() const {
601*67e74705SXin Li     }
602*67e74705SXin Li   };
603*67e74705SXin Li   template class DEFAULT Class<char>;
604*67e74705SXin Li   // CHECK-LABEL: define weak_odr void @_ZNK7PR116905ClassIcE4sizeEv
605*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define weak_odr void @_ZNK7PR116905ClassIcE4sizeEv
606*67e74705SXin Li 
Method()607*67e74705SXin Li   template<class T> void Method() {}
608*67e74705SXin Li   template  DEFAULT void Method<char>();
609*67e74705SXin Li   // CHECK-LABEL: define weak_odr void @_ZN7PR116906MethodIcEEvv
610*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define weak_odr void @_ZN7PR116906MethodIcEEvv
611*67e74705SXin Li }
612*67e74705SXin Li 
613*67e74705SXin Li namespace PR11690_2 {
614*67e74705SXin Li   namespace foo DEFAULT {
615*67e74705SXin Li     class bar;
616*67e74705SXin Li     template<typename T1, typename T2 = bar>
617*67e74705SXin Li     class zed {
bar()618*67e74705SXin Li       void bar() {
619*67e74705SXin Li       }
620*67e74705SXin Li     };
621*67e74705SXin Li   }
622*67e74705SXin Li   struct baz {
623*67e74705SXin Li   };
624*67e74705SXin Li   template class foo::zed<baz>;
625*67e74705SXin Li   // CHECK-LABEL: define weak_odr void @_ZN9PR11690_23foo3zedINS_3bazENS0_3barEE3barEv
626*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define weak_odr hidden void @_ZN9PR11690_23foo3zedINS_3bazENS0_3barEE3barEv
627*67e74705SXin Li }
628*67e74705SXin Li 
629*67e74705SXin Li namespace test23 {
630*67e74705SXin Li   // Having a template argument that is explicitly visible should not make
631*67e74705SXin Li   // the template instantiation visible.
632*67e74705SXin Li   template <typename T>
633*67e74705SXin Li   struct X {
ftest23::X634*67e74705SXin Li     static void f() {
635*67e74705SXin Li     }
636*67e74705SXin Li   };
637*67e74705SXin Li 
638*67e74705SXin Li   class DEFAULT A;
639*67e74705SXin Li 
g()640*67e74705SXin Li   void g() {
641*67e74705SXin Li     X<A> y;
642*67e74705SXin Li     y.f();
643*67e74705SXin Li   }
644*67e74705SXin Li   // CHECK-LABEL: define linkonce_odr void @_ZN6test231XINS_1AEE1fEv
645*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define linkonce_odr hidden void @_ZN6test231XINS_1AEE1fEv
646*67e74705SXin Li }
647*67e74705SXin Li 
648*67e74705SXin Li namespace PR12001 {
649*67e74705SXin Li   template <typename P1>
Bind(const P1 & p1)650*67e74705SXin Li   void Bind(const P1& p1) {
651*67e74705SXin Li   }
652*67e74705SXin Li 
653*67e74705SXin Li   class DEFAULT Version { };
654*67e74705SXin Li 
f()655*67e74705SXin Li   void f() {
656*67e74705SXin Li     Bind(Version());
657*67e74705SXin Li   }
658*67e74705SXin Li   // CHECK-LABEL: define linkonce_odr void @_ZN7PR120014BindINS_7VersionEEEvRKT_
659*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define linkonce_odr hidden void @_ZN7PR120014BindINS_7VersionEEEvRKT_
660*67e74705SXin Li }
661*67e74705SXin Li 
662*67e74705SXin Li namespace test24 {
663*67e74705SXin Li   class DEFAULT A { };
664*67e74705SXin Li 
665*67e74705SXin Li   struct S {
666*67e74705SXin Li     template <typename T>
memtest24::S667*67e74705SXin Li     void mem() {}
668*67e74705SXin Li   };
669*67e74705SXin Li 
test()670*67e74705SXin Li   void test() {
671*67e74705SXin Li     S s;
672*67e74705SXin Li     s.mem<A>();
673*67e74705SXin Li   }
674*67e74705SXin Li   // CHECK-LABEL: define linkonce_odr void @_ZN6test241S3memINS_1AEEEvv
675*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define linkonce_odr hidden void @_ZN6test241S3memINS_1AEEEvv
676*67e74705SXin Li }
677*67e74705SXin Li 
678*67e74705SXin Li namespace test26 {
679*67e74705SXin Li   template<typename T>
680*67e74705SXin Li   class C {
681*67e74705SXin Li     DEFAULT  void f();
682*67e74705SXin Li   };
683*67e74705SXin Li 
684*67e74705SXin Li   template<>
f()685*67e74705SXin Li   void C<int>::f() { }
686*67e74705SXin Li 
687*67e74705SXin Li   // CHECK-LABEL: define void @_ZN6test261CIiE1fEv
688*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define void @_ZN6test261CIiE1fEv
689*67e74705SXin Li }
690*67e74705SXin Li 
691*67e74705SXin Li namespace test31 {
692*67e74705SXin Li   struct A {
693*67e74705SXin Li     struct HIDDEN B {
694*67e74705SXin Li       static void DEFAULT baz();
695*67e74705SXin Li     };
696*67e74705SXin Li   };
f()697*67e74705SXin Li   void f() {
698*67e74705SXin Li     A::B::baz();
699*67e74705SXin Li   }
700*67e74705SXin Li   // CHECK: declare void @_ZN6test311A1B3bazEv()
701*67e74705SXin Li   // CHECK-HIDDEN: declare void @_ZN6test311A1B3bazEv()
702*67e74705SXin Li }
703*67e74705SXin Li 
704*67e74705SXin Li namespace test32 {
705*67e74705SXin Li   struct HIDDEN A {
706*67e74705SXin Li     struct DEFAULT B {
707*67e74705SXin Li       void DEFAULT baz();
708*67e74705SXin Li     };
709*67e74705SXin Li   };
baz()710*67e74705SXin Li   void A::B::baz() {
711*67e74705SXin Li   }
712*67e74705SXin Li   // CHECK-LABEL: define void @_ZN6test321A1B3bazEv
713*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define void @_ZN6test321A1B3bazEv
714*67e74705SXin Li }
715*67e74705SXin Li 
716*67e74705SXin Li namespace test33 {
717*67e74705SXin Li   template<typename T>
718*67e74705SXin Li   class foo {
bar()719*67e74705SXin Li     void bar() {}
720*67e74705SXin Li   };
721*67e74705SXin Li   struct HIDDEN zed {
722*67e74705SXin Li   };
723*67e74705SXin Li   template class DEFAULT foo<zed>;
724*67e74705SXin Li   // CHECK-LABEL: define weak_odr void @_ZN6test333fooINS_3zedEE3barEv
725*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define weak_odr void @_ZN6test333fooINS_3zedEE3barEv
726*67e74705SXin Li }
727*67e74705SXin Li 
728*67e74705SXin Li namespace test34 {
729*67e74705SXin Li   struct foo {
730*67e74705SXin Li   };
731*67e74705SXin Li   template<class T>
bar()732*67e74705SXin Li   void bar() {}
733*67e74705SXin Li   template DEFAULT void bar<foo>();
734*67e74705SXin Li   // CHECK-LABEL: define weak_odr void @_ZN6test343barINS_3fooEEEvv
735*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define weak_odr void @_ZN6test343barINS_3fooEEEvv
736*67e74705SXin Li }
737*67e74705SXin Li 
738*67e74705SXin Li namespace test35 {
739*67e74705SXin Li   // This is a really ugly testcase. GCC propagates the DEFAULT in zed's
740*67e74705SXin Li   // definition. It's not really clear what we can do here, because we
741*67e74705SXin Li   // produce the symbols before even seeing the DEFAULT definition of zed.
742*67e74705SXin Li   // FIXME: Maybe the best thing to do here is error?  It's certainly hard
743*67e74705SXin Li   // to argue that this ought to be valid.
744*67e74705SXin Li   template<typename T>
745*67e74705SXin Li   struct DEFAULT foo {
bartest35::foo746*67e74705SXin Li     void bar() {}
747*67e74705SXin Li   };
748*67e74705SXin Li   class zed;
749*67e74705SXin Li   template class foo<zed>;
750*67e74705SXin Li   class DEFAULT zed {
751*67e74705SXin Li   };
752*67e74705SXin Li   // CHECK-LABEL: define weak_odr void @_ZN6test353fooINS_3zedEE3barEv
753*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define weak_odr hidden void @_ZN6test353fooINS_3zedEE3barEv
754*67e74705SXin Li }
755*67e74705SXin Li 
756*67e74705SXin Li namespace test36 {
757*67e74705SXin Li   template<typename T1, typename T2>
758*67e74705SXin Li   class foo {
bar()759*67e74705SXin Li     void bar() {}
760*67e74705SXin Li   };
761*67e74705SXin Li   class DEFAULT S1 {};
762*67e74705SXin Li   struct HIDDEN S2 {};
763*67e74705SXin Li   template class foo<S1, S2>;
764*67e74705SXin Li   // CHECK-LABEL: define weak_odr hidden void @_ZN6test363fooINS_2S1ENS_2S2EE3barEv
765*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define weak_odr hidden void @_ZN6test363fooINS_2S1ENS_2S2EE3barEv
766*67e74705SXin Li }
767*67e74705SXin Li 
768*67e74705SXin Li namespace test37 {
769*67e74705SXin Li   struct HIDDEN foo {
770*67e74705SXin Li   };
771*67e74705SXin Li   template<class T>
bar()772*67e74705SXin Li   DEFAULT void bar() {}
773*67e74705SXin Li   template DEFAULT void bar<foo>();
774*67e74705SXin Li   // CHECK-LABEL: define weak_odr void @_ZN6test373barINS_3fooEEEvv
775*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define weak_odr void @_ZN6test373barINS_3fooEEEvv
776*67e74705SXin Li }
777*67e74705SXin Li 
778*67e74705SXin Li namespace test38 {
779*67e74705SXin Li   template<typename T>
780*67e74705SXin Li   class DEFAULT foo {
bar()781*67e74705SXin Li     void bar() {}
782*67e74705SXin Li   };
783*67e74705SXin Li   struct HIDDEN zed {
784*67e74705SXin Li   };
785*67e74705SXin Li   template class foo<zed>;
786*67e74705SXin Li   // CHECK-LABEL: define weak_odr hidden void @_ZN6test383fooINS_3zedEE3barEv
787*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define weak_odr hidden void @_ZN6test383fooINS_3zedEE3barEv
788*67e74705SXin Li }
789*67e74705SXin Li 
790*67e74705SXin Li namespace test39 {
791*67e74705SXin Li   class DEFAULT default_t;
792*67e74705SXin Li   class HIDDEN hidden_t;
793*67e74705SXin Li   template <class T> class A {
794*67e74705SXin Li     template <class U> class B {
hidden()795*67e74705SXin Li       HIDDEN void hidden() {}
noattr()796*67e74705SXin Li       void noattr() {}
temp()797*67e74705SXin Li       template <class V> void temp() {}
798*67e74705SXin Li     };
799*67e74705SXin Li   };
800*67e74705SXin Li   template class DEFAULT A<hidden_t>;
801*67e74705SXin Li   template class DEFAULT A<hidden_t>::B<hidden_t>;
802*67e74705SXin Li   template void A<hidden_t>::B<hidden_t>::temp<default_t>();
803*67e74705SXin Li   template void A<hidden_t>::B<hidden_t>::temp<hidden_t>();
804*67e74705SXin Li 
805*67e74705SXin Li   // CHECK-LABEL: define weak_odr hidden void @_ZN6test391AINS_8hidden_tEE1BIS1_E6hiddenEv
806*67e74705SXin Li   // CHECK-LABEL: define weak_odr void @_ZN6test391AINS_8hidden_tEE1BIS1_E6noattrEv
807*67e74705SXin Li   // CHECK-LABEL: define weak_odr void @_ZN6test391AINS_8hidden_tEE1BIS1_E4tempINS_9default_tEEEvv
808*67e74705SXin Li 
809*67e74705SXin Li   // GCC produces a default for this one. Why?
810*67e74705SXin Li   // CHECK-LABEL: define weak_odr hidden void @_ZN6test391AINS_8hidden_tEE1BIS1_E4tempIS1_EEvv
811*67e74705SXin Li 
812*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define weak_odr hidden void @_ZN6test391AINS_8hidden_tEE1BIS1_E6hiddenEv
813*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define weak_odr void @_ZN6test391AINS_8hidden_tEE1BIS1_E6noattrEv
814*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define weak_odr void @_ZN6test391AINS_8hidden_tEE1BIS1_E4tempINS_9default_tEEEvv
815*67e74705SXin Li 
816*67e74705SXin Li   // GCC produces a default for this one. Why?
817*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define weak_odr hidden void @_ZN6test391AINS_8hidden_tEE1BIS1_E4tempIS1_EEvv
818*67e74705SXin Li }
819*67e74705SXin Li 
820*67e74705SXin Li namespace test42 {
821*67e74705SXin Li   struct HIDDEN foo {
822*67e74705SXin Li   };
823*67e74705SXin Li   template <class P>
824*67e74705SXin Li   struct bar {
825*67e74705SXin Li   };
826*67e74705SXin Li   template <>
827*67e74705SXin Li   struct HIDDEN bar<foo> {
828*67e74705SXin Li     DEFAULT static void zed();
829*67e74705SXin Li   };
zed()830*67e74705SXin Li   void bar<foo>::zed() {
831*67e74705SXin Li   }
832*67e74705SXin Li   // CHECK-LABEL: define void @_ZN6test423barINS_3fooEE3zedEv
833*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define void @_ZN6test423barINS_3fooEE3zedEv
834*67e74705SXin Li }
835*67e74705SXin Li 
836*67e74705SXin Li namespace test43 {
837*67e74705SXin Li   struct HIDDEN foo {
838*67e74705SXin Li   };
839*67e74705SXin Li   template <class P>
bar()840*67e74705SXin Li   void bar() {
841*67e74705SXin Li   }
842*67e74705SXin Li   template <>
bar()843*67e74705SXin Li   DEFAULT void bar<foo>() {
844*67e74705SXin Li   }
845*67e74705SXin Li   // CHECK-LABEL: define void @_ZN6test433barINS_3fooEEEvv
846*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define void @_ZN6test433barINS_3fooEEEvv
847*67e74705SXin Li }
848*67e74705SXin Li 
849*67e74705SXin Li namespace test44 {
850*67e74705SXin Li   template <typename T>
851*67e74705SXin Li   struct foo {
footest44::foo852*67e74705SXin Li     foo() {}
853*67e74705SXin Li   };
854*67e74705SXin Li   namespace {
855*67e74705SXin Li     struct bar;
856*67e74705SXin Li   }
857*67e74705SXin Li   template struct DEFAULT foo<bar>;
858*67e74705SXin Li   foo<bar> x;
859*67e74705SXin Li   // CHECK-LABEL: define internal void @_ZN6test443fooINS_12_GLOBAL__N_13barEEC1Ev
860*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define internal void @_ZN6test443fooINS_12_GLOBAL__N_13barEEC1Ev
861*67e74705SXin Li }
862*67e74705SXin Li 
863*67e74705SXin Li namespace test45 {
864*67e74705SXin Li   template <typename T>
865*67e74705SXin Li   struct foo {
866*67e74705SXin Li     template <typename T2>
867*67e74705SXin Li     struct bar {
bartest45::foo::bar868*67e74705SXin Li       bar() {};
869*67e74705SXin Li     };
870*67e74705SXin Li   };
871*67e74705SXin Li   namespace {
872*67e74705SXin Li     struct zed;
873*67e74705SXin Li   }
874*67e74705SXin Li   template struct DEFAULT foo<int>::bar<zed>;
875*67e74705SXin Li   foo<int>::bar<zed> x;
876*67e74705SXin Li   // CHECK-LABEL: define internal void @_ZN6test453fooIiE3barINS_12_GLOBAL__N_13zedEEC1Ev
877*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define internal void @_ZN6test453fooIiE3barINS_12_GLOBAL__N_13zedEEC1Ev
878*67e74705SXin Li }
879*67e74705SXin Li 
880*67e74705SXin Li namespace test46 {
881*67e74705SXin Li   template <typename T>
foo()882*67e74705SXin Li   void foo() {
883*67e74705SXin Li   }
884*67e74705SXin Li   namespace {
885*67e74705SXin Li     struct bar;
886*67e74705SXin Li   }
887*67e74705SXin Li   template DEFAULT void foo<bar>();
zed()888*67e74705SXin Li   void zed() {
889*67e74705SXin Li     foo<bar>();
890*67e74705SXin Li   }
891*67e74705SXin Li   // CHECK-LABEL: define internal void @_ZN6test463fooINS_12_GLOBAL__N_13barEEEvv
892*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define internal void @_ZN6test463fooINS_12_GLOBAL__N_13barEEEvv
893*67e74705SXin Li }
894*67e74705SXin Li 
895*67e74705SXin Li namespace test47 {
896*67e74705SXin Li   struct foo {
897*67e74705SXin Li     template <typename T>
bartest47::foo898*67e74705SXin Li     static void bar() {
899*67e74705SXin Li     }
900*67e74705SXin Li   };
901*67e74705SXin Li   namespace {
902*67e74705SXin Li     struct zed;
903*67e74705SXin Li   }
904*67e74705SXin Li   template DEFAULT void foo::bar<zed>();
baz()905*67e74705SXin Li   void baz() {
906*67e74705SXin Li     foo::bar<zed>();
907*67e74705SXin Li   }
908*67e74705SXin Li   // CHECK-LABEL: define internal void @_ZN6test473foo3barINS_12_GLOBAL__N_13zedEEEvv
909*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define internal void @_ZN6test473foo3barINS_12_GLOBAL__N_13zedEEEvv
910*67e74705SXin Li }
911*67e74705SXin Li 
912*67e74705SXin Li namespace test49 {
913*67e74705SXin Li   // Test that we use the visibility of struct foo when instantiating the
914*67e74705SXin Li   // template. Note that is a case where we disagree with gcc, it produces
915*67e74705SXin Li   // a default symbol.
916*67e74705SXin Li 
917*67e74705SXin Li   struct HIDDEN foo {
918*67e74705SXin Li   };
919*67e74705SXin Li 
920*67e74705SXin Li   DEFAULT foo x;
921*67e74705SXin Li 
922*67e74705SXin Li   struct bar {
923*67e74705SXin Li     template<foo *z>
zedtest49::bar924*67e74705SXin Li     void zed() {
925*67e74705SXin Li     }
926*67e74705SXin Li   };
927*67e74705SXin Li 
928*67e74705SXin Li   template void bar::zed<&x>();
929*67e74705SXin Li   // CHECK-LABEL: define weak_odr hidden void @_ZN6test493bar3zedIXadL_ZNS_1xEEEEEvv
930*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define weak_odr hidden void @_ZN6test493bar3zedIXadL_ZNS_1xEEEEEvv
931*67e74705SXin Li }
932*67e74705SXin Li 
933*67e74705SXin Li namespace test50 {
934*67e74705SXin Li   // Test that we use the visibility of struct foo when instantiating the
935*67e74705SXin Li   // template. Note that is a case where we disagree with gcc, it produces
936*67e74705SXin Li   // a default symbol.
937*67e74705SXin Li 
938*67e74705SXin Li   struct HIDDEN foo {
939*67e74705SXin Li   };
940*67e74705SXin Li   DEFAULT foo x;
941*67e74705SXin Li   template<foo *z>
942*67e74705SXin Li   struct DEFAULT bar {
zedtest50::bar943*67e74705SXin Li     void zed() {
944*67e74705SXin Li     }
945*67e74705SXin Li   };
946*67e74705SXin Li   template void bar<&x>::zed();
947*67e74705SXin Li   // CHECK-LABEL: define weak_odr hidden void @_ZN6test503barIXadL_ZNS_1xEEEE3zedEv
948*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define weak_odr hidden void @_ZN6test503barIXadL_ZNS_1xEEEE3zedEv
949*67e74705SXin Li }
950*67e74705SXin Li 
951*67e74705SXin Li namespace test51 {
952*67e74705SXin Li   // Test that we use the visibility of struct foo when instantiating the
953*67e74705SXin Li   // template. Note that is a case where we disagree with gcc, it produces
954*67e74705SXin Li   // a default symbol.
955*67e74705SXin Li 
956*67e74705SXin Li   struct HIDDEN foo {
957*67e74705SXin Li   };
958*67e74705SXin Li   DEFAULT foo x;
959*67e74705SXin Li   template<foo *z>
zed()960*67e74705SXin Li   void DEFAULT zed() {
961*67e74705SXin Li   }
962*67e74705SXin Li   template void zed<&x>();
963*67e74705SXin Li   // CHECK-LABEL: define weak_odr hidden void @_ZN6test513zedIXadL_ZNS_1xEEEEEvv
964*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define weak_odr hidden void @_ZN6test513zedIXadL_ZNS_1xEEEEEvv
965*67e74705SXin Li }
966*67e74705SXin Li 
967*67e74705SXin Li namespace test52 {
968*67e74705SXin Li   // Test that we use the linkage of struct foo when instantiating the
969*67e74705SXin Li   // template. Note that is a case where we disagree with gcc, it produces
970*67e74705SXin Li   // an external symbol.
971*67e74705SXin Li 
972*67e74705SXin Li   namespace {
973*67e74705SXin Li     struct foo {
974*67e74705SXin Li     };
975*67e74705SXin Li   }
976*67e74705SXin Li   template<foo *x>
zed()977*67e74705SXin Li   void zed() {
978*67e74705SXin Li   }
f()979*67e74705SXin Li   void f() {
980*67e74705SXin Li     zed<nullptr>();
981*67e74705SXin Li   }
982*67e74705SXin Li   // CHECK-LABEL: define internal void @_ZN6test523zedILPNS_12_GLOBAL__N_13fooE0EEEvv
983*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define internal void @_ZN6test523zedILPNS_12_GLOBAL__N_13fooE0EEEvv
984*67e74705SXin Li }
985*67e74705SXin Li 
986*67e74705SXin Li namespace test53 {
987*67e74705SXin Li   template<typename _Tp > struct vector   {
988*67e74705SXin Li     static void       _M_fill_insert();
989*67e74705SXin Li   };
990*67e74705SXin Li #pragma GCC visibility push(hidden)
991*67e74705SXin Li   // GCC doesn't seem to use the visibility of enums at all, we do.
992*67e74705SXin Li   enum zed {v1};
993*67e74705SXin Li 
994*67e74705SXin Li   // GCC fails to mark this specialization hidden, we mark it.
995*67e74705SXin Li   template<>
996*67e74705SXin Li   struct vector<int> {
997*67e74705SXin Li     static void       _M_fill_insert();
998*67e74705SXin Li   };
foo()999*67e74705SXin Li   void foo() {
1000*67e74705SXin Li     vector<unsigned>::_M_fill_insert();
1001*67e74705SXin Li     vector<int>::_M_fill_insert();
1002*67e74705SXin Li     vector<zed>::_M_fill_insert();
1003*67e74705SXin Li   }
1004*67e74705SXin Li #pragma GCC visibility pop
1005*67e74705SXin Li   // CHECK: declare void @_ZN6test536vectorIjE14_M_fill_insertEv
1006*67e74705SXin Li   // CHECK-HIDDEN: declare void @_ZN6test536vectorIjE14_M_fill_insertEv
1007*67e74705SXin Li   // CHECK: declare hidden void @_ZN6test536vectorIiE14_M_fill_insertEv
1008*67e74705SXin Li   // CHECK-HIDDEN: declare hidden void @_ZN6test536vectorIiE14_M_fill_insertEv
1009*67e74705SXin Li   // CHECK: declare hidden void @_ZN6test536vectorINS_3zedEE14_M_fill_insertEv
1010*67e74705SXin Li   // CHECK-HIDDEN: declare hidden void @_ZN6test536vectorINS_3zedEE14_M_fill_insertEv
1011*67e74705SXin Li }
1012*67e74705SXin Li 
1013*67e74705SXin Li namespace test54 {
1014*67e74705SXin Li   template <class T>
1015*67e74705SXin Li   struct foo {
1016*67e74705SXin Li     static void bar();
1017*67e74705SXin Li   };
1018*67e74705SXin Li #pragma GCC visibility push(hidden)
1019*67e74705SXin Li   class zed {
1020*67e74705SXin Li     zed(const zed &);
1021*67e74705SXin Li   };
bah()1022*67e74705SXin Li   void bah() {
1023*67e74705SXin Li     foo<zed>::bar();
1024*67e74705SXin Li   }
1025*67e74705SXin Li #pragma GCC visibility pop
1026*67e74705SXin Li   // CHECK: declare hidden void @_ZN6test543fooINS_3zedEE3barEv
1027*67e74705SXin Li   // CHECK-HIDDEN: declare hidden void @_ZN6test543fooINS_3zedEE3barEv
1028*67e74705SXin Li }
1029*67e74705SXin Li 
1030*67e74705SXin Li namespace test55 {
1031*67e74705SXin Li   template <class T>
1032*67e74705SXin Li   struct HIDDEN foo {
1033*67e74705SXin Li     static void bar();
1034*67e74705SXin Li   };
1035*67e74705SXin Li   template <class T> struct foo;
foobar()1036*67e74705SXin Li   void foobar() {
1037*67e74705SXin Li     foo<int>::bar();
1038*67e74705SXin Li   }
1039*67e74705SXin Li   // CHECK: declare hidden void @_ZN6test553fooIiE3barEv
1040*67e74705SXin Li   // CHECK-HIDDEN: declare hidden void @_ZN6test553fooIiE3barEv
1041*67e74705SXin Li }
1042*67e74705SXin Li 
1043*67e74705SXin Li namespace test56 {
1044*67e74705SXin Li   template <class T> struct foo;
1045*67e74705SXin Li   template <class T>
1046*67e74705SXin Li   struct HIDDEN foo {
1047*67e74705SXin Li     static void bar();
1048*67e74705SXin Li   };
foobar()1049*67e74705SXin Li   void foobar() {
1050*67e74705SXin Li     foo<int>::bar();
1051*67e74705SXin Li   }
1052*67e74705SXin Li   // CHECK: declare hidden void @_ZN6test563fooIiE3barEv
1053*67e74705SXin Li   // CHECK-HIDDEN: declare hidden void @_ZN6test563fooIiE3barEv
1054*67e74705SXin Li }
1055*67e74705SXin Li 
1056*67e74705SXin Li namespace test57 {
1057*67e74705SXin Li #pragma GCC visibility push(hidden)
1058*67e74705SXin Li   template <class T>
1059*67e74705SXin Li   struct foo;
1060*67e74705SXin Li   void bar(foo<int>*);
1061*67e74705SXin Li   template <class T>
1062*67e74705SXin Li   struct foo {
1063*67e74705SXin Li     static void zed();
1064*67e74705SXin Li   };
bah()1065*67e74705SXin Li   void bah() {
1066*67e74705SXin Li     foo<int>::zed();
1067*67e74705SXin Li   }
1068*67e74705SXin Li #pragma GCC visibility pop
1069*67e74705SXin Li   // CHECK: declare hidden void @_ZN6test573fooIiE3zedEv
1070*67e74705SXin Li   // CHECK-HIDDEN: declare hidden void @_ZN6test573fooIiE3zedEv
1071*67e74705SXin Li }
1072*67e74705SXin Li 
1073*67e74705SXin Li namespace test58 {
1074*67e74705SXin Li #pragma GCC visibility push(hidden)
1075*67e74705SXin Li   struct foo;
1076*67e74705SXin Li   template<typename T>
1077*67e74705SXin Li   struct DEFAULT bar {
zedtest58::bar1078*67e74705SXin Li     static void zed() {
1079*67e74705SXin Li     }
1080*67e74705SXin Li   };
bah()1081*67e74705SXin Li   void bah() {
1082*67e74705SXin Li     bar<foo>::zed();
1083*67e74705SXin Li   }
1084*67e74705SXin Li #pragma GCC visibility pop
1085*67e74705SXin Li   // CHECK-LABEL: define linkonce_odr hidden void @_ZN6test583barINS_3fooEE3zedEv
1086*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define linkonce_odr hidden void @_ZN6test583barINS_3fooEE3zedEv
1087*67e74705SXin Li }
1088*67e74705SXin Li 
1089*67e74705SXin Li namespace test59 {
1090*67e74705SXin Li   DEFAULT int f();
1091*67e74705SXin Li   HIDDEN int g();
1092*67e74705SXin Li   typedef int (*foo)();
1093*67e74705SXin Li   template<foo x, foo y>
test()1094*67e74705SXin Li   void test() {}
use()1095*67e74705SXin Li   void use() {
1096*67e74705SXin Li     test<&g, &f>();
1097*67e74705SXin Li     // CHECK-LABEL: define linkonce_odr hidden void @_ZN6test594testIXadL_ZNS_1gEvEEXadL_ZNS_1fEvEEEEvv
1098*67e74705SXin Li     // CHECK-HIDDEN-LABEL: define linkonce_odr hidden void @_ZN6test594testIXadL_ZNS_1gEvEEXadL_ZNS_1fEvEEEEvv
1099*67e74705SXin Li 
1100*67e74705SXin Li     test<&f, &g>();
1101*67e74705SXin Li     // CHECK-LABEL: define linkonce_odr hidden void @_ZN6test594testIXadL_ZNS_1fEvEEXadL_ZNS_1gEvEEEEvv
1102*67e74705SXin Li     // CHECK-HIDDEN-LABEL: define linkonce_odr hidden void @_ZN6test594testIXadL_ZNS_1fEvEEXadL_ZNS_1gEvEEEEvv
1103*67e74705SXin Li   }
1104*67e74705SXin Li }
1105*67e74705SXin Li 
1106*67e74705SXin Li namespace test60 {
1107*67e74705SXin Li   template<int i>
1108*67e74705SXin Li   class HIDDEN a {};
1109*67e74705SXin Li   template<int i>
1110*67e74705SXin Li   class DEFAULT b {};
1111*67e74705SXin Li   template<template<int> class x, template<int> class y>
test()1112*67e74705SXin Li   void test() {}
use()1113*67e74705SXin Li   void use() {
1114*67e74705SXin Li     test<a, b>();
1115*67e74705SXin Li     // CHECK-LABEL: define linkonce_odr hidden void @_ZN6test604testINS_1aENS_1bEEEvv
1116*67e74705SXin Li     // CHECK-HIDDEN-LABEL: define linkonce_odr hidden void @_ZN6test604testINS_1aENS_1bEEEvv
1117*67e74705SXin Li 
1118*67e74705SXin Li     test<b, a>();
1119*67e74705SXin Li     // CHECK-LABEL: define linkonce_odr hidden void @_ZN6test604testINS_1bENS_1aEEEvv
1120*67e74705SXin Li     // CHECK-HIDDEN-LABEL: define linkonce_odr hidden void @_ZN6test604testINS_1bENS_1aEEEvv
1121*67e74705SXin Li   }
1122*67e74705SXin Li }
1123*67e74705SXin Li 
1124*67e74705SXin Li namespace test61 {
1125*67e74705SXin Li   template <typename T1>
1126*67e74705SXin Li   struct Class1
1127*67e74705SXin Li   {
f1test61::Class11128*67e74705SXin Li     void f1() { f2(); }
1129*67e74705SXin Li     inline void f2();
1130*67e74705SXin Li   };
1131*67e74705SXin Li   template<>
f2()1132*67e74705SXin Li   inline void Class1<int>::f2()
1133*67e74705SXin Li   {
1134*67e74705SXin Li   }
g(Class1<int> * x)1135*67e74705SXin Li   void g(Class1<int> *x) {
1136*67e74705SXin Li     x->f1();
1137*67e74705SXin Li   }
1138*67e74705SXin Li }
1139*67e74705SXin Li namespace test61 {
1140*67e74705SXin Li   // Just test that we don't crash. Currently we apply this attribute. Current
1141*67e74705SXin Li   // gcc issues a warning about it being unused since "the type is already
1142*67e74705SXin Li   // defined". We should probably do the same.
1143*67e74705SXin Li   template class HIDDEN Class1<int>;
1144*67e74705SXin Li }
1145*67e74705SXin Li 
1146*67e74705SXin Li namespace test62 {
1147*67e74705SXin Li   template <typename T1>
1148*67e74705SXin Li   struct Class1
1149*67e74705SXin Li   {
f1test62::Class11150*67e74705SXin Li     void f1() { f2(); }
f2test62::Class11151*67e74705SXin Li     inline void f2() {}
1152*67e74705SXin Li   };
1153*67e74705SXin Li   template<>
f2()1154*67e74705SXin Li   inline void Class1<int>::f2()
1155*67e74705SXin Li   {
1156*67e74705SXin Li   }
g(Class1<int> * x)1157*67e74705SXin Li   void g(Class1<int> *x) {
1158*67e74705SXin Li     x->f2();
1159*67e74705SXin Li   }
1160*67e74705SXin Li }
1161*67e74705SXin Li namespace test62 {
1162*67e74705SXin Li   template class HIDDEN Class1<int>;
1163*67e74705SXin Li   // Just test that we don't crash. Currently we apply this attribute. Current
1164*67e74705SXin Li   // gcc issues a warning about it being unused since "the type is already
1165*67e74705SXin Li   // defined". We should probably do the same.
1166*67e74705SXin Li }
1167*67e74705SXin Li 
1168*67e74705SXin Li namespace test63 {
1169*67e74705SXin Li   enum HIDDEN E { E0 };
1170*67e74705SXin Li   struct A {
footest63::A1171*67e74705SXin Li     template <E> static void foo() {}
1172*67e74705SXin Li 
1173*67e74705SXin Li     template <E> struct B {
footest63::A::B1174*67e74705SXin Li       static void foo() {}
1175*67e74705SXin Li     };
1176*67e74705SXin Li   };
1177*67e74705SXin Li 
test()1178*67e74705SXin Li   void test() {
1179*67e74705SXin Li     A::foo<E0>();
1180*67e74705SXin Li     A::B<E0>::foo();
1181*67e74705SXin Li   }
1182*67e74705SXin Li   // CHECK-LABEL: define linkonce_odr hidden void @_ZN6test631A3fooILNS_1EE0EEEvv()
1183*67e74705SXin Li   // CHECK-LABEL: define linkonce_odr hidden void @_ZN6test631A1BILNS_1EE0EE3fooEv()
1184*67e74705SXin Li }
1185*67e74705SXin Li 
1186*67e74705SXin Li // Don't ignore the visibility of template arguments just because we
1187*67e74705SXin Li // explicitly instantiated something.
1188*67e74705SXin Li namespace test64 {
1189*67e74705SXin Li   struct HIDDEN A {};
1190*67e74705SXin Li   template <class P> struct B {
footest64::B1191*67e74705SXin Li     static DEFAULT void foo() {}
1192*67e74705SXin Li   };
1193*67e74705SXin Li 
1194*67e74705SXin Li   template class B<A>;
1195*67e74705SXin Li   // CHECK-LABEL: define weak_odr hidden void @_ZN6test641BINS_1AEE3fooEv()
1196*67e74705SXin Li }
1197*67e74705SXin Li 
1198*67e74705SXin Li namespace test65 {
1199*67e74705SXin Li   class HIDDEN A {};
1200*67e74705SXin Li   template <class T> struct B {
1201*67e74705SXin Li     static void func();
1202*67e74705SXin Li     template <class U> static void funcT1();
1203*67e74705SXin Li     template <class U> static void funcT2();
1204*67e74705SXin Li     class Inner {};
1205*67e74705SXin Li     template <class U> class InnerT {};
1206*67e74705SXin Li   };
1207*67e74705SXin Li   template <template <class T> class Temp> struct C {
footest65::C1208*67e74705SXin Li     static void foo() {}
1209*67e74705SXin Li   };
1210*67e74705SXin Li 
1211*67e74705SXin Li   // CHECK-LABEL: define void @_ZN6test651BINS_1AEE4funcEv()
func()1212*67e74705SXin Li   template <> DEFAULT void B<A>::func() {}
1213*67e74705SXin Li 
1214*67e74705SXin Li   // CHECK-LABEL: define void @_ZN6test651BINS_1AEE6funcT2IS1_EEvv()
funcT2()1215*67e74705SXin Li   template <> template <> DEFAULT void B<A>::funcT2<A>() {}
1216*67e74705SXin Li 
1217*67e74705SXin Li   // CHECK-LABEL: define linkonce_odr void @_ZN6test651BINS_1AEE6funcT1IiEEvv()
1218*67e74705SXin Li   // CHECK-LABEL: define linkonce_odr hidden void @_ZN6test651BINS_1AEE6funcT1IS1_EEvv()
funcT1()1219*67e74705SXin Li   template <> template <class T> DEFAULT void B<A>::funcT1() {}
1220*67e74705SXin Li 
1221*67e74705SXin Li   // CHECK-LABEL: define linkonce_odr void @_ZN6test651BINS_1AEE5Inner3fooEv()
1222*67e74705SXin Li   template <> struct DEFAULT B<A>::Inner {
footest65::B::Inner1223*67e74705SXin Li     static void foo() {}
1224*67e74705SXin Li   };
1225*67e74705SXin Li 
1226*67e74705SXin Li   // CHECK-LABEL: define linkonce_odr void @_ZN6test651BINS_1AEE6InnerTIiE3fooEv()
1227*67e74705SXin Li   // CHECK-LABEL: define linkonce_odr hidden void @_ZN6test651BINS_1AEE6InnerTIS1_E3fooEv()
1228*67e74705SXin Li   template <> template <class U> struct DEFAULT B<A>::InnerT {
footest65::B::InnerT1229*67e74705SXin Li     static void foo() {}
1230*67e74705SXin Li   };
1231*67e74705SXin Li 
test()1232*67e74705SXin Li   void test() {
1233*67e74705SXin Li     B<A>::funcT1<int>();
1234*67e74705SXin Li     B<A>::funcT1<A>();
1235*67e74705SXin Li     B<A>::Inner::foo();
1236*67e74705SXin Li     B<A>::InnerT<int>::foo();
1237*67e74705SXin Li     B<A>::InnerT<A>::foo();
1238*67e74705SXin Li   }
1239*67e74705SXin Li 
1240*67e74705SXin Li   template class C<B<A>::InnerT>;
1241*67e74705SXin Li }
1242*67e74705SXin Li 
1243*67e74705SXin Li namespace test66 {
1244*67e74705SXin Li   template <typename T>
1245*67e74705SXin Li   struct DEFAULT barT {
zedtest66::barT1246*67e74705SXin Li     static void zed() {}
1247*67e74705SXin Li   };
1248*67e74705SXin Li   class foo;
1249*67e74705SXin Li   class DEFAULT foo;
1250*67e74705SXin Li   template struct barT<foo>;
1251*67e74705SXin Li   // CHECK-LABEL: define weak_odr void @_ZN6test664barTINS_3fooEE3zedEv
1252*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define weak_odr void @_ZN6test664barTINS_3fooEE3zedEv
1253*67e74705SXin Li 
1254*67e74705SXin Li   template <int* I>
1255*67e74705SXin Li   struct DEFAULT barI {
zedtest66::barI1256*67e74705SXin Li     static void zed() {}
1257*67e74705SXin Li   };
1258*67e74705SXin Li   extern int I;
1259*67e74705SXin Li   extern int I DEFAULT;
1260*67e74705SXin Li   template struct barI<&I>;
1261*67e74705SXin Li   // CHECK-LABEL: define weak_odr void @_ZN6test664barIIXadL_ZNS_1IEEEE3zedEv
1262*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define weak_odr void @_ZN6test664barIIXadL_ZNS_1IEEEE3zedEv
1263*67e74705SXin Li 
1264*67e74705SXin Li   typedef void (*fType)(void);
1265*67e74705SXin Li   template<fType F>
1266*67e74705SXin Li   struct DEFAULT barF {
zedtest66::barF1267*67e74705SXin Li     static void zed() {}
1268*67e74705SXin Li   };
1269*67e74705SXin Li   void F();
1270*67e74705SXin Li   void F() DEFAULT;
1271*67e74705SXin Li   template struct barF<F>;
1272*67e74705SXin Li   // CHECK-LABEL: define weak_odr void @_ZN6test664barFIXadL_ZNS_1FEvEEE3zedEv
1273*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define weak_odr void @_ZN6test664barFIXadL_ZNS_1FEvEEE3zedEv
1274*67e74705SXin Li }
1275*67e74705SXin Li 
1276*67e74705SXin Li namespace test67 {
1277*67e74705SXin Li   template <typename T>
1278*67e74705SXin Li   struct DEFAULT bar {
zedtest67::bar1279*67e74705SXin Li     static void zed() {}
1280*67e74705SXin Li   };
1281*67e74705SXin Li 
1282*67e74705SXin Li   class foo;
1283*67e74705SXin Li   class compute {
1284*67e74705SXin Li     void f(foo *rootfoo);
1285*67e74705SXin Li   };
1286*67e74705SXin Li   class DEFAULT foo;
1287*67e74705SXin Li 
1288*67e74705SXin Li   template struct bar<foo>;
1289*67e74705SXin Li   // CHECK-LABEL: define weak_odr void @_ZN6test673barINS_3fooEE3zedEv
1290*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define weak_odr void @_ZN6test673barINS_3fooEE3zedEv
1291*67e74705SXin Li }
1292*67e74705SXin Li 
1293*67e74705SXin Li namespace test68 {
1294*67e74705SXin Li   class A { public: ~A(); };
1295*67e74705SXin Li   class f {
1296*67e74705SXin Li   public:
f()1297*67e74705SXin Li     f() {
1298*67e74705SXin Li       static A test;
1299*67e74705SXin Li     }
1300*67e74705SXin Li   };
g()1301*67e74705SXin Li   void g() {
1302*67e74705SXin Li     f a;
1303*67e74705SXin Li   }
1304*67e74705SXin Li   // Check lines at top of file.
1305*67e74705SXin Li }
1306*67e74705SXin Li 
1307*67e74705SXin Li namespace test69 {
1308*67e74705SXin Li   // PR18174
1309*67e74705SXin Li   namespace foo {
1310*67e74705SXin Li     void f();
1311*67e74705SXin Li   }
1312*67e74705SXin Li   namespace foo {
f()1313*67e74705SXin Li     void f() {};
1314*67e74705SXin Li   }
1315*67e74705SXin Li   namespace foo __attribute__((visibility("hidden"))) {
1316*67e74705SXin Li   }
1317*67e74705SXin Li   // CHECK-LABEL: define void @_ZN6test693foo1fEv
1318*67e74705SXin Li   // CHECK-HIDDEN-LABEL: define hidden void @_ZN6test693foo1fEv
1319*67e74705SXin Li }
1320