1// RUN: %clang_cc1 -fcxx-exceptions -fexceptions -fsyntax-only -verify %s
2
3// ---------------------------------------------------------------------
4// C++ Functional Casts
5// ---------------------------------------------------------------------
6template<int N>
7struct ValueInit0 {
8  int f() {
9    return int();
10  }
11};
12
13template struct ValueInit0<5>;
14
15template<int N>
16struct FunctionalCast0 {
17  int f() {
18    return int(N);
19  }
20};
21
22template struct FunctionalCast0<5>;
23
24struct X { // expected-note 3 {{candidate constructor (the implicit copy constructor)}}
25  X(int, int); // expected-note 3 {{candidate constructor}}
26};
27
28template<int N, int M>
29struct BuildTemporary0 {
30  X f() {
31    return X(N, M);
32  }
33};
34
35template struct BuildTemporary0<5, 7>;
36
37template<int N, int M>
38struct Temporaries0 {
39  void f() {
40    (void)X(N, M);
41  }
42};
43
44template struct Temporaries0<5, 7>;
45
46// Ensure that both the constructor and the destructor are instantiated by
47// checking for parse errors from each.
48template<int N> struct BadX {
49  BadX() { int a[-N]; } // expected-error {{array with a negative size}}
50  ~BadX() { int a[-N]; } // expected-error {{array with a negative size}}
51};
52
53template<int N>
54struct PR6671 {
55  void f() { (void)BadX<1>(); } // expected-note 2 {{instantiation}}
56};
57template struct PR6671<1>;
58
59// ---------------------------------------------------------------------
60// new/delete expressions
61// ---------------------------------------------------------------------
62struct Y { };
63
64template<typename T>
65struct New0 {
66  T* f(bool x) {
67    if (x)
68      return new T; // expected-error{{no matching}}
69    else
70      return new T();
71  }
72};
73
74template struct New0<int>;
75template struct New0<Y>;
76template struct New0<X>; // expected-note{{instantiation}}
77
78template<typename T, typename Arg1>
79struct New1 {
80  T* f(bool x, Arg1 a1) {
81    return new T(a1); // expected-error{{no matching}}
82  }
83};
84
85template struct New1<int, float>;
86template struct New1<Y, Y>;
87template struct New1<X, Y>; // expected-note{{instantiation}}
88
89template<typename T, typename Arg1, typename Arg2>
90struct New2 {
91  T* f(bool x, Arg1 a1, Arg2 a2) {
92    return new T(a1, a2); // expected-error{{no matching}}
93  }
94};
95
96template struct New2<X, int, float>;
97template struct New2<X, int, int*>; // expected-note{{instantiation}}
98// FIXME: template struct New2<int, int, float>;
99
100// PR5833
101struct New3 {
102  New3();
103
104  void *operator new[](__SIZE_TYPE__) __attribute__((unavailable)); // expected-note{{explicitly made unavailable}}
105};
106
107template<class C>
108void* object_creator() {
109  return new C(); // expected-error{{call to unavailable function 'operator new[]'}}
110}
111
112template void *object_creator<New3[4]>(); // expected-note{{instantiation}}
113
114template<typename T>
115struct Delete0 {
116  void f(T t) {
117    delete t; // expected-error{{cannot delete}}
118    ::delete [] t; // expected-error{{cannot delete}}
119  }
120};
121
122template struct Delete0<int*>;
123template struct Delete0<X*>;
124template struct Delete0<int>; // expected-note{{instantiation}}
125
126namespace PR5755 {
127  template <class T>
128  void Foo() {
129    char* p = 0;
130    delete[] p;
131  }
132
133  void Test() {
134    Foo<int>();
135  }
136}
137
138namespace PR10480 {
139  template<typename T>
140  struct X {
141    X();
142    ~X() {
143      T *ptr = 1; // expected-error{{cannot initialize a variable of type 'int *' with an rvalue of type 'int'}}
144    }
145  };
146
147  template<typename T>
148  void f() {
149    new X<int>[1]; // expected-note{{in instantiation of member function 'PR10480::X<int>::~X' requested here}}
150  }
151
152  template void f<int>();
153}
154
155// ---------------------------------------------------------------------
156// throw expressions
157// ---------------------------------------------------------------------
158template<typename T>
159struct Throw1 {
160  void f(T t) {
161    throw;
162    throw t; // expected-error{{incomplete type}}
163  }
164};
165
166struct Incomplete; // expected-note 2{{forward}}
167
168template struct Throw1<int>;
169template struct Throw1<int*>;
170template struct Throw1<Incomplete*>; // expected-note{{instantiation}}
171
172// ---------------------------------------------------------------------
173// typeid expressions
174// ---------------------------------------------------------------------
175
176namespace std {
177  class type_info;
178}
179
180template<typename T>
181struct TypeId0 {
182  const std::type_info &f(T* ptr) {
183    if (ptr)
184      return typeid(ptr);
185    else
186      return typeid(T); // expected-error{{'typeid' of incomplete type 'Incomplete'}}
187  }
188};
189
190struct Abstract {
191  virtual void f() = 0;
192};
193
194template struct TypeId0<int>;
195template struct TypeId0<Incomplete>; // expected-note{{instantiation of member function}}
196template struct TypeId0<Abstract>;
197
198// ---------------------------------------------------------------------
199// type traits
200// ---------------------------------------------------------------------
201template<typename T>
202struct is_pod {
203  static const bool value = __is_pod(T);
204};
205
206static int is_pod0[is_pod<X>::value? -1 : 1];
207static int is_pod1[is_pod<Y>::value? 1 : -1];
208
209// ---------------------------------------------------------------------
210// initializer lists
211// ---------------------------------------------------------------------
212template<typename T, typename Val1>
213struct InitList1 {
214  void f(Val1 val1) {
215    T x = { val1 };
216  }
217};
218
219struct APair {
220  int *x;
221  const float *y;
222};
223
224template struct InitList1<int[1], float>;
225template struct InitList1<APair, int*>;
226
227template<typename T, typename Val1, typename Val2>
228struct InitList2 {
229  void f(Val1 val1, Val2 val2) {
230    T x = { val1, val2 }; // expected-error{{cannot initialize}}
231  }
232};
233
234template struct InitList2<APair, int*, float*>;
235template struct InitList2<APair, int*, double*>; // expected-note{{instantiation}}
236
237// ---------------------------------------------------------------------
238// member references
239// ---------------------------------------------------------------------
240template<typename T, typename Result>
241struct DotMemRef0 {
242  void f(T t) {
243    Result result = t.m; // expected-error{{non-const lvalue reference to type}}
244  }
245};
246
247struct MemInt {
248  int m;
249};
250
251struct InheritsMemInt : MemInt { };
252
253struct MemIntFunc {
254  static int m(int);
255};
256
257template struct DotMemRef0<MemInt, int&>;
258template struct DotMemRef0<InheritsMemInt, int&>;
259template struct DotMemRef0<MemIntFunc, int (*)(int)>;
260template struct DotMemRef0<MemInt, float&>; // expected-note{{instantiation}}
261
262template<typename T, typename Result>
263struct ArrowMemRef0 {
264  void f(T t) {
265    Result result = t->m; // expected-error 2{{non-const lvalue reference}}
266  }
267};
268
269template<typename T>
270struct ArrowWrapper {
271  T operator->();
272};
273
274template struct ArrowMemRef0<MemInt*, int&>;
275template struct ArrowMemRef0<InheritsMemInt*, int&>;
276template struct ArrowMemRef0<MemIntFunc*, int (*)(int)>;
277template struct ArrowMemRef0<MemInt*, float&>; // expected-note{{instantiation}}
278
279template struct ArrowMemRef0<ArrowWrapper<MemInt*>, int&>;
280template struct ArrowMemRef0<ArrowWrapper<InheritsMemInt*>, int&>;
281template struct ArrowMemRef0<ArrowWrapper<MemIntFunc*>, int (*)(int)>;
282template struct ArrowMemRef0<ArrowWrapper<MemInt*>, float&>; // expected-note{{instantiation}}
283template struct ArrowMemRef0<ArrowWrapper<ArrowWrapper<MemInt*> >, int&>;
284
285struct UnresolvedMemRefArray {
286  int f(int);
287  int f(char);
288};
289UnresolvedMemRefArray Arr[10];
290template<typename U> int UnresolvedMemRefArrayT(U u) {
291  return Arr->f(u);
292}
293template int UnresolvedMemRefArrayT<int>(int);
294
295// FIXME: we should be able to return a MemInt without the reference!
296MemInt &createMemInt(int);
297
298template<int N>
299struct NonDepMemberExpr0 {
300  void f() {
301    createMemInt(N).m = N;
302  }
303};
304
305template struct NonDepMemberExpr0<0>;
306
307template<typename T, typename Result>
308struct MemberFuncCall0 {
309  void f(T t) {
310    Result result = t.f();
311  }
312};
313
314template<typename T>
315struct HasMemFunc0 {
316  T f();
317};
318
319
320template struct MemberFuncCall0<HasMemFunc0<int&>, const int&>;
321
322template<typename Result>
323struct ThisMemberFuncCall0 {
324  Result g();
325
326  void f() {
327    Result r1 = g();
328    Result r2 = this->g();
329  }
330};
331
332template struct ThisMemberFuncCall0<int&>;
333
334template<typename T>
335struct NonDepMemberCall0 {
336  void foo(HasMemFunc0<int&> x) {
337    T result = x.f(); // expected-error{{non-const lvalue reference}}
338  }
339};
340
341template struct NonDepMemberCall0<int&>;
342template struct NonDepMemberCall0<const int&>;
343template struct NonDepMemberCall0<float&>; // expected-note{{instantiation}}
344
345
346template<typename T>
347struct QualifiedDeclRef0 {
348  T f() {
349    return is_pod<X>::value; // expected-error{{non-const lvalue reference to type 'int' cannot bind to a value of unrelated type 'const bool'}}
350  }
351};
352
353template struct QualifiedDeclRef0<bool>;
354template struct QualifiedDeclRef0<int&>; // expected-note{{instantiation}}
355