Home | History | Annotate | Download | only in SemaCXX
      1 // RUN: %clang_cc1 -fsyntax-only -verify -std=c++11 %s
      2 
      3 struct A { };
      4 A::A() { } // expected-error {{definition of implicitly declared default constructor}}
      5 
      6 struct B { };
      7 B::B(const B&) { } // expected-error {{definition of implicitly declared copy constructor}}
      8 
      9 struct C { };
     10 C& C::operator=(const C&) { return *this; } // expected-error {{definition of implicitly declared copy assignment operator}}
     11 
     12 struct D { };
     13 D::~D() { } // expected-error {{definition of implicitly declared destructor}}
     14 
     15 // Make sure that the special member functions are introduced for
     16 // name-lookup purposes and overload with user-declared
     17 // constructors and assignment operators.
     18 namespace PR6570 {
     19   class A { };
     20 
     21   class B {
     22   public:
     23     B() {}
     24 
     25     B(const A& a) {
     26       operator = (CONST);
     27       operator = (a);
     28     }
     29 
     30     B& operator = (const A& a) {
     31       return *this;
     32     }
     33 
     34     void f(const A &a) {
     35       B b(a);
     36     };
     37 
     38     static const B CONST;
     39   };
     40 
     41 }
     42 
     43 namespace PR7594 {
     44   // If the lazy declaration of special member functions is triggered
     45   // in an out-of-line initializer, make sure the functions aren't in
     46   // the initializer scope. This used to crash Clang:
     47   struct C {
     48     C();
     49     static C *c;
     50   };
     51   C *C::c = new C();
     52 }
     53 
     54 namespace Recursion {
     55   template<typename T> struct InvokeCopyConstructor {
     56     static const T &get();
     57     typedef decltype(T(get())) type; // expected-error {{no matching conver}}
     58   };
     59   struct B;
     60   struct A {
     61     // expected-note@-1 {{while substituting deduced template arguments}}
     62     typedef B type;
     63     template<typename T,
     64              typename = typename InvokeCopyConstructor<typename T::type>::type>
     65     // expected-note@-1 {{in instantiation of template class}}
     66     A(const T &);
     67     // expected-note@-1 {{in instantiation of default argument}}
     68   };
     69   struct B { // expected-note {{candidate constructor (the implicit move }}
     70     B(); // expected-note {{candidate constructor not viable}}
     71     A a;
     72   };
     73   // Triggering the declaration of B's copy constructor causes overload
     74   // resolution to occur for A's copying constructor, which instantiates
     75   // InvokeCopyConstructor<B>, which triggers the declaration of B's copy
     76   // constructor. Notionally, this happens when we get to the end of the
     77   // definition of 'struct B', so there is no declared copy constructor yet.
     78   //
     79   // This behavior is g++-compatible, but isn't exactly right; the class is
     80   // supposed to be incomplete when we implicitly declare its special members.
     81   B b = B();
     82 
     83 
     84   // Another case, which isn't ill-formed under our rules. This is inspired by
     85   // a problem which occurs when combining CGAL with libstdc++-4.7.
     86 
     87   template<typename T> T &&declval();
     88   template<typename T, typename U> struct pair {
     89     pair();
     90     template<typename V, typename W,
     91              typename = decltype(T(declval<const V&>())),
     92              typename = decltype(U(declval<const W&>()))>
     93     pair(const pair<V,W> &);
     94   };
     95 
     96   template<typename K> struct Line;
     97 
     98   template<typename K> struct Vector {
     99     Vector(const Line<K> &l);
    100   };
    101 
    102   template<typename K> struct Point {
    103     Vector<K> v;
    104   };
    105 
    106   template<typename K> struct Line {
    107     pair<Point<K>, Vector<K>> x;
    108   };
    109 
    110   // Trigger declaration of Line copy ctor, which causes substitution into
    111   // pair's templated constructor, which triggers instantiation of the
    112   // definition of Point's copy constructor, which performs overload resolution
    113   // on Vector's constructors, which requires declaring all of Line's
    114   // constructors. That should not find a copy constructor (because we've not
    115   // declared it yet), but by the time we get all the way back here, we should
    116   // find the copy constructor.
    117   Line<void> L1;
    118   Line<void> L2(L1);
    119 }
    120