From 222e2a7620e6520ffaf4fc4e69d79c18da31542e Mon Sep 17 00:00:00 2001 From: "Zancanaro; Carlo" Date: Mon, 24 Sep 2012 09:58:17 +1000 Subject: Add the clang library to the repo (with some of my changes, too). --- .../temp.deduct/temp.deduct.call/p3.cpp | 148 +++++++++++++++++++++ 1 file changed, 148 insertions(+) create mode 100644 clang/test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.call/p3.cpp (limited to 'clang/test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.call/p3.cpp') diff --git a/clang/test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.call/p3.cpp b/clang/test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.call/p3.cpp new file mode 100644 index 0000000..295f080 --- /dev/null +++ b/clang/test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.call/p3.cpp @@ -0,0 +1,148 @@ +// RUN: %clang_cc1 -fsyntax-only -verify %s + +template struct A { }; + +// Top-level cv-qualifiers of P's type are ignored for type deduction. +template A f0(const T); + +void test_f0(int i, const int ci) { + A a0 = f0(i); + A a1 = f0(ci); +} + +// If P is a reference type, the type referred to by P is used for type +// deduction. +template A f1(T&); + +void test_f1(int i, const int ci, volatile int vi) { + A a0 = f1(i); + A a1 = f1(ci); + A a2 = f1(vi); +} + +template struct B { }; +template B g0(T (&array)[N]); +template B g0b(const T (&array)[N]); + +void test_g0() { + int array0[5]; + B b0 = g0(array0); + const int array1[] = { 1, 2, 3}; + B b1 = g0(array1); + B b2 = g0b(array1); +} + +template B g1(const A&); + +void test_g1(A af) { + B b0 = g1(af); + B b1 = g1(A()); +} + +// - If the original P is a reference type, the deduced A (i.e., the type +// referred to by the reference) can be more cv-qualified than the +// transformed A. +template A f2(const T&); + +void test_f2(int i, const int ci, volatile int vi) { + A a0 = f2(i); + A a1 = f2(ci); + A a2 = f2(vi); +} + +// PR5913 +template +void Foo(const T (&a)[N]) { + T x; + x = 0; +} + +const int a[1] = { 0 }; + +void Test() { + Foo(a); +} + +// - The transformed A can be another pointer or pointer to member type that +// can be converted to the deduced A via a qualification conversion (4.4). +template A f3(T * * const * const); + +void test_f3(int ***ip, volatile int ***vip) { + A a0 = f3(ip); + A a1 = f3(vip); +} + +// Also accept conversions for pointer types which require removing +// [[noreturn]]. +namespace noreturn_stripping { + template + void f(R (*function)()); + + void g() __attribute__ ((__noreturn__)); + void h(); + void test() { + f(g); + f(h); + } +} + +// - If P is a class, and P has the form template-id, then A can be a +// derived class of the deduced A. Likewise, if P is a pointer to a class +// of the form template-id, A can be a pointer to a derived class pointed +// to by the deduced A. +template struct C { }; + +struct D : public C { }; +struct E : public D { }; +struct F : A { }; +struct G : A, C { }; + +template + C *f4a(const C&); +template + C *f4b(C); +template + C *f4c(C*); +int *f4c(...); + +void test_f4(D d, E e, F f, G g) { + C *ci1a = f4a(d); + C *ci2a = f4a(e); + C *ci1b = f4b(d); + C *ci2b = f4b(e); + C *ci1c = f4c(&d); + C *ci2c = f4c(&e); + C *ci3c = f4c(&g); + int *ip1 = f4c(&f); +} + +// PR8462 +namespace N { + struct T0; + struct T1; + + template struct B {}; + + struct J : B {}; + struct K : B {}; + + struct D : J, K {}; + + template void F(B); + + void test() + { + D d; + N::F(d); // Fails + N::F(d); // OK + } +} + +namespace PR9233 { + template void f(const T **q); // expected-note{{candidate template ignored: substitution failure [with T = int]}} + + void g(int **p) { + f(p); // expected-error{{no matching function for call to 'f'}} + } + +} -- cgit v1.2.3