xref: /llvm-project/clang/test/SemaCXX/cxx1z-class-template-argument-deduction.cpp (revision df762a1643bb5b0b3c907611d118c82d4b68a39d)
1 // RUN: %clang_cc1 -std=c++1z -verify %s -DERRORS -Wundefined-func-template
2 // RUN: %clang_cc1 -std=c++1z -verify %s -UERRORS -Wundefined-func-template
3 
4 // This test is split into two because we only produce "undefined internal"
5 // warnings if we didn't produce any errors.
6 #if ERRORS
7 
8 namespace std {
9   using size_t = decltype(sizeof(0));
10   template<typename T> struct initializer_list {
11     const T *p;
12     size_t n;
13     initializer_list();
14   };
15 }
16 
17 template<typename T> constexpr bool has_type(...) { return false; }
18 template<typename T> constexpr bool has_type(T&) { return true; }
19 
20 std::initializer_list il1 = {1, 2, 3, 4, 5};
21 auto il2 = std::initializer_list{1, 2, 3, 4};
22 auto il3 = std::initializer_list{il1};
23 auto il4 = std::initializer_list{il1, il1, il1};
24 static_assert(has_type<std::initializer_list<int>>(il1));
25 static_assert(has_type<std::initializer_list<int>>(il2));
26 static_assert(has_type<std::initializer_list<int>>(il3));
27 static_assert(has_type<std::initializer_list<std::initializer_list<int>>>(il4));
28 
29 template<typename T> struct vector {
30   template<typename Iter> vector(Iter, Iter);
31   vector(std::initializer_list<T>);
32 };
33 
34 template<typename T> vector(std::initializer_list<T>) -> vector<T>;
35 template<typename Iter> explicit vector(Iter, Iter) -> vector<typename Iter::value_type>;
36 template<typename T> explicit vector(std::size_t, T) -> vector<T>;
37 
38 vector v1 = {1, 2, 3, 4};
39 static_assert(has_type<vector<int>>(v1));
40 
41 struct iter { typedef char value_type; } it, end;
42 vector v2(it, end);
43 static_assert(has_type<vector<char>>(v2));
44 
45 vector v3(5, 5);
46 static_assert(has_type<vector<int>>(v3));
47 
48 vector v4 = {it, end};
49 static_assert(has_type<vector<iter>>(v4));
50 
51 vector v5{it, end};
52 static_assert(has_type<vector<iter>>(v5));
53 
54 template<typename ...T> struct tuple { tuple(T...); };
55 template<typename ...T> explicit tuple(T ...t) -> tuple<T...>; // expected-note {{declared}}
56 // FIXME: Remove
57 template<typename ...T> tuple(tuple<T...>) -> tuple<T...>;
58 
59 const int n = 4;
60 tuple ta = tuple{1, 'a', "foo", n};
61 static_assert(has_type<tuple<int, char, const char*, int>>(ta));
62 
63 tuple tb{ta};
64 static_assert(has_type<tuple<int, char, const char*, int>>(tb));
65 
66 // FIXME: This should be tuple<tuple<...>>; when the above guide is removed.
67 tuple tc = {ta};
68 static_assert(has_type<tuple<int, char, const char*, int>>(tc));
69 
70 tuple td = {1, 2, 3}; // expected-error {{selected an explicit deduction guide}}
71 static_assert(has_type<tuple<int, char, const char*, int>>(td));
72 
73 // FIXME: This is a GCC extension for now; if CWG don't allow this, at least
74 // add a warning for it.
75 namespace new_expr {
76   tuple<int> *p = new tuple{0};
77   tuple<float, float> *q = new tuple(1.0f, 2.0f);
78 }
79 
80 namespace ambiguity {
81   template<typename T> struct A {};
82   A(unsigned short) -> A<int>; // expected-note {{candidate}}
83   A(short) -> A<int>; // expected-note {{candidate}}
84   A a = 0; // expected-error {{ambiguous deduction for template arguments of 'A'}}
85 
86   template<typename T> struct B {};
87   template<typename T> B(T(&)(int)) -> B<int>; // expected-note {{candidate function [with T = int]}}
88   template<typename T> B(int(&)(T)) -> B<int>; // expected-note {{candidate function [with T = int]}}
89   int f(int);
90   B b = f; // expected-error {{ambiguous deduction for template arguments of 'B'}}
91 }
92 
93 // FIXME: Revisit this once CWG decides if attributes, and [[deprecated]] in
94 // particular, should be permitted here.
95 namespace deprecated {
96   template<typename T> struct A { A(int); };
97   [[deprecated]] A(int) -> A<void>; // expected-note {{marked deprecated here}}
98   A a = 0; // expected-warning {{'<deduction guide for A>' is deprecated}}
99 }
100 
101 namespace dependent {
102   template<template<typename...> typename A> decltype(auto) a = A{1, 2, 3};
103   static_assert(has_type<vector<int>>(a<vector>));
104   static_assert(has_type<tuple<int, int, int>>(a<tuple>));
105 
106   struct B {
107     template<typename T> struct X { X(T); };
108     X(int) -> X<int>;
109     template<typename T> using Y = X<T>;
110   };
111   template<typename T> void f() {
112     typename T::X tx = 0;
113     typename T::Y ty = 0;
114   }
115   template void f<B>();
116 
117   template<typename T> struct C { C(T); };
118   template<typename T> C(T) -> C<T>;
119   template<typename T> void g(T a) {
120     C b = 0;
121     C c = a;
122     using U = decltype(b); // expected-note {{previous}}
123     using U = decltype(c); // expected-error {{different types ('C<const char *>' vs 'C<int>')}}
124   }
125   void h() {
126     g(0);
127     g("foo"); // expected-note {{instantiation of}}
128   }
129 }
130 
131 namespace look_into_current_instantiation {
132   template<typename U> struct Q {};
133   template<typename T> struct A {
134     using U = T;
135     template<typename> using V = Q<A<T>::U>;
136     template<typename W = int> A(V<W>);
137   };
138   A a = Q<float>(); // ok, can look through class-scope typedefs and alias
139                     // templates, and members of the current instantiation
140   A<float> &r = a;
141 
142   template<typename T> struct B { // expected-note {{could not match 'B<T>' against 'int'}}
143     struct X {
144       typedef T type;
145     };
146     B(typename X::type); // expected-note {{couldn't infer template argument 'T'}}
147   };
148   B b = 0; // expected-error {{no viable}}
149 
150   // We should have a substitution failure in the immediate context of
151   // deduction when using the C(T, U) constructor (probably; core wording
152   // unclear).
153   template<typename T> struct C {
154     using U = typename T::type;
155     C(T, U);
156   };
157 
158   struct R { R(int); typedef R type; };
159   C(...) -> C<R>;
160 
161   C c = {1, 2};
162 }
163 
164 namespace nondeducible {
165   template<typename A, typename B> struct X {};
166 
167   template<typename A> // expected-note {{non-deducible template parameter 'A'}}
168   X() -> X<A, int>; // expected-error {{deduction guide template contains a template parameter that cannot be deduced}}
169 
170   template<typename A> // expected-note {{non-deducible template parameter 'A'}}
171   X(typename X<A, int>::type) -> X<A, int>; // expected-error {{deduction guide template contains a template parameter that cannot be deduced}}
172 
173   template<typename A = int,
174            typename B> // expected-note {{non-deducible template parameter 'B'}}
175   X(int) -> X<A, B>; // expected-error {{deduction guide template contains a template parameter that cannot be deduced}}
176 
177   template<typename A = int,
178            typename ...B>
179   X(float) -> X<A, B...>; // ok
180 
181   template <typename> struct UnnamedTemplateParam {};
182   template <typename>                                  // expected-note {{non-deducible template parameter (anonymous)}}
183   UnnamedTemplateParam() -> UnnamedTemplateParam<int>; // expected-error {{deduction guide template contains a template parameter that cannot be deduced}}
184 }
185 
186 namespace default_args_from_ctor {
187   template <class A> struct S { S(A = 0) {} };
188   S s(0);
189 
190   template <class A> struct T { template<typename B> T(A = 0, B = 0) {} };
191   T t(0, 0);
192 }
193 
194 namespace transform_params {
195   template<typename T, T N, template<T (*v)[N]> typename U, T (*X)[N]>
196   struct A {
197     template<typename V, V M, V (*Y)[M], template<V (*v)[M]> typename W>
198     A(U<X>, W<Y>);
199 
200     static constexpr T v = N;
201   };
202 
203   int n[12];
204   template<int (*)[12]> struct Q {};
205   Q<&n> qn;
206   A a(qn, qn);
207   static_assert(a.v == 12);
208 
209   template<typename ...T> struct B {
210     template<T ...V> B(const T (&...p)[V]) {
211       constexpr int Vs[] = {V...};
212       static_assert(Vs[0] == 3 && Vs[1] == 4 && Vs[2] == 4);
213     }
214     static constexpr int (*p)(T...) = (int(*)(int, char, char))nullptr;
215   };
216   B b({1, 2, 3}, "foo", {'x', 'y', 'z', 'w'}); // ok
217 
218   template<typename ...T> struct C {
219     template<T ...V, template<T...> typename X>
220       C(X<V...>);
221   };
222   template<int...> struct Y {};
223   C c(Y<0, 1, 2>{});
224 
225   template<typename ...T> struct D {
226     template<T ...V> D(Y<V...>);
227   };
228   D d(Y<0, 1, 2>{});
229 }
230 
231 namespace variadic {
232   int arr3[3], arr4[4];
233 
234   // PR32673
235   template<typename T> struct A {
236     template<typename ...U> A(T, U...);
237   };
238   A a(1, 2, 3);
239 
240   template<typename T> struct B {
241     template<int ...N> B(T, int (&...r)[N]);
242   };
243   B b(1, arr3, arr4);
244 
245   template<typename T> struct C {
246     template<template<typename> typename ...U> C(T, U<int>...);
247   };
248   C c(1, a, b);
249 
250   template<typename ...U> struct X {
251     template<typename T> X(T, U...);
252   };
253   X x(1, 2, 3);
254 
255   template<int ...N> struct Y {
256     template<typename T> Y(T, int (&...r)[N]);
257   };
258   Y y(1, arr3, arr4);
259 
260   template<template<typename> typename ...U> struct Z {
261     template<typename T> Z(T, U<int>...);
262   };
263   Z z(1, a, b);
264 }
265 
266 namespace tuple_tests {
267   // The converting n-ary constructor appears viable, deducing T as an empty
268   // pack (until we check its SFINAE constraints).
269   namespace libcxx_1 {
270     template<class ...T> struct tuple {
271       template<class ...Args> struct X { static const bool value = false; };
272       template<class ...U, bool Y = X<U...>::value> tuple(U &&...u);
273     };
274     tuple a = {1, 2, 3};
275   }
276 
277   // Don't get caught by surprise when X<...> doesn't even exist in the
278   // selected specialization!
279   namespace libcxx_2 {
280     template<class ...T> struct tuple {
281       template<class ...Args> struct X { static const bool value = false; };
282       // Substitution into X<U...>::value succeeds but produces the
283       // value-dependent expression
284       //   tuple<T...>::X<>::value
285       // FIXME: Is that the right behavior?
286       template<class ...U, bool Y = X<U...>::value> tuple(U &&...u);
287     };
288     template <> class tuple<> {};
289     tuple a = {1, 2, 3}; // expected-error {{excess elements in struct initializer}}
290   }
291 
292   namespace libcxx_3 {
293     template<typename ...T> struct scoped_lock {
294       scoped_lock(T...);
295     };
296     template<> struct scoped_lock<> {};
297     scoped_lock l = {};
298   }
299 }
300 
301 namespace dependent {
302   template<typename T> struct X { // expected-note 3{{here}}
303     X(T);
304   };
305   template<typename T> int Var(T t) {
306     X x(t);
307     return X(x) + 1; // expected-error {{invalid operands}}
308   }
309   template<typename T> int Cast(T t) {
310     return X(X(t)) + 1; // expected-error {{invalid operands}}
311   }
312   template<typename T> int Cast2(T t) {
313     return (X)(X)t + 1; // expected-error {{deduction not allowed}}
314   }
315   template<typename T> int Cast3(T t) {
316     return X{X{t}} + 1; // expected-error {{invalid operands}}
317   }
318   template<typename T> int Cast4(T t) {
319     return (X){(X){t}} + 1; // expected-error 2{{deduction not allowed}}
320   }
321   template<typename T> int New(T t) {
322     return X(new X(t)) + 1; // expected-error {{invalid operands}}
323   };
324   template<typename T> int *New2(T t) {
325     return new X(X(t)) * 2; // expected-error {{invalid operands}}
326   };
327   template int Var(float); // expected-note {{instantiation of}}
328   template int Cast(float); // expected-note {{instantiation of}}
329   template int Cast3(float); // expected-note {{instantiation of}}
330   template int New(float); // expected-note {{instantiation of}}
331   template int *New2(float); // expected-note {{instantiation of}}
332   template<typename T> int operator+(X<T>, int);
333   template int Var(int);
334   template int Cast(int);
335   template int New(int);
336 
337   template<template<typename> typename Y> void test() {
338     Y(0);
339     new Y(0);
340     Y y(0);
341   }
342   template void test<X>();
343 }
344 
345 namespace injected_class_name {
346   template<typename T = void> struct A {
347     A();
348     template<typename U> A(A<U>);
349   };
350   A<int> a;
351   A b = a;
352   using T = decltype(a);
353   using T = decltype(b);
354 }
355 
356 namespace member_guides {
357   // PR34520
358   template<class>
359   struct Foo {
360     template <class T> struct Bar {
361       Bar(...) {}
362     };
363     Bar(int) -> Bar<int>;
364   };
365   Foo<int>::Bar b = 0;
366 
367   struct A {
368     template<typename T> struct Public; // expected-note {{declared public}}
369     Public(float) -> Public<float>;
370   protected: // expected-note {{declared protected by intervening access specifier}}
371     template<typename T> struct Protected; // expected-note 2{{declared protected}}
372     Protected(float) -> Protected<float>;
373     Public(int) -> Public<int>; // expected-error {{different access}}
374   private: // expected-note {{declared private by intervening access specifier}}
375     template<typename T> struct Private; // expected-note {{declared private}}
376     Protected(int) -> Protected<int>; // expected-error {{different access}}
377   public: // expected-note 2{{declared public by intervening access specifier}}
378     template<typename T> Public(T) -> Public<T>;
379     template<typename T> Protected(T) -> Protected<T>; // expected-error {{different access}}
380     template<typename T> Private(T) -> Private<T>; // expected-error {{different access}}
381   };
382 }
383 
384 namespace rdar41903969 {
385 template <class T> struct A {};
386 template <class T> struct B;
387 template <class T> struct C {
388   C(A<T>&);
389   C(B<T>&);
390 };
391 
392 void foo(A<int> &a, B<int> &b) {
393   (void)C{b};
394   (void)C{a};
395 }
396 
397 template<typename T> struct X {
398   X(std::initializer_list<T>) = delete;
399   X(const X&);
400 };
401 
402 template <class T> struct D : X<T> {};
403 
404 void bar(D<int>& d) {
405   (void)X{d};
406 }
407 }
408 
409 namespace rdar41330135 {
410 template <int> struct A {};
411 template <class T>
412 struct S {
413   template <class U>
414   S(T a, U t, A<sizeof(t)>);
415 };
416 template <class T> struct D {
417   D(T t, A<sizeof(t)>);
418 };
419 int f() {
420   S s(0, 0, A<sizeof(int)>());
421   D d(0, A<sizeof(int)>());
422 }
423 
424 namespace test_dupls {
425 template<unsigned long> struct X {};
426 template<typename T> struct A {
427   A(T t, X<sizeof(t)>);
428 };
429 A a(0, {});
430 template<typename U> struct B {
431   B(U u, X<sizeof(u)>);
432 };
433 B b(0, {});
434 }
435 
436 }
437 
438 namespace no_crash_on_default_arg {
439 class A {
440   template <typename T> class B {
441     B(int c = 1);
442   };
443   // This used to crash due to unparsed default arg above. The diagnostic could
444   // be improved, but the point of this test is to simply check we do not crash.
445   B(); // expected-error {{deduction guide declaration without trailing return type}}
446 };
447 } // namespace no_crash_on_default_arg
448 
449 #pragma clang diagnostic push
450 #pragma clang diagnostic warning "-Wctad-maybe-unsupported"
451 namespace test_implicit_ctad_warning {
452 
453 template <class T>
454 struct Tag {};
455 
456 template <class T>
457 struct NoExplicit { // expected-note {{add a deduction guide to suppress this warning}}
458   NoExplicit(T) {}
459   NoExplicit(T, int) {}
460 };
461 
462 // expected-warning@+1 {{'NoExplicit' may not intend to support class template argument deduction}}
463 NoExplicit ne(42);
464 
465 template <class U>
466 struct HasExplicit {
467   HasExplicit(U) {}
468   HasExplicit(U, int) {}
469 };
470 template <class U> HasExplicit(U, int) -> HasExplicit<Tag<U>>;
471 
472 HasExplicit he(42);
473 
474 // Motivating examples from (taken from Stephan Lavavej's 2018 Cppcon talk)
475 template <class T, class U>
476 struct AmateurPair { // expected-note {{add a deduction guide to suppress this warning}}
477   T first;
478   U second;
479   explicit AmateurPair(const T &t, const U &u) {}
480 };
481 // expected-warning@+1 {{'AmateurPair' may not intend to support class template argument deduction}}
482 AmateurPair p1(42, "hello world"); // deduces to Pair<int, char[12]>
483 
484 template <class T, class U>
485 struct AmateurPair2 { // expected-note {{add a deduction guide to suppress this warning}}
486   T first;
487   U second;
488   explicit AmateurPair2(T t, U u) {}
489 };
490 // expected-warning@+1 {{'AmateurPair2' may not intend to support class template argument deduction}}
491 AmateurPair2 p2(42, "hello world"); // deduces to Pair2<int, const char*>
492 
493 template <class T, class U>
494 struct ProPair {
495   T first; U second;
496     explicit ProPair(T const& t, U  const& u)  {}
497 };
498 template<class T1, class T2>
499 ProPair(T1, T2) -> ProPair<T1, T2>;
500 ProPair p3(42, "hello world"); // deduces to ProPair<int, const char*>
501 static_assert(__is_same(decltype(p3), ProPair<int, const char*>));
502 
503 // Test that user-defined explicit guides suppress the warning even if they
504 // aren't used as candidates.
505 template <class T>
506 struct TestExplicitCtor {
507   TestExplicitCtor(T) {}
508 };
509 template <class T>
510 explicit TestExplicitCtor(TestExplicitCtor<T> const&) -> TestExplicitCtor<void>;
511 TestExplicitCtor<int> ce1{42};
512 TestExplicitCtor ce2 = ce1;
513 static_assert(__is_same(decltype(ce2), TestExplicitCtor<int>), "");
514 
515 struct allow_ctad_t {
516   allow_ctad_t() = delete;
517 };
518 
519 template <class T>
520 struct TestSuppression {
521   TestSuppression(T) {}
522 };
523 TestSuppression(allow_ctad_t)->TestSuppression<void>;
524 TestSuppression ta("abc");
525 static_assert(__is_same(decltype(ta), TestSuppression<const char *>), "");
526 }
527 #pragma clang diagnostic pop
528 
529 namespace PR41549 {
530 
531 template <class H, class P> struct umm;
532 
533 template <class H = int, class P = int>
534 struct umm {
535   umm(H h = 0, P p = 0);
536 };
537 
538 template <class H, class P> struct umm;
539 
540 umm m(1);
541 
542 }
543 
544 namespace PR45124 {
545   class a { int d; };
546   class b : a {};
547 
548   struct x { ~x(); };
549   template<typename> class y { y(x = x()); };
550   template<typename z> y(z)->y<z>;
551 
552   // Not a constant initializer, but trivial default initialization. We won't
553   // detect this as trivial default initialization if synthesizing the implicit
554   // deduction guide 'template<typename T> y(x = x()) -> Y<T>;' leaves behind a
555   // pending cleanup.
556   __thread b g;
557 }
558 
559 namespace PR47175 {
560   template<typename T> struct A { A(T); T x; };
561   template<typename T> int &&n = A(T()).x;
562   int m = n<int>;
563 }
564 
565 // Ensure we don't crash when CTAD fails.
566 template <typename T1, typename T2>
567 struct Foo {   // expected-note{{candidate function template not viable}}
568   Foo(T1, T2); // expected-note{{candidate function template not viable}}
569 };
570 
571 template <typename... Args>
572 void insert(Args &&...args);
573 
574 void foo() {
575   insert(Foo(2, 2, 2)); // expected-error{{no viable constructor or deduction guide}}
576 }
577 
578 namespace PR52139 {
579   struct Abstract {
580     template <class... Ts>
581     struct overloaded : Ts... {
582       using Ts::operator()...;
583     };
584     template <class... Ts>
585     overloaded(Ts...) -> overloaded<Ts...>;
586 
587   private:
588     virtual void f() = 0;
589   };
590 }
591 
592 namespace function_prototypes {
593   template<class T> using fptr1 = void (*) (T);
594   template<class T> using fptr2 = fptr1<fptr1<T>>;
595 
596   template<class T> void foo0(fptr1<T>) {
597     static_assert(__is_same(T, const char*));
598   }
599   void bar0(const char *const volatile __restrict);
600   void t0() { foo0(&bar0); }
601 
602   template<class T> void foo1(fptr1<const T *>) {
603      static_assert(__is_same(T, char));
604   }
605   void bar1(const char * __restrict);
606   void t1() { foo1(&bar1); }
607 
608   template<class T> void foo2(fptr2<const T *>) {
609     static_assert(__is_same(T, char));
610   }
611   void bar2(fptr1<const char * __restrict>);
612   void t2() { foo2(&bar2); }
613 
614   template<class T> void foo3(fptr1<const T *>) {}
615   void bar3(char * __restrict);
616   void t3() { foo3(&bar3); }
617   // expected-error@-1 {{no matching function for call to 'foo3'}}
618   // expected-note@-4  {{candidate template ignored: cannot deduce a type for 'T' that would make 'const T' equal 'char'}}
619 
620   template<class T> void foo4(fptr2<const T *>) {}
621   void bar4(fptr1<char * __restrict>);
622   void t4() { foo4(&bar4); }
623   // expected-error@-1 {{no matching function for call to 'foo4'}}
624   // expected-note@-4  {{candidate template ignored: cannot deduce a type for 'T' that would make 'const T' equal 'char'}}
625 
626   template<typename T> void foo5(T(T)) {}
627   const int bar5(int);
628   void t5() { foo5(bar5); }
629   // expected-error@-1 {{no matching function for call to 'foo5'}}
630   // expected-note@-4  {{candidate template ignored: deduced conflicting types for parameter 'T' ('const int' vs. 'int')}}
631 
632   struct Foo6 {};
633   template<typename T> void foo6(void(*)(struct Foo6, T)) {}
634   void bar6(Foo6, int);
635   void t6() { foo6(bar6); }
636 }
637 #else
638 
639 // expected-no-diagnostics
640 namespace undefined_warnings {
641   // Make sure we don't get an "undefined but used internal symbol" warning for the deduction guide here.
642   namespace {
643     template <typename T>
644     struct TemplDObj {
645       explicit TemplDObj(T func) noexcept {}
646     };
647     auto test1 = TemplDObj(0);
648 
649     TemplDObj(float) -> TemplDObj<double>;
650     auto test2 = TemplDObj(.0f);
651   }
652 }
653 
654 namespace GH51710 {
655 template<typename T>
656 struct A {
657   A(T f()) {}
658   A(int f(), T) {}
659 
660   A(T array[10]) {}
661   A(int array[10], T) {}
662 };
663 
664 template<typename T>
665 struct B {
666    B(T array[]) {}
667    B(int array[], T) {}
668 };
669 
670 
671 int foo();
672 
673 void bar() {
674   A test1(foo);
675   A test2(foo, 1);
676 
677   int array[10];
678   A test3(array);
679   A test4(array, 1);
680 
681   B test5(array);
682   B test6(array, 1);
683 }
684 } // namespace GH51710
685 
686 #endif
687