summaryrefslogtreecommitdiff
path: root/test/SemaTemplate/deduction.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'test/SemaTemplate/deduction.cpp')
-rw-r--r--test/SemaTemplate/deduction.cpp59
1 files changed, 59 insertions, 0 deletions
diff --git a/test/SemaTemplate/deduction.cpp b/test/SemaTemplate/deduction.cpp
index 9471bac91c308..5695cab9a27e5 100644
--- a/test/SemaTemplate/deduction.cpp
+++ b/test/SemaTemplate/deduction.cpp
@@ -348,3 +348,62 @@ namespace deduction_substitution_failure {
template<typename T> int B<T, typename Fail<T>::error> {}; // expected-note {{instantiation of}}
int bi = B<char, char>; // expected-note {{during template argument deduction for variable template partial specialization 'B<T, typename Fail<T>::error>' [with T = char]}}
}
+
+namespace deduction_after_explicit_pack {
+ template<typename ...T, typename U> int *f(T ...t, int &r, U *u) { // expected-note {{couldn't infer template argument 'U'}}
+ return u;
+ }
+ template<typename U, typename ...T> int *g(T ...t, int &r, U *u) {
+ return u;
+ }
+ void h(float a, double b, int c) {
+ // FIXME: Under DR1388, this appears to be valid.
+ f<float&, double&>(a, b, c, &c); // expected-error {{no matching}}
+ g<int, float&, double&>(a, b, c, &c); // ok
+ }
+}
+
+namespace overload_vs_pack {
+ void f(int);
+ void f(float);
+ void g(double);
+
+ template<typename ...T> struct X {};
+ template<typename ...T> void x(T...);
+
+ template<typename ...T> struct Y { typedef int type(typename T::error...); };
+ template<> struct Y<int, float, double> { typedef int type; };
+
+ template<typename ...T> typename Y<T...>::type g1(X<T...>, void (*...fns)(T)); // expected-note {{deduced conflicting types for parameter 'T' (<int, float> vs. <(no value), double>)}}
+ template<typename ...T> typename Y<T...>::type g2(void(*)(T...), void (*...fns)(T)); // expected-note {{deduced conflicting types for parameter 'T' (<int, float> vs. <(no value), double>)}}
+
+ template<typename T> int &h1(decltype(g1(X<int, float, T>(), f, f, g)) *p);
+ template<typename T> float &h1(...);
+
+ template<typename T> int &h2(decltype(g2(x<int, float, T>, f, f, g)) *p);
+ template<typename T> float &h2(...);
+
+ int n1 = g1(X<int, float>(), f, g); // expected-error {{no matching function}}
+ int n2 = g2(x<int, float>, f, g); // expected-error {{no matching function}}
+
+ int &a1 = h1<double>(0); // ok, skip deduction for 'f's, deduce matching value from 'g'
+ int &a2 = h2<double>(0);
+
+ float &b1 = h1<float>(0); // deduce mismatching value from 'g', so we do not trigger instantiation of Y
+ float &b2 = h2<float>(0);
+
+ template<typename ...T> int partial_deduction(void (*...f)(T)); // expected-note {{deduced incomplete pack <(no value), double> for template parameter 'T'}}
+ int pd1 = partial_deduction(f, g); // expected-error {{no matching function}}
+
+ template<typename ...T> int partial_deduction_2(void (*...f)(T), ...); // expected-note {{deduced incomplete pack <(no value), double> for template parameter 'T'}}
+ int pd2 = partial_deduction_2(f, g); // expected-error {{no matching function}}
+
+ namespace cwg_example {
+ void f(char, char);
+ void f(int, int);
+ void x(int, char);
+
+ template<typename T, typename ...U> void j(void(*)(U...), void (*...fns)(T, U));
+ void test() { j(x, f, x); }
+ }
+}