brintos

brintos / llvm-project-archived public Read only

0
0
Text · 6.8 KiB · a1f1988 Raw
231 lines · cpp
1// RUN: %clang_cc1 -std=c++1z -verify %s2 3// Test that we cope with failure to expand a pack.4template<typename ...T> struct Unexpanded : T... {5  using T::f; // expected-error {{unexpanded}}6  using typename T::type; // expected-error {{unexpanded}}7  template<typename ...U> void g(U ...u) { f(u...); } // expected-error {{explicit qualification required to use member 'f' from dependent base class}}8  void h() {9    Unexpanded<type...> *p; // expected-error {{undeclared identifier 'type'}}10  }11};12void test_Unexpanded() {13  struct A { void f(); };14  struct B { void f(int); }; // expected-note {{here}}15  Unexpanded<A, B>().g(0); // expected-note {{instantiation of}}16}17 18// Test using non-type members from pack of base classes.19template<typename ...T> struct A : T... {20  using T::T ...; // expected-note 2{{inherited here}}21  using T::operator() ...;22  using T::operator T* ...;23  using T::h ...;24 25  void f(int n) { h(n); } // expected-error {{ambiguous}}26  void f(int n, int m) { h(n, m); } // expected-error {{member using declaration 'h' instantiates to an empty pack}}27  void g(int n) { (*this)(n); } // expected-error {{ambiguous}}28  void g(int n, int m) { (*this)(n, m); } // expected-error {{does not provide a call operator}}29};30 31namespace test_A {32  struct X {33    X();34    X(int); // expected-note {{candidate}}35    void operator()(int); // expected-note 2{{candidate}}36    operator X *();37    void h(int); // expected-note {{candidate}}38  };39  struct Y {40    Y();41    Y(int, int);42    void operator()(int, int);43    operator Y *();44    void h(int, int);45  };46  struct Z {47    Z();48    Z(int); // expected-note {{candidate}}49    void operator()(int); // expected-note 2{{candidate}}50    operator Z *();51    void h(int); // expected-note {{candidate}}52  };53 54  void f() {55    A<> a;56    a.f(0, 0); // expected-note {{instantiation of}}57    a.g(0, 0); // expected-note {{instantiation of}}58 59    A<X, Y> axy(0);60    A<X, Y>(0, 0);61    axy.f(0);62    axy.f(0, 0);63    axy.g(0);64    axy.g(0, 0);65    axy(0);66    axy(0, 0);67 68    A<X, Y, Z>(0); // expected-error {{ambiguous}}69    A<X, Y, Z> axyz(0, 0);70    axyz.f(0); // expected-note {{instantiation of}}71    axyz.f(0, 0);72    axyz.g(0); // expected-note {{instantiation of}}73    axyz.g(0, 0);74    axyz(0); // expected-error {{ambiguous}}75    axyz(0, 0);76 77    X *x;78    x = a; // expected-error {{incompatible}}79    x = axy;80    x = axyz;81    x = a.operator X*(); // expected-error {{no member}}82    x = axy.operator X*();83    x = axyz.operator X*();84 85    Z *z;86    z = axyz;87    z = axyz.operator Z*();88  }89}90 91// Test using pack of non-type members from single base class.92template<typename X, typename Y, typename ...T> struct B : X, Y {93  using X::operator T* ...;94};95 96namespace test_B {97  struct X { operator int*(); operator float*(); operator char*(); }; // expected-note {{candidate}}98  struct Y { operator int*(); operator float*(); operator char*(); }; // expected-note {{candidate}}99  B<X, Y, int, float> bif;100  int *pi = bif;101  float *pf = bif;102  char *pc = bif; // expected-error {{ambiguous}}103}104 105// Test using type member from pack of base classes.106template<typename ...T> struct C : T... {107  using typename T::type ...; // expected-error {{target of using declaration conflicts}}108  void f() { type value; } // expected-error {{member using declaration 'type' instantiates to an empty pack}}109};110 111namespace test_C {112  struct X { typedef int type; };113  struct Y { typedef int type; }; // expected-note {{conflicting}}114  struct Z { typedef float type; }; // expected-note {{target}}115 116  void f() {117    C<> c;118    c.f(); // expected-note {{instantiation of}}119 120    C<X, Y> cxy;121    cxy.f();122 123    C<X, Y, Z> cxyz; // expected-note {{instantiation of}}124    cxyz.f();125  }126}127 128// Test using pack of non-types at block scope.129template<typename ...T> int fn1() {130  using T::e ...; // expected-error 2{{class member}} expected-note 2{{instead}}131  // expected-error@-1 2{{produces multiple values}}132  return e; // expected-error {{using declaration 'e' instantiates to an empty pack}}133}134 135namespace test_fn1 {136  struct X { static int e; };137  struct Y { typedef int e; };138  inline namespace P { enum E { e }; }139  inline namespace Q { enum F { e }; }140  void f() {141    fn1<>(); // expected-note {{instantiation of}}142    fn1<X>(); // expected-note {{instantiation of}}143    fn1<Y>(); // expected-note {{instantiation of}}144    fn1<E>();145    fn1<E, F>(); // expected-note {{instantiation of}}146    fn1<E, X>(); // expected-note {{instantiation of}}147  }148}149 150// Test using pack of types at block scope.151template<typename ...T> void fn2() {152  // This cannot ever be valid: in order for T::type to be a type, T must be a153  // class, and a class member cannot be named by a block-scope using declaration.154  using typename T::type ...; // expected-error {{class member}}155  type x; // expected-error {{unknown type name 'type'}}156}157 158// Test partial substitution into class-scope pack.159template<typename ...T> auto lambda1() {160  return [](auto x) { // expected-note 1+{{substituting into a lambda}}161    struct A : T::template X<decltype(x)>... { // expected-note 1+{{instantiation of}}162      using T::template X<decltype(x)>::f ...;163      using typename T::template X<decltype(x)>::type ...;164      void g(int n) { f(n); } // expected-error {{empty pack}} expected-error {{expected 2, have 1}} expected-error {{ambiguous}}165      void h() { type value; } // expected-error {{empty pack}}166    };167    return A();168  };169}170 171namespace test_lambda1 {172  struct A {173    template<typename> struct X {174      void f(int); // expected-note {{candidate}}175      using type = int;176    };177  };178  struct B {179    template<typename> struct X {180      void f(int, int); // expected-note {{declared here}}181      using type = int;182    };183  };184  struct C {185    template<typename> struct X {186      void f(int); // expected-note {{candidate}}187      void f(int, int);188      using type = int;189    };190  };191 192  void f() {193    lambda1<>() // expected-note 2{{instantiation of}}194      (0)195      // FIXME: This is poor error recovery196      .g(0); // expected-error {{no member named 'g'}}197    lambda1<A>()198      (0)199      .g(0);200    lambda1<B>()201      (0) // expected-note {{instantiation of}}202      .g(0);203    lambda1<A, B, C>()204      (0) // expected-note {{instantiation of}}205      .g(0);206  }207}208 209namespace p0195r2_example {210  template<typename ...Ts>211  struct Overloader : Ts... {212    using Ts::operator() ...;213  };214 215  template<typename ...Ts>216  constexpr auto make_overloader(Ts &&...ts) {217    return Overloader<Ts...>{static_cast<Ts&&>(ts)...};218  }219 220  void test() {221    auto o = make_overloader(222      [&](int &r) -> int & { return r; }, // expected-note {{candidate function}}223      [&](float &r) -> float & { return r; } // expected-note {{candidate function}}224    );225    int a; float f; double d;226    int &ra = o(a);227    float &rf = o(f);228    double &rd = o(d); // expected-error {{no matching function}}229  }230}231