xref: /minix3/external/bsd/llvm/dist/clang/test/SemaCXX/overloaded-operator.cpp (revision 0a6a1f1d05b60e214de2f05a7310ddd1f0e590e7)
1f4a2713aSLionel Sambuc // RUN: %clang_cc1 -fsyntax-only -verify -std=c++11 %s
2f4a2713aSLionel Sambuc class X { };
3f4a2713aSLionel Sambuc 
4f4a2713aSLionel Sambuc X operator+(X, X);
5f4a2713aSLionel Sambuc 
f(X x)6f4a2713aSLionel Sambuc void f(X x) {
7f4a2713aSLionel Sambuc   x = x + x;
8f4a2713aSLionel Sambuc }
9f4a2713aSLionel Sambuc 
10f4a2713aSLionel Sambuc struct Y;
11f4a2713aSLionel Sambuc struct Z;
12f4a2713aSLionel Sambuc 
13f4a2713aSLionel Sambuc struct Y {
14f4a2713aSLionel Sambuc   Y(const Z&);
15f4a2713aSLionel Sambuc };
16f4a2713aSLionel Sambuc 
17f4a2713aSLionel Sambuc struct Z {
18f4a2713aSLionel Sambuc   Z(const Y&);
19f4a2713aSLionel Sambuc };
20f4a2713aSLionel Sambuc 
21f4a2713aSLionel Sambuc Y operator+(Y, Y);
22f4a2713aSLionel Sambuc bool operator-(Y, Y); // expected-note{{candidate function}}
23f4a2713aSLionel Sambuc bool operator-(Z, Z); // expected-note{{candidate function}}
24f4a2713aSLionel Sambuc 
g(Y y,Z z)25f4a2713aSLionel Sambuc void g(Y y, Z z) {
26f4a2713aSLionel Sambuc   y = y + z;
27f4a2713aSLionel Sambuc   bool b = y - z; // expected-error{{use of overloaded operator '-' is ambiguous}}
28f4a2713aSLionel Sambuc }
29f4a2713aSLionel Sambuc 
30f4a2713aSLionel Sambuc struct A {
31f4a2713aSLionel Sambuc   bool operator==(Z&); // expected-note 2{{candidate function}}
32f4a2713aSLionel Sambuc };
33f4a2713aSLionel Sambuc 
34f4a2713aSLionel Sambuc A make_A();
35f4a2713aSLionel Sambuc 
36f4a2713aSLionel Sambuc bool operator==(A&, Z&); // expected-note 3{{candidate function}}
37f4a2713aSLionel Sambuc 
h(A a,const A ac,Z z)38f4a2713aSLionel Sambuc void h(A a, const A ac, Z z) {
39f4a2713aSLionel Sambuc   make_A() == z; // expected-warning{{equality comparison result unused}}
40f4a2713aSLionel Sambuc   a == z; // expected-error{{use of overloaded operator '==' is ambiguous}}
41f4a2713aSLionel Sambuc   ac == z; // expected-error{{invalid operands to binary expression ('const A' and 'Z')}}
42f4a2713aSLionel Sambuc }
43f4a2713aSLionel Sambuc 
44f4a2713aSLionel Sambuc struct B {
45f4a2713aSLionel Sambuc   bool operator==(const B&) const;
46f4a2713aSLionel Sambuc 
testB47f4a2713aSLionel Sambuc   void test(Z z) {
48f4a2713aSLionel Sambuc     make_A() == z; // expected-warning{{equality comparison result unused}}
49f4a2713aSLionel Sambuc   }
50f4a2713aSLionel Sambuc };
51f4a2713aSLionel Sambuc 
52f4a2713aSLionel Sambuc // we shouldn't see warnings about self-comparison,
53f4a2713aSLionel Sambuc // this is a member function, we dunno what it'll do
i(B b)54f4a2713aSLionel Sambuc bool i(B b)
55f4a2713aSLionel Sambuc {
56f4a2713aSLionel Sambuc   return b == b;
57f4a2713aSLionel Sambuc }
58f4a2713aSLionel Sambuc 
59f4a2713aSLionel Sambuc enum Enum1 { };
60f4a2713aSLionel Sambuc enum Enum2 { };
61f4a2713aSLionel Sambuc 
62f4a2713aSLionel Sambuc struct E1 {
E1E163f4a2713aSLionel Sambuc   E1(Enum1) { }
64f4a2713aSLionel Sambuc };
65f4a2713aSLionel Sambuc 
66f4a2713aSLionel Sambuc struct E2 {
67f4a2713aSLionel Sambuc   E2(Enum2);
68f4a2713aSLionel Sambuc };
69f4a2713aSLionel Sambuc 
70f4a2713aSLionel Sambuc // C++ [over.match.oper]p3 - enum restriction.
71f4a2713aSLionel Sambuc float& operator==(E1, E2);  // expected-note{{candidate function}}
72f4a2713aSLionel Sambuc 
enum_test(Enum1 enum1,Enum2 enum2,E1 e1,E2 e2,Enum1 next_enum1)73f4a2713aSLionel Sambuc void enum_test(Enum1 enum1, Enum2 enum2, E1 e1, E2 e2, Enum1 next_enum1) {
74f4a2713aSLionel Sambuc   float &f1 = (e1 == e2);
75f4a2713aSLionel Sambuc   float &f2 = (enum1 == e2);
76f4a2713aSLionel Sambuc   float &f3 = (e1 == enum2);
77f4a2713aSLionel Sambuc   float &f4 = (enum1 == next_enum1);  // expected-error{{non-const lvalue reference to type 'float' cannot bind to a temporary of type 'bool'}}
78f4a2713aSLionel Sambuc }
79f4a2713aSLionel Sambuc 
80f4a2713aSLionel Sambuc // PR5244 - Argument-dependent lookup would include the two operators below,
81f4a2713aSLionel Sambuc // which would break later assumptions and lead to a crash.
82f4a2713aSLionel Sambuc class pr5244_foo
83f4a2713aSLionel Sambuc {
84f4a2713aSLionel Sambuc   pr5244_foo(int);
85f4a2713aSLionel Sambuc   pr5244_foo(char);
86f4a2713aSLionel Sambuc };
87f4a2713aSLionel Sambuc 
88f4a2713aSLionel Sambuc bool operator==(const pr5244_foo& s1, const pr5244_foo& s2); // expected-note{{candidate function}}
89f4a2713aSLionel Sambuc bool operator==(char c, const pr5244_foo& s); // expected-note{{candidate function}}
90f4a2713aSLionel Sambuc 
91f4a2713aSLionel Sambuc enum pr5244_bar
92f4a2713aSLionel Sambuc {
93f4a2713aSLionel Sambuc     pr5244_BAR
94f4a2713aSLionel Sambuc };
95f4a2713aSLionel Sambuc 
96f4a2713aSLionel Sambuc class pr5244_baz
97f4a2713aSLionel Sambuc {
98f4a2713aSLionel Sambuc public:
99f4a2713aSLionel Sambuc     pr5244_bar quux;
100f4a2713aSLionel Sambuc };
101f4a2713aSLionel Sambuc 
pr5244_barbaz()102f4a2713aSLionel Sambuc void pr5244_barbaz()
103f4a2713aSLionel Sambuc {
104f4a2713aSLionel Sambuc   pr5244_baz quuux;
105f4a2713aSLionel Sambuc   (void)(pr5244_BAR == quuux.quux);
106f4a2713aSLionel Sambuc }
107f4a2713aSLionel Sambuc 
108f4a2713aSLionel Sambuc 
109f4a2713aSLionel Sambuc 
110f4a2713aSLionel Sambuc struct PostInc {
111f4a2713aSLionel Sambuc   PostInc operator++(int);
112f4a2713aSLionel Sambuc   PostInc& operator++();
113f4a2713aSLionel Sambuc };
114f4a2713aSLionel Sambuc 
115f4a2713aSLionel Sambuc struct PostDec {
116f4a2713aSLionel Sambuc   PostDec operator--(int);
117f4a2713aSLionel Sambuc   PostDec& operator--();
118f4a2713aSLionel Sambuc };
119f4a2713aSLionel Sambuc 
incdec_test(PostInc pi,PostDec pd)120f4a2713aSLionel Sambuc void incdec_test(PostInc pi, PostDec pd) {
121f4a2713aSLionel Sambuc   const PostInc& pi1 = pi++;
122f4a2713aSLionel Sambuc   const PostDec& pd1 = pd--;
123f4a2713aSLionel Sambuc   PostInc &pi2 = ++pi;
124f4a2713aSLionel Sambuc   PostDec &pd2 = --pd;
125f4a2713aSLionel Sambuc }
126f4a2713aSLionel Sambuc 
127f4a2713aSLionel Sambuc struct SmartPtr {
128f4a2713aSLionel Sambuc   int& operator*();
129f4a2713aSLionel Sambuc   long& operator*() const volatile;
130f4a2713aSLionel Sambuc };
131f4a2713aSLionel Sambuc 
test_smartptr(SmartPtr ptr,const SmartPtr cptr,const volatile SmartPtr cvptr)132f4a2713aSLionel Sambuc void test_smartptr(SmartPtr ptr, const SmartPtr cptr,
133f4a2713aSLionel Sambuc                    const volatile SmartPtr cvptr) {
134f4a2713aSLionel Sambuc   int &ir = *ptr;
135f4a2713aSLionel Sambuc   long &lr = *cptr;
136f4a2713aSLionel Sambuc   long &lr2 = *cvptr;
137f4a2713aSLionel Sambuc }
138f4a2713aSLionel Sambuc 
139f4a2713aSLionel Sambuc 
140f4a2713aSLionel Sambuc struct ArrayLike {
141f4a2713aSLionel Sambuc   int& operator[](int);
142f4a2713aSLionel Sambuc };
143f4a2713aSLionel Sambuc 
test_arraylike(ArrayLike a)144f4a2713aSLionel Sambuc void test_arraylike(ArrayLike a) {
145f4a2713aSLionel Sambuc   int& ir = a[17];
146f4a2713aSLionel Sambuc }
147f4a2713aSLionel Sambuc 
148f4a2713aSLionel Sambuc struct SmartRef {
149f4a2713aSLionel Sambuc   int* operator&();
150f4a2713aSLionel Sambuc };
151f4a2713aSLionel Sambuc 
test_smartref(SmartRef r)152f4a2713aSLionel Sambuc void test_smartref(SmartRef r) {
153f4a2713aSLionel Sambuc   int* ip = &r;
154f4a2713aSLionel Sambuc }
155f4a2713aSLionel Sambuc 
156f4a2713aSLionel Sambuc bool& operator,(X, Y);
157f4a2713aSLionel Sambuc 
test_comma(X x,Y y)158f4a2713aSLionel Sambuc void test_comma(X x, Y y) {
159f4a2713aSLionel Sambuc   bool& b1 = (x, y);
160f4a2713aSLionel Sambuc   X& xr = (x, x); // expected-warning {{expression result unused}}
161f4a2713aSLionel Sambuc }
162f4a2713aSLionel Sambuc 
163f4a2713aSLionel Sambuc struct Callable {
164f4a2713aSLionel Sambuc   int& operator()(int, double = 2.71828); // expected-note{{candidate function}}
165f4a2713aSLionel Sambuc   float& operator()(int, double, long, ...); // expected-note{{candidate function}}
166f4a2713aSLionel Sambuc 
167f4a2713aSLionel Sambuc   double& operator()(float); // expected-note{{candidate function}}
168f4a2713aSLionel Sambuc };
169f4a2713aSLionel Sambuc 
170f4a2713aSLionel Sambuc struct Callable2 {
171f4a2713aSLionel Sambuc   int& operator()(int i = 0);
172f4a2713aSLionel Sambuc   double& operator()(...) const;
173f4a2713aSLionel Sambuc };
174f4a2713aSLionel Sambuc 
175f4a2713aSLionel Sambuc struct DerivesCallable : public Callable {
176f4a2713aSLionel Sambuc };
177f4a2713aSLionel Sambuc 
test_callable(Callable c,Callable2 c2,const Callable2 & c2c,DerivesCallable dc)178f4a2713aSLionel Sambuc void test_callable(Callable c, Callable2 c2, const Callable2& c2c,
179f4a2713aSLionel Sambuc                    DerivesCallable dc) {
180f4a2713aSLionel Sambuc   int &ir = c(1);
181f4a2713aSLionel Sambuc   float &fr = c(1, 3.14159, 17, 42);
182f4a2713aSLionel Sambuc 
183f4a2713aSLionel Sambuc   c(); // expected-error{{no matching function for call to object of type 'Callable'}}
184f4a2713aSLionel Sambuc 
185f4a2713aSLionel Sambuc   double &dr = c(1.0f);
186f4a2713aSLionel Sambuc 
187f4a2713aSLionel Sambuc   int &ir2 = c2();
188f4a2713aSLionel Sambuc   int &ir3 = c2(1);
189f4a2713aSLionel Sambuc   double &fr2 = c2c();
190f4a2713aSLionel Sambuc 
191f4a2713aSLionel Sambuc   int &ir4 = dc(17);
192f4a2713aSLionel Sambuc   double &fr3 = dc(3.14159f);
193f4a2713aSLionel Sambuc }
194f4a2713aSLionel Sambuc 
195f4a2713aSLionel Sambuc typedef float FLOAT;
196f4a2713aSLionel Sambuc typedef int& INTREF;
197f4a2713aSLionel Sambuc typedef INTREF Func1(FLOAT, double);
198f4a2713aSLionel Sambuc typedef float& Func2(int, double);
199f4a2713aSLionel Sambuc 
200f4a2713aSLionel Sambuc struct ConvertToFunc {
201f4a2713aSLionel Sambuc   operator Func1*(); // expected-note 2{{conversion candidate of type 'INTREF (*)(FLOAT, double)'}}
202f4a2713aSLionel Sambuc   operator Func2&(); // expected-note 2{{conversion candidate of type 'float &(&)(int, double)'}}
203f4a2713aSLionel Sambuc   void operator()();
204f4a2713aSLionel Sambuc };
205f4a2713aSLionel Sambuc 
206f4a2713aSLionel Sambuc struct ConvertToFuncDerived : ConvertToFunc { };
207f4a2713aSLionel Sambuc 
test_funcptr_call(ConvertToFunc ctf,ConvertToFuncDerived ctfd)208f4a2713aSLionel Sambuc void test_funcptr_call(ConvertToFunc ctf, ConvertToFuncDerived ctfd) {
209f4a2713aSLionel Sambuc   int &i1 = ctf(1.0f, 2.0);
210f4a2713aSLionel Sambuc   float &f1 = ctf((short int)1, 1.0f);
211f4a2713aSLionel Sambuc   ctf((long int)17, 2.0); // expected-error{{call to object of type 'ConvertToFunc' is ambiguous}}
212f4a2713aSLionel Sambuc   ctf();
213f4a2713aSLionel Sambuc 
214f4a2713aSLionel Sambuc   int &i2 = ctfd(1.0f, 2.0);
215f4a2713aSLionel Sambuc   float &f2 = ctfd((short int)1, 1.0f);
216f4a2713aSLionel Sambuc   ctfd((long int)17, 2.0); // expected-error{{call to object of type 'ConvertToFuncDerived' is ambiguous}}
217f4a2713aSLionel Sambuc   ctfd();
218f4a2713aSLionel Sambuc }
219f4a2713aSLionel Sambuc 
220f4a2713aSLionel Sambuc struct HasMember {
221f4a2713aSLionel Sambuc   int m;
222f4a2713aSLionel Sambuc };
223f4a2713aSLionel Sambuc 
224f4a2713aSLionel Sambuc struct Arrow1 {
225f4a2713aSLionel Sambuc   HasMember* operator->();
226f4a2713aSLionel Sambuc };
227f4a2713aSLionel Sambuc 
228f4a2713aSLionel Sambuc struct Arrow2 {
229f4a2713aSLionel Sambuc   Arrow1 operator->(); // expected-note{{candidate function}}
230f4a2713aSLionel Sambuc };
231f4a2713aSLionel Sambuc 
test_arrow(Arrow1 a1,Arrow2 a2,const Arrow2 a3)232f4a2713aSLionel Sambuc void test_arrow(Arrow1 a1, Arrow2 a2, const Arrow2 a3) {
233f4a2713aSLionel Sambuc   int &i1 = a1->m;
234f4a2713aSLionel Sambuc   int &i2 = a2->m;
235f4a2713aSLionel Sambuc   a3->m; // expected-error{{no viable overloaded 'operator->'}}
236f4a2713aSLionel Sambuc }
237f4a2713aSLionel Sambuc 
238f4a2713aSLionel Sambuc struct CopyConBase {
239f4a2713aSLionel Sambuc };
240f4a2713aSLionel Sambuc 
241f4a2713aSLionel Sambuc struct CopyCon : public CopyConBase {
242f4a2713aSLionel Sambuc   CopyCon(const CopyConBase &Base);
243f4a2713aSLionel Sambuc 
CopyConCopyCon244f4a2713aSLionel Sambuc   CopyCon(const CopyConBase *Base) {
245f4a2713aSLionel Sambuc     *this = *Base;
246f4a2713aSLionel Sambuc   }
247f4a2713aSLionel Sambuc };
248f4a2713aSLionel Sambuc 
249f4a2713aSLionel Sambuc namespace N {
250f4a2713aSLionel Sambuc   struct X { };
251f4a2713aSLionel Sambuc }
252f4a2713aSLionel Sambuc 
253f4a2713aSLionel Sambuc namespace M {
254f4a2713aSLionel Sambuc   N::X operator+(N::X, N::X);
255f4a2713aSLionel Sambuc }
256f4a2713aSLionel Sambuc 
257f4a2713aSLionel Sambuc namespace M {
test_X(N::X x)258f4a2713aSLionel Sambuc   void test_X(N::X x) {
259f4a2713aSLionel Sambuc     (void)(x + x);
260f4a2713aSLionel Sambuc   }
261f4a2713aSLionel Sambuc }
262f4a2713aSLionel Sambuc 
263f4a2713aSLionel Sambuc struct AA { bool operator!=(AA&); };
264f4a2713aSLionel Sambuc struct BB : AA {};
x(BB y,BB z)265f4a2713aSLionel Sambuc bool x(BB y, BB z) { return y != z; }
266f4a2713aSLionel Sambuc 
267f4a2713aSLionel Sambuc 
268f4a2713aSLionel Sambuc struct AX {
269f4a2713aSLionel Sambuc   AX& operator ->();	 // expected-note {{declared here}}
270f4a2713aSLionel Sambuc   int b;
271f4a2713aSLionel Sambuc };
272f4a2713aSLionel Sambuc 
m()273f4a2713aSLionel Sambuc void m() {
274f4a2713aSLionel Sambuc   AX a;
275f4a2713aSLionel Sambuc   a->b = 0; // expected-error {{circular pointer delegation detected}}
276f4a2713aSLionel Sambuc }
277f4a2713aSLionel Sambuc 
278f4a2713aSLionel Sambuc struct CircA {
279f4a2713aSLionel Sambuc   struct CircB& operator->(); // expected-note {{declared here}}
280f4a2713aSLionel Sambuc   int val;
281f4a2713aSLionel Sambuc };
282f4a2713aSLionel Sambuc struct CircB {
283f4a2713aSLionel Sambuc   struct CircC& operator->(); // expected-note {{declared here}}
284f4a2713aSLionel Sambuc };
285f4a2713aSLionel Sambuc struct CircC {
286f4a2713aSLionel Sambuc   struct CircA& operator->(); // expected-note {{declared here}}
287f4a2713aSLionel Sambuc };
288f4a2713aSLionel Sambuc 
circ()289f4a2713aSLionel Sambuc void circ() {
290f4a2713aSLionel Sambuc   CircA a;
291f4a2713aSLionel Sambuc   a->val = 0; // expected-error {{circular pointer delegation detected}}
292f4a2713aSLionel Sambuc }
293f4a2713aSLionel Sambuc 
294f4a2713aSLionel Sambuc // PR5360: Arrays should lead to built-in candidates for subscript.
295f4a2713aSLionel Sambuc typedef enum {
296f4a2713aSLionel Sambuc   LastReg = 23,
297f4a2713aSLionel Sambuc } Register;
298f4a2713aSLionel Sambuc class RegAlloc {
getPriority(Register r)299f4a2713aSLionel Sambuc   int getPriority(Register r) {
300f4a2713aSLionel Sambuc     return usepri[r];
301f4a2713aSLionel Sambuc   }
302f4a2713aSLionel Sambuc   int usepri[LastReg + 1];
303f4a2713aSLionel Sambuc };
304f4a2713aSLionel Sambuc 
305f4a2713aSLionel Sambuc // PR5546: Don't generate incorrect and ambiguous overloads for multi-level
306f4a2713aSLionel Sambuc // arrays.
307f4a2713aSLionel Sambuc namespace pr5546
308f4a2713aSLionel Sambuc {
309f4a2713aSLionel Sambuc   enum { X };
310f4a2713aSLionel Sambuc   extern const char *const sMoveCommands[][2][2];
a()311f4a2713aSLionel Sambuc   const char* a() { return sMoveCommands[X][0][0]; }
b()312f4a2713aSLionel Sambuc   const char* b() { return (*(sMoveCommands+X))[0][0]; }
313f4a2713aSLionel Sambuc }
314f4a2713aSLionel Sambuc 
315f4a2713aSLionel Sambuc // PR5512 and its discussion
316f4a2713aSLionel Sambuc namespace pr5512 {
317f4a2713aSLionel Sambuc   struct Y {
318f4a2713aSLionel Sambuc     operator short();
319f4a2713aSLionel Sambuc     operator float();
320f4a2713aSLionel Sambuc   };
g_test(Y y)321f4a2713aSLionel Sambuc   void g_test(Y y) {
322f4a2713aSLionel Sambuc     short s = 0;
323f4a2713aSLionel Sambuc     // DR507, this should be ambiguous, but we special-case assignment
324f4a2713aSLionel Sambuc     s = y;
325f4a2713aSLionel Sambuc     // Note: DR507, this is ambiguous as specified
326f4a2713aSLionel Sambuc     //s += y;
327f4a2713aSLionel Sambuc   }
328f4a2713aSLionel Sambuc 
329f4a2713aSLionel Sambuc   struct S {};
330f4a2713aSLionel Sambuc   void operator +=(int&, S);
f(S s)331f4a2713aSLionel Sambuc   void f(S s) {
332f4a2713aSLionel Sambuc     int i = 0;
333f4a2713aSLionel Sambuc     i += s;
334f4a2713aSLionel Sambuc   }
335f4a2713aSLionel Sambuc 
336f4a2713aSLionel Sambuc   struct A {operator int();};
337f4a2713aSLionel Sambuc   int a;
b(A x)338f4a2713aSLionel Sambuc   void b(A x) {
339f4a2713aSLionel Sambuc     a += x;
340f4a2713aSLionel Sambuc   }
341f4a2713aSLionel Sambuc }
342f4a2713aSLionel Sambuc 
343f4a2713aSLionel Sambuc // PR5900
344f4a2713aSLionel Sambuc namespace pr5900 {
345f4a2713aSLionel Sambuc   struct NotAnArray {};
test0()346f4a2713aSLionel Sambuc   void test0() {
347f4a2713aSLionel Sambuc     NotAnArray x;
348f4a2713aSLionel Sambuc     x[0] = 0; // expected-error {{does not provide a subscript operator}}
349f4a2713aSLionel Sambuc   }
350f4a2713aSLionel Sambuc 
351f4a2713aSLionel Sambuc   struct NonConstArray {
352f4a2713aSLionel Sambuc     int operator[](unsigned); // expected-note {{candidate}}
353f4a2713aSLionel Sambuc   };
test1()354f4a2713aSLionel Sambuc   int test1() {
355f4a2713aSLionel Sambuc     const NonConstArray x = NonConstArray();
356f4a2713aSLionel Sambuc     return x[0]; // expected-error {{no viable overloaded operator[] for type}}
357f4a2713aSLionel Sambuc   }
358f4a2713aSLionel Sambuc 
359f4a2713aSLionel Sambuc   // Not really part of this PR, but implemented at the same time.
360f4a2713aSLionel Sambuc   struct NotAFunction {};
test2()361f4a2713aSLionel Sambuc   void test2() {
362f4a2713aSLionel Sambuc     NotAFunction x;
363f4a2713aSLionel Sambuc     x(); // expected-error {{does not provide a call operator}}
364f4a2713aSLionel Sambuc   }
365f4a2713aSLionel Sambuc }
366f4a2713aSLionel Sambuc 
367f4a2713aSLionel Sambuc // Operator lookup through using declarations.
368f4a2713aSLionel Sambuc namespace N {
369f4a2713aSLionel Sambuc   struct X2 { };
370f4a2713aSLionel Sambuc }
371f4a2713aSLionel Sambuc 
372f4a2713aSLionel Sambuc namespace N2 {
373f4a2713aSLionel Sambuc   namespace M {
374f4a2713aSLionel Sambuc     namespace Inner {
375f4a2713aSLionel Sambuc       template<typename T>
376f4a2713aSLionel Sambuc       N::X2 &operator<<(N::X2&, const T&);
377f4a2713aSLionel Sambuc     }
378f4a2713aSLionel Sambuc     using Inner::operator<<;
379f4a2713aSLionel Sambuc   }
380f4a2713aSLionel Sambuc }
381f4a2713aSLionel Sambuc 
test_lookup_through_using()382f4a2713aSLionel Sambuc void test_lookup_through_using() {
383f4a2713aSLionel Sambuc   using namespace N2::M;
384f4a2713aSLionel Sambuc   N::X2 x;
385f4a2713aSLionel Sambuc   x << 17;
386f4a2713aSLionel Sambuc }
387f4a2713aSLionel Sambuc 
388f4a2713aSLionel Sambuc namespace rdar9136502 {
389f4a2713aSLionel Sambuc   struct X {
390f4a2713aSLionel Sambuc     int i(); // expected-note{{possible target for call}}
391f4a2713aSLionel Sambuc     int i(int); // expected-note{{possible target for call}}
392f4a2713aSLionel Sambuc   };
393f4a2713aSLionel Sambuc 
394f4a2713aSLionel Sambuc   struct Y {
395f4a2713aSLionel Sambuc     Y &operator<<(int);
396f4a2713aSLionel Sambuc   };
397f4a2713aSLionel Sambuc 
f(X x,Y y)398f4a2713aSLionel Sambuc   void f(X x, Y y) {
399f4a2713aSLionel Sambuc     y << x
400f4a2713aSLionel Sambuc       .i; // expected-error{{reference to non-static member function must be called; did you mean to call it with no arguments?}}
401f4a2713aSLionel Sambuc   }
402f4a2713aSLionel Sambuc }
403f4a2713aSLionel Sambuc 
404f4a2713aSLionel Sambuc namespace rdar9222009 {
405f4a2713aSLionel Sambuc class StringRef {
operator ==(StringRef LHS,StringRef RHS)406f4a2713aSLionel Sambuc   inline bool operator==(StringRef LHS, StringRef RHS) { // expected-error{{overloaded 'operator==' must be a binary operator (has 3 parameters)}}
407f4a2713aSLionel Sambuc     return !(LHS == RHS); // expected-error{{invalid operands to binary expression ('rdar9222009::StringRef' and 'rdar9222009::StringRef')}}
408f4a2713aSLionel Sambuc   }
409f4a2713aSLionel Sambuc };
410f4a2713aSLionel Sambuc 
411f4a2713aSLionel Sambuc }
412f4a2713aSLionel Sambuc 
413f4a2713aSLionel Sambuc namespace PR11784 {
414f4a2713aSLionel Sambuc   struct A { A& operator=(void (*x)()); };
415f4a2713aSLionel Sambuc   void f();
416f4a2713aSLionel Sambuc   void f(int);
g()417f4a2713aSLionel Sambuc   void g() { A x; x = f; }
418f4a2713aSLionel Sambuc }
419f4a2713aSLionel Sambuc 
420f4a2713aSLionel Sambuc namespace test10 {
421f4a2713aSLionel Sambuc   struct A {
422f4a2713aSLionel Sambuc     void operator[](float (*fn)(int)); // expected-note 2 {{not viable: no overload of 'bar' matching 'float (*)(int)'}}
423f4a2713aSLionel Sambuc   };
424f4a2713aSLionel Sambuc 
425f4a2713aSLionel Sambuc   float foo(int);
426f4a2713aSLionel Sambuc   float foo(float);
427f4a2713aSLionel Sambuc 
428f4a2713aSLionel Sambuc   template <class T> T bar(T);
429f4a2713aSLionel Sambuc   template <class T, class U> T bar(U);
430f4a2713aSLionel Sambuc 
test(A & a)431f4a2713aSLionel Sambuc   void test(A &a) {
432f4a2713aSLionel Sambuc     a[&foo];
433f4a2713aSLionel Sambuc     a[foo];
434f4a2713aSLionel Sambuc 
435f4a2713aSLionel Sambuc     a[&bar<int>]; // expected-error {{no viable overloaded operator[]}}
436f4a2713aSLionel Sambuc     a[bar<int>]; // expected-error {{no viable overloaded operator[]}}
437f4a2713aSLionel Sambuc 
438f4a2713aSLionel Sambuc     // If these fail, it's because we're not letting the overload
439f4a2713aSLionel Sambuc     // resolution for operator| resolve the overload of 'bar'.
440f4a2713aSLionel Sambuc     a[&bar<float>];
441f4a2713aSLionel Sambuc     a[bar<float>];
442f4a2713aSLionel Sambuc   }
443f4a2713aSLionel Sambuc }
444f4a2713aSLionel Sambuc 
445f4a2713aSLionel Sambuc struct InvalidOperatorEquals {
446f4a2713aSLionel Sambuc   InvalidOperatorEquals operator=() = delete; // expected-error {{overloaded 'operator=' must be a binary operator}}
447f4a2713aSLionel Sambuc };
448f4a2713aSLionel Sambuc 
449f4a2713aSLionel Sambuc namespace PR7681 {
450f4a2713aSLionel Sambuc   template <typename PT1, typename PT2> class PointerUnion;
foo(PointerUnion<int *,float * > & Result)451f4a2713aSLionel Sambuc   void foo(PointerUnion<int*, float*> &Result) {
452f4a2713aSLionel Sambuc     Result = 1; // expected-error {{no viable overloaded '='}} // expected-note {{type 'PointerUnion<int *, float *>' is incomplete}}
453f4a2713aSLionel Sambuc   }
454f4a2713aSLionel Sambuc }
455*0a6a1f1dSLionel Sambuc 
456*0a6a1f1dSLionel Sambuc namespace PR14995 {
457*0a6a1f1dSLionel Sambuc   struct B {};
operator ++(B,T...)458*0a6a1f1dSLionel Sambuc   template<typename ...T> void operator++(B, T...) {}
459*0a6a1f1dSLionel Sambuc 
f()460*0a6a1f1dSLionel Sambuc   void f() {
461*0a6a1f1dSLionel Sambuc     B b;
462*0a6a1f1dSLionel Sambuc     b++;  // ok
463*0a6a1f1dSLionel Sambuc     ++b;  // ok
464*0a6a1f1dSLionel Sambuc   }
465*0a6a1f1dSLionel Sambuc 
466*0a6a1f1dSLionel Sambuc   template<typename... T>
467*0a6a1f1dSLionel Sambuc   struct C {
operator --PR14995::C468*0a6a1f1dSLionel Sambuc     void operator-- (T...) {}
469*0a6a1f1dSLionel Sambuc   };
470*0a6a1f1dSLionel Sambuc 
g()471*0a6a1f1dSLionel Sambuc   void g() {
472*0a6a1f1dSLionel Sambuc     C<int> postfix;
473*0a6a1f1dSLionel Sambuc     C<> prefix;
474*0a6a1f1dSLionel Sambuc     postfix--;  // ok
475*0a6a1f1dSLionel Sambuc     --prefix;  // ok
476*0a6a1f1dSLionel Sambuc   }
477*0a6a1f1dSLionel Sambuc 
478*0a6a1f1dSLionel Sambuc   struct D {};
operator ++(D,T)479*0a6a1f1dSLionel Sambuc   template<typename T> void operator++(D, T) {}
480*0a6a1f1dSLionel Sambuc 
h()481*0a6a1f1dSLionel Sambuc   void h() {
482*0a6a1f1dSLionel Sambuc     D d;
483*0a6a1f1dSLionel Sambuc     d++;  // ok
484*0a6a1f1dSLionel Sambuc     ++d; // expected-error{{cannot increment value of type 'PR14995::D'}}
485*0a6a1f1dSLionel Sambuc   }
486*0a6a1f1dSLionel Sambuc 
487*0a6a1f1dSLionel Sambuc   template<typename...T> struct E {
operator ++PR14995::E488*0a6a1f1dSLionel Sambuc     void operator++(T...) {} // expected-error{{parameter of overloaded post-increment operator must have type 'int' (not 'char')}}
489*0a6a1f1dSLionel Sambuc   };
490*0a6a1f1dSLionel Sambuc 
491*0a6a1f1dSLionel Sambuc   E<char> e; // expected-note {{in instantiation of template class 'PR14995::E<char>' requested here}}
492*0a6a1f1dSLionel Sambuc 
493*0a6a1f1dSLionel Sambuc   struct F {
494*0a6a1f1dSLionel Sambuc     template<typename... T>
operator ++PR14995::F495*0a6a1f1dSLionel Sambuc     int operator++ (T...) {}
496*0a6a1f1dSLionel Sambuc   };
497*0a6a1f1dSLionel Sambuc 
498*0a6a1f1dSLionel Sambuc   int k1 = F().operator++(0, 0);
499*0a6a1f1dSLionel Sambuc   int k2 = F().operator++('0');
500*0a6a1f1dSLionel Sambuc   // expected-error@-5 {{overloaded 'operator++' must be a unary or binary operator}}
501*0a6a1f1dSLionel Sambuc   // expected-note@-3 {{in instantiation of function template specialization 'PR14995::F::operator++<int, int>' requested here}}
502*0a6a1f1dSLionel Sambuc   // expected-error@-4 {{no matching member function for call to 'operator++'}}
503*0a6a1f1dSLionel Sambuc   // expected-note@-8 {{candidate template ignored: substitution failure}}
504*0a6a1f1dSLionel Sambuc   // expected-error@-9 {{parameter of overloaded post-increment operator must have type 'int' (not 'char')}}
505*0a6a1f1dSLionel Sambuc   // expected-note@-6 {{in instantiation of function template specialization 'PR14995::F::operator++<char>' requested here}}
506*0a6a1f1dSLionel Sambuc   // expected-error@-7 {{no matching member function for call to 'operator++'}}
507*0a6a1f1dSLionel Sambuc   // expected-note@-12 {{candidate template ignored: substitution failure}}
508*0a6a1f1dSLionel Sambuc } // namespace PR14995
509*0a6a1f1dSLionel Sambuc 
510*0a6a1f1dSLionel Sambuc namespace ConversionVersusTemplateOrdering {
511*0a6a1f1dSLionel Sambuc   struct A {
512*0a6a1f1dSLionel Sambuc     operator short() = delete;
513*0a6a1f1dSLionel Sambuc     template <typename T> operator T();
514*0a6a1f1dSLionel Sambuc   } a;
515*0a6a1f1dSLionel Sambuc   struct B {
516*0a6a1f1dSLionel Sambuc     template <typename T> operator T();
517*0a6a1f1dSLionel Sambuc     operator short() = delete;
518*0a6a1f1dSLionel Sambuc   } b;
519*0a6a1f1dSLionel Sambuc   int x = a;
520*0a6a1f1dSLionel Sambuc   int y = b;
521*0a6a1f1dSLionel Sambuc }
522*0a6a1f1dSLionel Sambuc 
523*0a6a1f1dSLionel Sambuc namespace NoADLForMemberOnlyOperators {
524*0a6a1f1dSLionel Sambuc   template<typename T> struct A { typename T::error e; }; // expected-error {{type 'char' cannot be used prior to '::'}}
525*0a6a1f1dSLionel Sambuc   template<typename T> struct B { int n; };
526*0a6a1f1dSLionel Sambuc 
f(B<A<void>> b1,B<A<int>> b2,B<A<char>> b3)527*0a6a1f1dSLionel Sambuc   void f(B<A<void> > b1, B<A<int> > b2, B<A<char> > b3) {
528*0a6a1f1dSLionel Sambuc     b1 = b1; // ok, does not instantiate A<void>.
529*0a6a1f1dSLionel Sambuc     (void)b1->n; // expected-error {{is not a pointer}}
530*0a6a1f1dSLionel Sambuc     b2[3]; // expected-error {{does not provide a subscript}}
531*0a6a1f1dSLionel Sambuc     b3 / 0; // expected-note {{in instantiation of}} expected-error {{invalid operands to}}
532*0a6a1f1dSLionel Sambuc   }
533*0a6a1f1dSLionel Sambuc }
534