1 // RUN: clang-cc -fsyntax-only -verify %s
2 
3 // This test concerns the identity of dependent types within the
4 // canonical type system, specifically focusing on the difference
5 // between members of the current instantiation and membmers of an
6 // unknown specialization. This considers C++ [temp.type], which
7 // specifies type equivalence within a template, and C++0x
8 // [temp.dep.type], which defines what it means to be a member of the
9 // current instantiation.
10 
11 template<typename T, typename U>
12 struct X0 {
13   typedef T T_type;
14   typedef U U_type;
15 
16   void f0(T&); // expected-note{{previous}}
17   void f0(typename X0::U_type&);
18   void f0(typename X0::T_type&); // expected-error{{redecl}}
19 
20   void f1(T&); // expected-note{{previous}}
21   void f1(typename X0::U_type&);
22   void f1(typename X0<T, U>::T_type&); // expected-error{{redecl}}
23 
24   void f2(T&); // expected-note{{previous}}
25   void f2(typename X0::U_type&);
26   void f2(typename X0<T_type, U_type>::T_type&); // expected-error{{redecl}}
27 
28   void f3(T&); // expected-note{{previous}}
29   void f3(typename X0::U_type&);
30   void f3(typename ::X0<T_type, U_type>::T_type&); // expected-error{{redecl}}
31 
32   struct X1 {
33     typedef T my_T_type;
34 
35     void g0(T&); // expected-note{{previous}}
36     void g0(typename X0::U_type&);
37     void g0(typename X0::T_type&); // expected-error{{redecl}}
38 
39     void g1(T&); // expected-note{{previous}}
40     void g1(typename X0::U_type&);
41     void g1(typename X0<T, U>::T_type&); // expected-error{{redecl}}
42 
43     void g2(T&); // expected-note{{previous}}
44     void g2(typename X0::U_type&);
45     void g2(typename X0<T_type, U_type>::T_type&); // expected-error{{redecl}}
46 
47     void g3(T&); // expected-note{{previous}}
48     void g3(typename X0::U_type&);
49     void g3(typename ::X0<T_type, U_type>::T_type&); // expected-error{{redecl}}
50 
51     void g4(T&); // expected-note{{previous}}
52     void g4(typename X0::U_type&);
53     void g4(typename X1::my_T_type&); // expected-error{{redecl}}
54 
55     void g5(T&); // expected-note{{previous}}
56     void g5(typename X0::U_type&);
57     void g5(typename X0::X1::my_T_type&); // expected-error{{redecl}}
58 
59     void g6(T&); // expected-note{{previous}}
60     void g6(typename X0::U_type&);
61     void g6(typename X0<T, U>::X1::my_T_type&); // expected-error{{redecl}}
62 
63     void g7(T&); // expected-note{{previous}}
64     void g7(typename X0::U_type&);
65     void g7(typename ::X0<typename X1::my_T_type, U_type>::X1::my_T_type&); // expected-error{{redecl}}
66 
67     void g8(T&); // expected-note{{previous}}
68     void g8(typename X0<U, T_type>::T_type&);
69     void g8(typename ::X0<typename X0<T_type, U>::X1::my_T_type, U_type>::X1::my_T_type&); // expected-error{{redecl}}
70   };
71 };
72 
73 
74 template<typename T, typename U>
75 struct X0<T*, U*> {
76   typedef T T_type;
77   typedef U U_type;
78   typedef T* Tptr;
79   typedef U* Uptr;
80 
81   void f0(T&); // expected-note{{previous}}
82   void f0(typename X0::U_type&);
83   void f0(typename X0::T_type&); // expected-error{{redecl}}
84 
85   void f1(T&); // expected-note{{previous}}
86   void f1(typename X0::U_type&);
87   void f1(typename X0<T*, U*>::T_type&); // expected-error{{redecl}}
88 
89   void f2(T&); // expected-note{{previous}}
90   void f2(typename X0::U_type&);
91   void f2(typename X0<T_type*, U_type*>::T_type&); // expected-error{{redecl}}
92 
93   void f3(T&); // expected-note{{previous}}
94   void f3(typename X0::U_type&);
95   void f3(typename ::X0<T_type*, U_type*>::T_type&); // expected-error{{redecl}}
96 
97   void f4(T&); // expected-note{{previous}}
98   void f4(typename X0::U_type&);
99   void f4(typename ::X0<Tptr, Uptr>::T_type&); // expected-error{{redecl}}
100 
101   void f5(X0*); // expected-note{{previous}}
102   void f5(::X0<T, U>*);
103   void f5(::X0<T*, U*>*); // expected-error{{redecl}}
104 
105   struct X2 {
106     typedef T my_T_type;
107 
108     void g0(T&); // expected-note{{previous}}
109     void g0(typename X0::U_type&);
110     void g0(typename X0::T_type&); // expected-error{{redecl}}
111 
112     void g1(T&); // expected-note{{previous}}
113     void g1(typename X0::U_type&);
114     void g1(typename X0<T*, U*>::T_type&); // expected-error{{redecl}}
115 
116     void g2(T&); // expected-note{{previous}}
117     void g2(typename X0::U_type&);
118     void g2(typename X0<T_type*, U_type*>::T_type&); // expected-error{{redecl}}
119 
120     void g3(T&); // expected-note{{previous}}
121     void g3(typename X0::U_type&);
122     void g3(typename ::X0<T_type*, U_type*>::T_type&); // expected-error{{redecl}}
123 
124     void g4(T&); // expected-note{{previous}}
125     void g4(typename X0::U_type&);
126     void g4(typename X2::my_T_type&); // expected-error{{redecl}}
127 
128     void g5(T&); // expected-note{{previous}}
129     void g5(typename X0::U_type&);
130     void g5(typename X0::X2::my_T_type&); // expected-error{{redecl}}
131 
132     void g6(T&); // expected-note{{previous}}
133     void g6(typename X0::U_type&);
134     void g6(typename X0<T*, U*>::X2::my_T_type&); // expected-error{{redecl}}
135 
136     void g7(T&); // expected-note{{previous}}
137     void g7(typename X0::U_type&);
138     void g7(typename ::X0<typename X2::my_T_type*, U_type*>::X2::my_T_type&); // expected-error{{redecl}}
139 
140     void g8(T&); // expected-note{{previous}}
141     void g8(typename X0<U, T_type>::T_type&);
142     void g8(typename ::X0<typename X0<T_type*, U*>::X2::my_T_type*, U_type*>::X2::my_T_type&); // expected-error{{redecl}}
143   };
144 };
145