1 // RUN: %clang_cc1 -fsyntax-only -fdiagnostics-show-option -Wbind-to-temporary-copy -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: expects an l-value 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}} 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