xref: /aosp_15_r20/external/clang/test/SemaCXX/virtual-override.cpp (revision 67e74705e28f6214e480b399dd47ea732279e315)
1*67e74705SXin Li // RUN: %clang_cc1 -fsyntax-only -triple %itanium_abi_triple -verify %s -std=c++11
2*67e74705SXin Li // RUN: %clang_cc1 -fsyntax-only -triple %ms_abi_triple -verify %s -std=c++11
3*67e74705SXin Li namespace T1 {
4*67e74705SXin Li 
5*67e74705SXin Li class A {
6*67e74705SXin Li   virtual int f(); // expected-note{{overridden virtual function is here}}
7*67e74705SXin Li };
8*67e74705SXin Li 
9*67e74705SXin Li class B : A {
10*67e74705SXin Li   virtual void f(); // expected-error{{virtual function 'f' has a different return type ('void') than the function it overrides (which has return type 'int')}}
11*67e74705SXin Li };
12*67e74705SXin Li 
13*67e74705SXin Li }
14*67e74705SXin Li 
15*67e74705SXin Li namespace T2 {
16*67e74705SXin Li 
17*67e74705SXin Li struct a { };
18*67e74705SXin Li struct b { };
19*67e74705SXin Li 
20*67e74705SXin Li class A {
21*67e74705SXin Li   virtual a* f(); // expected-note{{overridden virtual function is here}}
22*67e74705SXin Li };
23*67e74705SXin Li 
24*67e74705SXin Li class B : A {
25*67e74705SXin Li   virtual b* f(); // expected-error{{return type of virtual function 'f' is not covariant with the return type of the function it overrides ('T2::b *' is not derived from 'T2::a *')}}
26*67e74705SXin Li };
27*67e74705SXin Li 
28*67e74705SXin Li }
29*67e74705SXin Li 
30*67e74705SXin Li namespace T3 {
31*67e74705SXin Li 
32*67e74705SXin Li struct a { };
33*67e74705SXin Li struct b : private a { }; // expected-note{{declared private here}}
34*67e74705SXin Li 
35*67e74705SXin Li class A {
36*67e74705SXin Li   virtual a* f(); // FIXME: desired-note{{overridden virtual function is here}}
37*67e74705SXin Li };
38*67e74705SXin Li 
39*67e74705SXin Li class B : A {
40*67e74705SXin Li   virtual b* f(); // expected-error{{invalid covariant return for virtual function: 'T3::a' is a private base class of 'T3::b'}}
41*67e74705SXin Li };
42*67e74705SXin Li 
43*67e74705SXin Li }
44*67e74705SXin Li 
45*67e74705SXin Li namespace T4 {
46*67e74705SXin Li 
47*67e74705SXin Li struct a { };
48*67e74705SXin Li struct a1 : a { };
49*67e74705SXin Li struct b : a, a1 { }; // expected-warning{{direct base 'T4::a' is inaccessible due to ambiguity:\n    struct T4::b -> struct T4::a\n    struct T4::b -> struct T4::a1 -> struct T4::a}}
50*67e74705SXin Li 
51*67e74705SXin Li class A {
52*67e74705SXin Li   virtual a* f(); // expected-note{{overridden virtual function is here}}
53*67e74705SXin Li };
54*67e74705SXin Li 
55*67e74705SXin Li class B : A {
56*67e74705SXin Li   virtual b* f(); // expected-error{{return type of virtual function 'f' is not covariant with the return type of the function it overrides (ambiguous conversion from derived class 'T4::b' to base class 'T4::a':\n\
57*67e74705SXin Li     struct T4::b -> struct T4::a\n\
58*67e74705SXin Li     struct T4::b -> struct T4::a1 -> struct T4::a)}}
59*67e74705SXin Li };
60*67e74705SXin Li 
61*67e74705SXin Li }
62*67e74705SXin Li 
63*67e74705SXin Li namespace T5 {
64*67e74705SXin Li 
65*67e74705SXin Li struct a { };
66*67e74705SXin Li 
67*67e74705SXin Li class A {
68*67e74705SXin Li   virtual a* const f();
69*67e74705SXin Li   virtual a* const g(); // expected-note{{overridden virtual function is here}}
70*67e74705SXin Li };
71*67e74705SXin Li 
72*67e74705SXin Li class B : A {
73*67e74705SXin Li   virtual a* const f();
74*67e74705SXin Li   virtual a* g(); // expected-error{{return type of virtual function 'g' is not covariant with the return type of the function it overrides ('T5::a *' has different qualifiers than 'T5::a *const')}}
75*67e74705SXin Li };
76*67e74705SXin Li 
77*67e74705SXin Li }
78*67e74705SXin Li 
79*67e74705SXin Li namespace T6 {
80*67e74705SXin Li 
81*67e74705SXin Li struct a { };
82*67e74705SXin Li 
83*67e74705SXin Li class A {
84*67e74705SXin Li   virtual const a* f();
85*67e74705SXin Li   virtual a* g(); // expected-note{{overridden virtual function is here}}
86*67e74705SXin Li };
87*67e74705SXin Li 
88*67e74705SXin Li class B : A {
89*67e74705SXin Li   virtual a* f();
90*67e74705SXin Li   virtual const a* g(); // expected-error{{return type of virtual function 'g' is not covariant with the return type of the function it overrides (class type 'const T6::a *' is more qualified than class type 'T6::a *'}}
91*67e74705SXin Li };
92*67e74705SXin Li 
93*67e74705SXin Li }
94*67e74705SXin Li 
95*67e74705SXin Li namespace T7 {
96*67e74705SXin Li   struct a { };
97*67e74705SXin Li   struct b { };
98*67e74705SXin Li 
99*67e74705SXin Li   class A {
100*67e74705SXin Li     a* f();
101*67e74705SXin Li   };
102*67e74705SXin Li 
103*67e74705SXin Li   class B : A {
104*67e74705SXin Li     virtual b* f();
105*67e74705SXin Li   };
106*67e74705SXin Li }
107*67e74705SXin Li 
108*67e74705SXin Li namespace T8 {
109*67e74705SXin Li   struct a { };
110*67e74705SXin Li   struct b; // expected-note {{forward declaration of 'T8::b'}}
111*67e74705SXin Li 
112*67e74705SXin Li   class A {
113*67e74705SXin Li     virtual a *f();
114*67e74705SXin Li   };
115*67e74705SXin Li 
116*67e74705SXin Li   class B : A {
117*67e74705SXin Li     b* f(); // expected-error {{return type of virtual function 'f' is not covariant with the return type of the function it overrides ('T8::b' is incomplete)}}
118*67e74705SXin Li   };
119*67e74705SXin Li }
120*67e74705SXin Li 
121*67e74705SXin Li namespace T9 {
122*67e74705SXin Li   struct a { };
123*67e74705SXin Li 
124*67e74705SXin Li   template<typename T> struct b : a {
125*67e74705SXin Li     int a[sizeof(T) ? -1 : -1]; // expected-error {{array with a negative size}}
126*67e74705SXin Li   };
127*67e74705SXin Li 
128*67e74705SXin Li   class A {
129*67e74705SXin Li     virtual a *f();
130*67e74705SXin Li   };
131*67e74705SXin Li 
132*67e74705SXin Li   class B : A {
133*67e74705SXin Li     virtual b<int> *f(); // expected-note {{in instantiation of template class 'T9::b<int>' requested here}}
134*67e74705SXin Li   };
135*67e74705SXin Li }
136*67e74705SXin Li 
137*67e74705SXin Li // PR5656
138*67e74705SXin Li class X0 {
139*67e74705SXin Li   virtual void f0();
140*67e74705SXin Li };
141*67e74705SXin Li class X1 : public X0 {
142*67e74705SXin Li   void f0() = 0;
143*67e74705SXin Li };
144*67e74705SXin Li 
145*67e74705SXin Li template <typename Base>
146*67e74705SXin Li struct Foo : Base {
147*67e74705SXin Li   void f(int) = 0; // expected-error{{not virtual and cannot be declared pure}}
148*67e74705SXin Li };
149*67e74705SXin Li 
150*67e74705SXin Li struct Base1 { virtual void f(int); };
151*67e74705SXin Li struct Base2 { };
152*67e74705SXin Li 
test()153*67e74705SXin Li void test() {
154*67e74705SXin Li   (void)sizeof(Foo<Base1>);
155*67e74705SXin Li   (void)sizeof(Foo<Base2>); // expected-note{{instantiation}}
156*67e74705SXin Li }
157*67e74705SXin Li 
158*67e74705SXin Li template<typename Base>
159*67e74705SXin Li struct Foo2 : Base {
160*67e74705SXin Li   template<typename T> int f(T);
161*67e74705SXin Li };
162*67e74705SXin Li 
test2()163*67e74705SXin Li void test2() {
164*67e74705SXin Li   Foo2<Base1> f1;
165*67e74705SXin Li   Foo2<Base2> f2;
166*67e74705SXin Li   f1.f(17);
167*67e74705SXin Li   f2.f(17);
168*67e74705SXin Li };
169*67e74705SXin Li 
170*67e74705SXin Li struct Foo3 {
171*67e74705SXin Li   virtual void f(int) = 0; // expected-note{{unimplemented pure virtual method}}
172*67e74705SXin Li };
173*67e74705SXin Li 
174*67e74705SXin Li template<typename T>
175*67e74705SXin Li struct Bar3 : Foo3 {
176*67e74705SXin Li   void f(T);
177*67e74705SXin Li };
178*67e74705SXin Li 
test3()179*67e74705SXin Li void test3() {
180*67e74705SXin Li   Bar3<int> b3i; // okay
181*67e74705SXin Li   Bar3<float> b3f; // expected-error{{is an abstract class}}
182*67e74705SXin Li }
183*67e74705SXin Li 
184*67e74705SXin Li // 5920
185*67e74705SXin Li namespace PR5920 {
186*67e74705SXin Li   class Base {};
187*67e74705SXin Li 
188*67e74705SXin Li   template <typename T>
189*67e74705SXin Li   class Derived : public Base {};
190*67e74705SXin Li 
191*67e74705SXin Li   class Foo {
192*67e74705SXin Li    public:
193*67e74705SXin Li     virtual Base* Method();
194*67e74705SXin Li   };
195*67e74705SXin Li 
196*67e74705SXin Li   class Bar : public Foo {
197*67e74705SXin Li    public:
198*67e74705SXin Li     virtual Derived<int>* Method();
199*67e74705SXin Li   };
200*67e74705SXin Li }
201*67e74705SXin Li 
202*67e74705SXin Li // Look through template types and typedefs to see whether return types are
203*67e74705SXin Li // pointers or references.
204*67e74705SXin Li namespace PR6110 {
205*67e74705SXin Li   class Base {};
206*67e74705SXin Li   class Derived : public Base {};
207*67e74705SXin Li 
208*67e74705SXin Li   typedef Base* BaseP;
209*67e74705SXin Li   typedef Derived* DerivedP;
210*67e74705SXin Li 
211*67e74705SXin Li   class X { virtual BaseP f(); };
212*67e74705SXin Li   class X1 : public X { virtual DerivedP f(); };
213*67e74705SXin Li 
214*67e74705SXin Li   template <typename T> class Y { virtual T f(); };
215*67e74705SXin Li   template <typename T1, typename T> class Y1 : public Y<T> { virtual T1 f(); };
216*67e74705SXin Li   Y1<Derived*, Base*> y;
217*67e74705SXin Li }
218*67e74705SXin Li 
219*67e74705SXin Li // Defer checking for covariance if either return type is dependent.
220*67e74705SXin Li namespace type_dependent_covariance {
221*67e74705SXin Li   struct B {};
222*67e74705SXin Li   template <int N> struct TD : public B {};
223*67e74705SXin Li   template <> struct TD<1> {};
224*67e74705SXin Li 
225*67e74705SXin Li   template <int N> struct TB {};
226*67e74705SXin Li   struct D : public TB<0> {};
227*67e74705SXin Li 
228*67e74705SXin Li   template <int N> struct X {
229*67e74705SXin Li     virtual B* f1(); // expected-note{{overridden virtual function is here}}
230*67e74705SXin Li     virtual TB<N>* f2(); // expected-note{{overridden virtual function is here}}
231*67e74705SXin Li   };
232*67e74705SXin Li   template <int N, int M> struct X1 : X<N> {
233*67e74705SXin Li     virtual TD<M>* f1(); // expected-error{{return type of virtual function 'f1' is not covariant with the return type of the function it overrides ('TD<1> *'}}
234*67e74705SXin Li     virtual D* f2(); // expected-error{{return type of virtual function 'f2' is not covariant with the return type of the function it overrides ('type_dependent_covariance::D *' is not derived from 'TB<1> *')}}
235*67e74705SXin Li   };
236*67e74705SXin Li 
237*67e74705SXin Li   X1<0, 0> good;
238*67e74705SXin Li   X1<0, 1> bad_derived; // expected-note{{instantiation}}
239*67e74705SXin Li   X1<1, 0> bad_base; // expected-note{{instantiation}}
240*67e74705SXin Li }
241*67e74705SXin Li 
242*67e74705SXin Li namespace T10 {
243*67e74705SXin Li   struct A { };
244*67e74705SXin Li   struct B : A { };
245*67e74705SXin Li 
246*67e74705SXin Li   struct C {
247*67e74705SXin Li     virtual A&& f();
248*67e74705SXin Li   };
249*67e74705SXin Li 
250*67e74705SXin Li   struct D : C {
251*67e74705SXin Li     virtual B&& f();
252*67e74705SXin Li   };
253*67e74705SXin Li };
254*67e74705SXin Li 
255*67e74705SXin Li namespace T11 {
256*67e74705SXin Li   struct A { };
257*67e74705SXin Li   struct B : A { };
258*67e74705SXin Li 
259*67e74705SXin Li   struct C {
260*67e74705SXin Li     virtual A& f(); // expected-note {{overridden virtual function is here}}
261*67e74705SXin Li   };
262*67e74705SXin Li 
263*67e74705SXin Li   struct D : C {
264*67e74705SXin Li     virtual B&& f(); // expected-error {{virtual function 'f' has a different return type ('T11::B &&') than the function it overrides (which has return type 'T11::A &')}}
265*67e74705SXin Li   };
266*67e74705SXin Li };
267*67e74705SXin Li 
268*67e74705SXin Li namespace T12 {
269*67e74705SXin Li   struct A { };
270*67e74705SXin Li   struct B : A { };
271*67e74705SXin Li 
272*67e74705SXin Li   struct C {
273*67e74705SXin Li     virtual A&& f(); // expected-note {{overridden virtual function is here}}
274*67e74705SXin Li   };
275*67e74705SXin Li 
276*67e74705SXin Li   struct D : C {
277*67e74705SXin Li     virtual B& f(); // expected-error {{virtual function 'f' has a different return type ('T12::B &') than the function it overrides (which has return type 'T12::A &&')}}
278*67e74705SXin Li   };
279*67e74705SXin Li };
280*67e74705SXin Li 
281*67e74705SXin Li namespace PR8168 {
282*67e74705SXin Li   class A {
283*67e74705SXin Li   public:
foo()284*67e74705SXin Li     virtual void foo() {} // expected-note{{overridden virtual function is here}}
285*67e74705SXin Li   };
286*67e74705SXin Li 
287*67e74705SXin Li   class B : public A {
288*67e74705SXin Li   public:
foo()289*67e74705SXin Li     static void foo() {} // expected-error{{'static' member function 'foo' overrides a virtual function}}
290*67e74705SXin Li   };
291*67e74705SXin Li }
292