xref: /aosp_15_r20/external/clang/test/SemaTemplate/current-instantiation.cpp (revision 67e74705e28f6214e480b399dd47ea732279e315)
1*67e74705SXin Li // RUN: %clang_cc1 -fsyntax-only -verify %s
2*67e74705SXin Li 
3*67e74705SXin Li // This test concerns the identity of dependent types within the
4*67e74705SXin Li // canonical type system, specifically focusing on the difference
5*67e74705SXin Li // between members of the current instantiation and members of an
6*67e74705SXin Li // unknown specialization. This considers C++ [temp.type], which
7*67e74705SXin Li // specifies type equivalence within a template, and C++0x
8*67e74705SXin Li // [temp.dep.type], which defines what it means to be a member of the
9*67e74705SXin Li // current instantiation.
10*67e74705SXin Li 
11*67e74705SXin Li template<typename T, typename U>
12*67e74705SXin Li struct X0 {
13*67e74705SXin Li   typedef T T_type;
14*67e74705SXin Li   typedef U U_type;
15*67e74705SXin Li 
16*67e74705SXin Li   void f0(T&); // expected-note{{previous}}
17*67e74705SXin Li   void f0(typename X0::U_type&);
18*67e74705SXin Li   void f0(typename X0::T_type&); // expected-error{{redecl}}
19*67e74705SXin Li 
20*67e74705SXin Li   void f1(T&); // expected-note{{previous}}
21*67e74705SXin Li   void f1(typename X0::U_type&);
22*67e74705SXin Li   void f1(typename X0<T, U>::T_type&); // expected-error{{redecl}}
23*67e74705SXin Li 
24*67e74705SXin Li   void f2(T&); // expected-note{{previous}}
25*67e74705SXin Li   void f2(typename X0::U_type&);
26*67e74705SXin Li   void f2(typename X0<T_type, U_type>::T_type&); // expected-error{{redecl}}
27*67e74705SXin Li 
28*67e74705SXin Li   void f3(T&); // expected-note{{previous}}
29*67e74705SXin Li   void f3(typename X0::U_type&);
30*67e74705SXin Li   void f3(typename ::X0<T_type, U_type>::T_type&); // expected-error{{redecl}}
31*67e74705SXin Li 
32*67e74705SXin Li   struct X1 {
33*67e74705SXin Li     typedef T my_T_type;
34*67e74705SXin Li 
35*67e74705SXin Li     void g0(T&); // expected-note{{previous}}
36*67e74705SXin Li     void g0(typename X0::U_type&);
37*67e74705SXin Li     void g0(typename X0::T_type&); // expected-error{{redecl}}
38*67e74705SXin Li 
39*67e74705SXin Li     void g1(T&); // expected-note{{previous}}
40*67e74705SXin Li     void g1(typename X0::U_type&);
41*67e74705SXin Li     void g1(typename X0<T, U>::T_type&); // expected-error{{redecl}}
42*67e74705SXin Li 
43*67e74705SXin Li     void g2(T&); // expected-note{{previous}}
44*67e74705SXin Li     void g2(typename X0::U_type&);
45*67e74705SXin Li     void g2(typename X0<T_type, U_type>::T_type&); // expected-error{{redecl}}
46*67e74705SXin Li 
47*67e74705SXin Li     void g3(T&); // expected-note{{previous}}
48*67e74705SXin Li     void g3(typename X0::U_type&);
49*67e74705SXin Li     void g3(typename ::X0<T_type, U_type>::T_type&); // expected-error{{redecl}}
50*67e74705SXin Li 
51*67e74705SXin Li     void g4(T&); // expected-note{{previous}}
52*67e74705SXin Li     void g4(typename X0::U_type&);
53*67e74705SXin Li     void g4(typename X1::my_T_type&); // expected-error{{redecl}}
54*67e74705SXin Li 
55*67e74705SXin Li     void g5(T&); // expected-note{{previous}}
56*67e74705SXin Li     void g5(typename X0::U_type&);
57*67e74705SXin Li     void g5(typename X0::X1::my_T_type&); // expected-error{{redecl}}
58*67e74705SXin Li 
59*67e74705SXin Li     void g6(T&); // expected-note{{previous}}
60*67e74705SXin Li     void g6(typename X0::U_type&);
61*67e74705SXin Li     void g6(typename X0<T, U>::X1::my_T_type&); // expected-error{{redecl}}
62*67e74705SXin Li 
63*67e74705SXin Li     void g7(T&); // expected-note{{previous}}
64*67e74705SXin Li     void g7(typename X0::U_type&);
65*67e74705SXin Li     void g7(typename ::X0<typename X1::my_T_type, U_type>::X1::my_T_type&); // expected-error{{redecl}}
66*67e74705SXin Li 
67*67e74705SXin Li     void g8(T&); // expected-note{{previous}}
68*67e74705SXin Li     void g8(typename X0<U, T_type>::T_type&);
69*67e74705SXin Li     void g8(typename ::X0<typename X0<T_type, U>::X1::my_T_type, U_type>::X1::my_T_type&); // expected-error{{redecl}}
70*67e74705SXin Li   };
71*67e74705SXin Li };
72*67e74705SXin Li 
73*67e74705SXin Li 
74*67e74705SXin Li template<typename T, typename U>
75*67e74705SXin Li struct X0<T*, U*> {
76*67e74705SXin Li   typedef T T_type;
77*67e74705SXin Li   typedef U U_type;
78*67e74705SXin Li   typedef T* Tptr;
79*67e74705SXin Li   typedef U* Uptr;
80*67e74705SXin Li 
81*67e74705SXin Li   void f0(T&); // expected-note{{previous}}
82*67e74705SXin Li   void f0(typename X0::U_type&);
83*67e74705SXin Li   void f0(typename X0::T_type&); // expected-error{{redecl}}
84*67e74705SXin Li 
85*67e74705SXin Li   void f1(T&); // expected-note{{previous}}
86*67e74705SXin Li   void f1(typename X0::U_type&);
87*67e74705SXin Li   void f1(typename X0<T*, U*>::T_type&); // expected-error{{redecl}}
88*67e74705SXin Li 
89*67e74705SXin Li   void f2(T&); // expected-note{{previous}}
90*67e74705SXin Li   void f2(typename X0::U_type&);
91*67e74705SXin Li   void f2(typename X0<T_type*, U_type*>::T_type&); // expected-error{{redecl}}
92*67e74705SXin Li 
93*67e74705SXin Li   void f3(T&); // expected-note{{previous}}
94*67e74705SXin Li   void f3(typename X0::U_type&);
95*67e74705SXin Li   void f3(typename ::X0<T_type*, U_type*>::T_type&); // expected-error{{redecl}}
96*67e74705SXin Li 
97*67e74705SXin Li   void f4(T&); // expected-note{{previous}}
98*67e74705SXin Li   void f4(typename X0::U_type&);
99*67e74705SXin Li   void f4(typename ::X0<Tptr, Uptr>::T_type&); // expected-error{{redecl}}
100*67e74705SXin Li 
101*67e74705SXin Li   void f5(X0*); // expected-note{{previous}}
102*67e74705SXin Li   void f5(::X0<T, U>*);
103*67e74705SXin Li   void f5(::X0<T*, U*>*); // expected-error{{redecl}}
104*67e74705SXin Li 
105*67e74705SXin Li   struct X2 {
106*67e74705SXin Li     typedef T my_T_type;
107*67e74705SXin Li 
108*67e74705SXin Li     void g0(T&); // expected-note{{previous}}
109*67e74705SXin Li     void g0(typename X0::U_type&);
110*67e74705SXin Li     void g0(typename X0::T_type&); // expected-error{{redecl}}
111*67e74705SXin Li 
112*67e74705SXin Li     void g1(T&); // expected-note{{previous}}
113*67e74705SXin Li     void g1(typename X0::U_type&);
114*67e74705SXin Li     void g1(typename X0<T*, U*>::T_type&); // expected-error{{redecl}}
115*67e74705SXin Li 
116*67e74705SXin Li     void g2(T&); // expected-note{{previous}}
117*67e74705SXin Li     void g2(typename X0::U_type&);
118*67e74705SXin Li     void g2(typename X0<T_type*, U_type*>::T_type&); // expected-error{{redecl}}
119*67e74705SXin Li 
120*67e74705SXin Li     void g3(T&); // expected-note{{previous}}
121*67e74705SXin Li     void g3(typename X0::U_type&);
122*67e74705SXin Li     void g3(typename ::X0<T_type*, U_type*>::T_type&); // expected-error{{redecl}}
123*67e74705SXin Li 
124*67e74705SXin Li     void g4(T&); // expected-note{{previous}}
125*67e74705SXin Li     void g4(typename X0::U_type&);
126*67e74705SXin Li     void g4(typename X2::my_T_type&); // expected-error{{redecl}}
127*67e74705SXin Li 
128*67e74705SXin Li     void g5(T&); // expected-note{{previous}}
129*67e74705SXin Li     void g5(typename X0::U_type&);
130*67e74705SXin Li     void g5(typename X0::X2::my_T_type&); // expected-error{{redecl}}
131*67e74705SXin Li 
132*67e74705SXin Li     void g6(T&); // expected-note{{previous}}
133*67e74705SXin Li     void g6(typename X0::U_type&);
134*67e74705SXin Li     void g6(typename X0<T*, U*>::X2::my_T_type&); // expected-error{{redecl}}
135*67e74705SXin Li 
136*67e74705SXin Li     void g7(T&); // expected-note{{previous}}
137*67e74705SXin Li     void g7(typename X0::U_type&);
138*67e74705SXin Li     void g7(typename ::X0<typename X2::my_T_type*, U_type*>::X2::my_T_type&); // expected-error{{redecl}}
139*67e74705SXin Li 
140*67e74705SXin Li     void g8(T&); // expected-note{{previous}}
141*67e74705SXin Li     void g8(typename X0<U, T_type>::T_type&);
142*67e74705SXin Li     void g8(typename ::X0<typename X0<T_type*, U*>::X2::my_T_type*, U_type*>::X2::my_T_type&); // expected-error{{redecl}}
143*67e74705SXin Li   };
144*67e74705SXin Li };
145*67e74705SXin Li 
146*67e74705SXin Li template<typename T>
147*67e74705SXin Li struct X1 {
148*67e74705SXin Li   static int *a;
fX1149*67e74705SXin Li   void f(float *b) {
150*67e74705SXin Li     X1<T>::a = b; // expected-error{{incompatible}}
151*67e74705SXin Li     X1<T*>::a = b;
152*67e74705SXin Li   }
153*67e74705SXin Li };
154*67e74705SXin Li 
155*67e74705SXin Li namespace ConstantInCurrentInstantiation {
156*67e74705SXin Li   template<typename T>
157*67e74705SXin Li   struct X {
158*67e74705SXin Li     static const int value = 2;
159*67e74705SXin Li     static int array[value];
160*67e74705SXin Li   };
161*67e74705SXin Li 
162*67e74705SXin Li   template<typename T> const int X<T>::value;
163*67e74705SXin Li 
164*67e74705SXin Li   template<typename T>
165*67e74705SXin Li   int X<T>::array[X<T>::value] = { 1, 2 };
166*67e74705SXin Li }
167*67e74705SXin Li 
168*67e74705SXin Li namespace Expressions {
169*67e74705SXin Li   template <bool b>
170*67e74705SXin Li   struct Bool {
171*67e74705SXin Li     enum anonymous_enum { value = b };
172*67e74705SXin Li   };
173*67e74705SXin Li   struct True : public Bool<true> {};
174*67e74705SXin Li   struct False : public Bool<false> {};
175*67e74705SXin Li 
176*67e74705SXin Li   template <typename T1, typename T2>
177*67e74705SXin Li   struct Is_Same : public False {};
178*67e74705SXin Li   template <typename T>
179*67e74705SXin Li   struct Is_Same<T, T> : public True {};
180*67e74705SXin Li 
181*67e74705SXin Li   template <bool b, typename T = void>
182*67e74705SXin Li   struct Enable_If {};
183*67e74705SXin Li   template <typename T>
184*67e74705SXin Li   struct Enable_If<true, T>  {
185*67e74705SXin Li     typedef T type;
186*67e74705SXin Li   };
187*67e74705SXin Li 
188*67e74705SXin Li   template <typename T>
189*67e74705SXin Li   class Class {
190*67e74705SXin Li   public:
191*67e74705SXin Li     template <typename U>
192*67e74705SXin Li     typename Enable_If<Is_Same<U, Class>::value, void>::type
193*67e74705SXin Li     foo();
194*67e74705SXin Li   };
195*67e74705SXin Li 
196*67e74705SXin Li 
197*67e74705SXin Li   template <typename T>
198*67e74705SXin Li   template <typename U>
199*67e74705SXin Li   typename Enable_If<Is_Same<U, Class<T> >::value, void>::type
foo()200*67e74705SXin Li   Class<T>::foo() {}
201*67e74705SXin Li }
202*67e74705SXin Li 
203*67e74705SXin Li namespace PR9255 {
204*67e74705SXin Li   template<typename T>
205*67e74705SXin Li   class X0  {
206*67e74705SXin Li   public:
207*67e74705SXin Li     class Inner1;
208*67e74705SXin Li 
209*67e74705SXin Li     class Inner2  {
210*67e74705SXin Li     public:
f()211*67e74705SXin Li       void f()
212*67e74705SXin Li       {
213*67e74705SXin Li         Inner1::f.g();
214*67e74705SXin Li       }
215*67e74705SXin Li     };
216*67e74705SXin Li   };
217*67e74705SXin Li }
218*67e74705SXin Li 
219*67e74705SXin Li namespace rdar10194295 {
220*67e74705SXin Li   template<typename XT>
221*67e74705SXin Li   class X {
222*67e74705SXin Li   public:
223*67e74705SXin Li     enum Enum { Yes, No };
224*67e74705SXin Li     template<Enum> void foo();
225*67e74705SXin Li     template<Enum> class Inner;
226*67e74705SXin Li   };
227*67e74705SXin Li 
228*67e74705SXin Li   template<typename XT>
229*67e74705SXin Li   template<typename X<XT>::Enum>
foo()230*67e74705SXin Li   void X<XT>::foo()
231*67e74705SXin Li   {
232*67e74705SXin Li   }
233*67e74705SXin Li 
234*67e74705SXin Li   template<typename XT>
235*67e74705SXin Li   template<typename X<XT>::Enum>
236*67e74705SXin Li   class X<XT>::Inner { };
237*67e74705SXin Li }
238*67e74705SXin Li 
239*67e74705SXin Li namespace RebuildDependentScopeDeclRefExpr {
240*67e74705SXin Li   template<int> struct N {};
241*67e74705SXin Li   template<typename T> struct X {
242*67e74705SXin Li     static const int thing = 0;
243*67e74705SXin Li     N<thing> data();
244*67e74705SXin Li     N<thing> foo();
245*67e74705SXin Li   };
data()246*67e74705SXin Li   template<typename T> N<X<T>::thing> X<T>::data() {}
247*67e74705SXin Li   // FIXME: We should issue a typo-correction here.
foo()248*67e74705SXin Li   template<typename T> N<X<T>::think> X<T>::foo() {} // expected-error {{no member named 'think' in 'X<T>'}}
249*67e74705SXin Li }
250