Home | History | Annotate | Download | only in dcl.init.ref
      1 // RUN: %clang_cc1 -fsyntax-only -fdiagnostics-show-option -verify %s
      2 
      3 // C++03 requires that we check for a copy constructor when binding a
      4 // reference to a temporary, since we are allowed to make a copy, Even
      5 // though we don't actually make that copy, make sure that we diagnose
      6 // cases where that copy constructor is somehow unavailable.  As an
      7 // extension, this is only a warning.
      8 
      9 struct X1 {
     10   X1();
     11   explicit X1(const X1&);
     12 };
     13 
     14 struct X2 {
     15   X2();
     16 
     17 private:
     18   X2(const X2&); // expected-note{{declared private here}}
     19 };
     20 
     21 struct X3 {
     22   X3();
     23 
     24 private:
     25   X3(X3&); // expected-note{{candidate constructor not viable: no known conversion from 'X3' to 'X3 &' for 1st argument}}
     26 };
     27 
     28 // Check for instantiation of default arguments
     29 template<typename T>
     30 T get_value_badly() {
     31   double *dp = 0;
     32   // The extension doesn't extend far enough to turn this error into a warning.
     33   T *tp = dp; // expected-error{{ cannot initialize a variable of type 'int *' with an lvalue of type 'double *'}}
     34   return T();
     35 }
     36 
     37 template<typename T>
     38 struct X4 {
     39   X4();
     40   X4(const X4&, T = get_value_badly<T>()); // expected-note{{in instantiation of}}
     41 };
     42 
     43 // Check for "dangerous" default arguments that could cause recursion.
     44 struct X5 {
     45   X5();
     46   X5(const X5&, const X5& = X5()); // expected-warning{{no viable constructor copying parameter of type 'X5'}}
     47 };
     48 
     49 void g1(const X1&);
     50 void g2(const X2&);
     51 void g3(const X3&);
     52 void g4(const X4<int>&);
     53 void g5(const X5&);
     54 
     55 void test() {
     56   g1(X1());
     57   g2(X2()); // expected-warning{{C++98 requires an accessible copy constructor for class 'X2' when binding a reference to a temporary; was private [-Wbind-to-temporary-copy]}}
     58   g3(X3()); // expected-warning{{no viable constructor copying parameter of type 'X3'}}
     59   g4(X4<int>());
     60   g5(X5());  // Generates a warning in the default argument.
     61 }
     62 
     63 // Check that unavailable copy constructors still cause SFINAE failures.
     64 template<int> struct int_c { };
     65 
     66 template<typename T> T f(const T&);
     67 
     68 // Would be ambiguous with the next g(), except the instantiation failure in
     69 // sizeof() prevents that.
     70 template<typename T>
     71 int &g(int_c<sizeof(f(T()))> * = 0);
     72 
     73 template<typename T> float &g();
     74 
     75 void h() {
     76   float &fp2 = g<X3>();  // Not ambiguous.
     77 }
     78