1 // RUN: %clang_cc1 -fsyntax-only -verify %s
4 static const bool value
= false;
8 struct is_pointer
<T
*> {
9 static const bool value
= true;
13 struct is_pointer
<const T
*> {
14 static const bool value
= true;
17 int array0
[is_pointer
<int>::value
? -1 : 1];
18 int array1
[is_pointer
<int*>::value
? 1 : -1];
19 int array2
[is_pointer
<const int*>::value
? 1 : -1];
22 struct is_lvalue_reference
{
23 static const bool value
= false;
27 struct is_lvalue_reference
<T
&> {
28 static const bool value
= true;
31 int lvalue_ref0
[is_lvalue_reference
<int>::value
? -1 : 1];
32 int lvalue_ref1
[is_lvalue_reference
<const int&>::value
? 1 : -1];
36 static const bool value
= false;
40 struct is_const
<const T
> {
41 static const bool value
= true;
44 int is_const0
[is_const
<int>::value
? -1 : 1];
45 int is_const1
[is_const
<const int>::value
? 1 : -1];
46 int is_const2
[is_const
<const volatile int>::value
? 1 : -1];
47 int is_const3
[is_const
<const int [3]>::value
? 1 : -1];
48 int is_const4
[is_const
<const volatile int[3]>::value
? 1 : -1];
49 int is_const5
[is_const
<volatile int[3]>::value
? -1 : 1];
53 static const bool value
= false;
57 struct is_volatile
<volatile T
> {
58 static const bool value
= true;
61 int is_volatile0
[is_volatile
<int>::value
? -1 : 1];
62 int is_volatile1
[is_volatile
<volatile int>::value
? 1 : -1];
63 int is_volatile2
[is_volatile
<const volatile int>::value
? 1 : -1];
64 int is_volatile3
[is_volatile
<volatile char[3]>::value
? 1 : -1];
66 template<typename T
, typename U
>
68 static const bool value
= false;
72 struct is_same
<T
, T
> {
73 static const bool value
= true;
79 int is_same0
[is_same
<int, int>::value
? 1 : -1];
80 int is_same1
[is_same
<int, INT
>::value
? 1 : -1];
81 int is_same2
[is_same
<const int, int>::value
? -1 : 1];
82 int is_same3
[is_same
<int_ptr
, int>::value
? -1 : 1];
85 struct remove_reference
{
90 struct remove_reference
<T
&> {
94 int remove_ref0
[is_same
<remove_reference
<int>::type
, int>::value
? 1 : -1];
95 int remove_ref1
[is_same
<remove_reference
<int&>::type
, int>::value
? 1 : -1];
103 struct remove_const
<const T
> {
107 int remove_const0
[is_same
<remove_const
<const int>::type
, int>::value
? 1 : -1];
108 int remove_const1
[is_same
<remove_const
<const int[3]>::type
, int[3]>::value
? 1 : -1];
111 struct is_incomplete_array
{
112 static const bool value
= false;
116 struct is_incomplete_array
<T
[]> {
117 static const bool value
= true;
120 int incomplete_array0
[is_incomplete_array
<int>::value
? -1 : 1];
121 int incomplete_array1
[is_incomplete_array
<int[1]>::value
? -1 : 1];
122 int incomplete_array2
[is_incomplete_array
<bool[]>::value
? 1 : -1];
123 int incomplete_array3
[is_incomplete_array
<int[]>::value
? 1 : -1];
126 struct is_array_with_4_elements
{
127 static const bool value
= false;
131 struct is_array_with_4_elements
<T
[4]> {
132 static const bool value
= true;
135 int array_with_4_elements0
[is_array_with_4_elements
<int[]>::value
? -1 : 1];
136 int array_with_4_elements1
[is_array_with_4_elements
<int[1]>::value
? -1 : 1];
137 int array_with_4_elements2
[is_array_with_4_elements
<int[4]>::value
? 1 : -1];
138 int array_with_4_elements3
[is_array_with_4_elements
<int[4][2]>::value
? 1 : -1];
141 struct get_array_size
;
143 template<typename T
, unsigned N
>
144 struct get_array_size
<T
[N
]> {
145 static const unsigned value
= N
;
148 int array_size0
[get_array_size
<int[12]>::value
== 12? 1 : -1];
151 struct remove_extent
{
156 struct remove_extent
<T
[]> {
160 template<typename T
, unsigned N
>
161 struct remove_extent
<T
[N
]> {
165 int remove_extent0
[is_same
<remove_extent
<int[][5]>::type
, int[5]>::value
? 1 : -1];
166 int remove_extent1
[is_same
<remove_extent
<const int[][5]>::type
, const int[5]>::value
? 1 : -1];
169 struct is_unary_function
{
170 static const bool value
= false;
173 template<typename T
, typename U
>
174 struct is_unary_function
<T (*)(U
)> {
175 static const bool value
= true;
178 int is_unary_function0
[is_unary_function
<int>::value
? -1 : 1];
179 int is_unary_function1
[is_unary_function
<int (*)()>::value
? -1 : 1];
180 int is_unary_function2
[is_unary_function
<int (*)(int, bool)>::value
? -1 : 1];
181 int is_unary_function3
[is_unary_function
<int (*)(bool)>::value
? 1 : -1];
182 int is_unary_function4
[is_unary_function
<int (*)(int)>::value
? 1 : -1];
185 struct is_unary_function_with_same_return_type_as_argument_type
{
186 static const bool value
= false;
190 struct is_unary_function_with_same_return_type_as_argument_type
<T (*)(T
)> {
191 static const bool value
= true;
194 int is_unary_function5
[is_unary_function_with_same_return_type_as_argument_type
<int>::value
? -1 : 1];
195 int is_unary_function6
[is_unary_function_with_same_return_type_as_argument_type
<int (*)()>::value
? -1 : 1];
196 int is_unary_function7
[is_unary_function_with_same_return_type_as_argument_type
<int (*)(int, bool)>::value
? -1 : 1];
197 int is_unary_function8
[is_unary_function_with_same_return_type_as_argument_type
<int (*)(bool)>::value
? -1 : 1];
198 int is_unary_function9
[is_unary_function_with_same_return_type_as_argument_type
<int (*)(int)>::value
? 1 : -1];
199 int is_unary_function10
[is_unary_function_with_same_return_type_as_argument_type
<int (*)(int, ...)>::value
? -1 : 1];
200 int is_unary_function11
[is_unary_function_with_same_return_type_as_argument_type
<int (* const)(int)>::value
? -1 : 1];
203 struct is_binary_function
{
204 static const bool value
= false;
207 template<typename R
, typename T1
, typename T2
>
208 struct is_binary_function
<R(T1
, T2
)> {
209 static const bool value
= true;
212 int is_binary_function0
[is_binary_function
<int(float, double)>::value
? 1 : -1];
215 struct is_member_pointer
{
216 static const bool value
= false;
219 template<typename T
, typename Class
>
220 struct is_member_pointer
<T
Class::*> {
221 static const bool value
= true;
226 int is_member_pointer0
[is_member_pointer
<int X::*>::value
? 1 : -1];
227 int is_member_pointer1
[is_member_pointer
<const int X::*>::value
? 1 : -1];
228 int is_member_pointer2
[is_member_pointer
<int (X::*)()>::value
? 1 : -1];
229 int is_member_pointer3
[is_member_pointer
<int (X::*)(int) const>::value
? 1 : -1];
230 int is_member_pointer4
[is_member_pointer
<int (X::**)(int) const>::value
? -1 : 1];
231 int is_member_pointer5
[is_member_pointer
<int>::value
? -1 : 1];
234 struct is_member_function_pointer
{
235 static const bool value
= false;
238 template<typename T
, typename Class
>
239 struct is_member_function_pointer
<T (Class::*)()> {
240 static const bool value
= true;
243 template<typename T
, typename Class
>
244 struct is_member_function_pointer
<T (Class::*)() const> {
245 static const bool value
= true;
248 template<typename T
, typename Class
>
249 struct is_member_function_pointer
<T (Class::*)() volatile> {
250 static const bool value
= true;
253 template<typename T
, typename Class
>
254 struct is_member_function_pointer
<T (Class::*)() const volatile> {
255 static const bool value
= true;
258 template<typename T
, typename Class
, typename A1
>
259 struct is_member_function_pointer
<T (Class::*)(A1
)> {
260 static const bool value
= true;
263 template<typename T
, typename Class
, typename A1
>
264 struct is_member_function_pointer
<T (Class::*)(A1
) const> {
265 static const bool value
= true;
268 template<typename T
, typename Class
, typename A1
>
269 struct is_member_function_pointer
<T (Class::*)(A1
) volatile> {
270 static const bool value
= true;
273 template<typename T
, typename Class
, typename A1
>
274 struct is_member_function_pointer
<T (Class::*)(A1
) const volatile> {
275 static const bool value
= true;
278 int is_member_function_pointer0
[
279 is_member_function_pointer
<int X::*>::value
? -1 : 1];
280 int is_member_function_pointer1
[
281 is_member_function_pointer
<int (X::*)()>::value
? 1 : -1];
282 int is_member_function_pointer2
[
283 is_member_function_pointer
<X (X::*)(X
&)>::value
? 1 : -1];
284 int is_member_function_pointer3
[
285 is_member_function_pointer
<int (X::*)() const>::value
? 1 : -1];
286 int is_member_function_pointer4
[
287 is_member_function_pointer
<int (X::*)(float) const>::value
? 1 : -1];
289 // Test substitution of non-dependent arguments back into the template
290 // argument list of the class template partial specialization.
291 template<typename T
, typename ValueType
= T
>
292 struct is_nested_value_type_identity
{
293 static const bool value
= false;
297 struct is_nested_value_type_identity
<T
, typename
T::value_type
> {
298 static const bool value
= true;
302 struct HasValueType
{
303 typedef T value_type
;
306 struct HasIdentityValueType
{
307 typedef HasIdentityValueType value_type
;
310 struct NoValueType
{ };
312 int is_nested_value_type_identity0
[
313 is_nested_value_type_identity
<HasValueType
<int> >::value
? -1 : 1];
314 int is_nested_value_type_identity1
[
315 is_nested_value_type_identity
<HasIdentityValueType
>::value
? 1 : -1];
316 int is_nested_value_type_identity2
[
317 is_nested_value_type_identity
<NoValueType
>::value
? -1 : 1];
320 // C++ [temp.class.spec]p4:
321 template<class T1
, class T2
, int I
> class A
{ }; //#1
322 template<class T
, int I
> class A
<T
, T
*, I
> { }; //#2
323 template<class T1
, class T2
, int I
> class A
<T1
*, T2
, I
> { }; //#3
324 template<class T
> class A
<int, T
*, 5> { }; //#4
325 template<class T1
, class T2
, int I
> class A
<T1
, T2
*, I
> { }; //#5
327 // Redefinition of class template partial specializations
328 template<typename T
, T N
, typename U
> class A0
;
330 template<typename T
, T N
> class A0
<T
, N
, int> { }; // expected-note{{here}}
331 template<typename T
, T N
> class A0
<T
, N
, int>;
332 template<typename T
, T N
> class A0
<T
, N
, int> { }; // expected-error{{redef}}
335 template< int N
> struct A
;
339 template< typename F
>
343 template< typename Protect
, typename Second
>
347 struct C
< T
, A
< N::B
<T
>::value
> >
359 class a
<s
> // expected-error{{partial specialization of 'a' does not use any of its template parameters}}
365 // Check that we do not crash on invalid code that leads to invalid base.
367 template <typename X
>
373 template <typename Z
>
374 class Bar
<0> : public Foo
<Z
> { // expected-error{{partial specialization of 'Bar' does not use any of its template parameters}}
383 template<typename T
> class Foo
;
385 template <typename T
>
386 class Foo
<int> : public Base
<T
> {}; // expected-error{{partial specialization of 'Foo' does not use any of its template parameters}}
388 // verify that getASTRecordLayout doesn't crash on the ClassTemplateSpecializationDecl.
389 constexpr int s
= sizeof(Foo
<int>);