Home | History | Annotate | Download | only in SemaCXX
      1 // RUN: %clang_cc1 -fsyntax-only -verify %s
      2 
      3 struct A {};
      4 enum B { Dummy };
      5 namespace C {}
      6 struct D : A {};
      7 struct E : A {};
      8 struct F : D, E {};
      9 struct G : virtual D {};
     10 class H : A {}; // expected-note 2{{implicitly declared private here}}
     11 
     12 int A::*pdi1;
     13 int (::A::*pdi2);
     14 int (A::*pfi)(int);
     15 void (*A::*ppfie)() throw(); // expected-error {{exception specifications are not allowed beyond a single level of indirection}}
     16 
     17 int B::*pbi; // expected-warning{{use of enumeration in a nested name specifier is a C++11 extension}} \
     18              // expected-error {{'pbi' does not point into a class}}
     19 int C::*pci; // expected-error {{'pci' does not point into a class}}
     20 void A::*pdv; // expected-error {{'pdv' declared as a member pointer to void}}
     21 int& A::*pdr; // expected-error {{'pdr' declared as a member pointer to a reference}}
     22 
     23 void f() {
     24   // This requires tentative parsing.
     25   int (A::*pf)(int, int);
     26 
     27   // Implicit conversion to bool.
     28   bool b = pdi1;
     29   b = pfi;
     30 
     31   // Conversion from null pointer constant.
     32   pf = 0;
     33   pf = __null;
     34 
     35   // Conversion to member of derived.
     36   int D::*pdid = pdi1;
     37   pdid = pdi2;
     38 
     39   // Fail conversion due to ambiguity and virtuality.
     40   int F::*pdif = pdi1; // expected-error {{ambiguous conversion from pointer to member of base class 'A' to pointer to member of derived class 'F':}}
     41   int G::*pdig = pdi1; // expected-error {{conversion from pointer to member of class 'A' to pointer to member of class 'G' via virtual base 'D' is not allowed}}
     42 
     43   // Conversion to member of base.
     44   pdi1 = pdid; // expected-error {{assigning to 'int A::*' from incompatible type 'int D::*'}}
     45 
     46   // Comparisons
     47   int (A::*pf2)(int, int);
     48   int (D::*pf3)(int, int) = 0;
     49   bool b1 = (pf == pf2); (void)b1;
     50   bool b2 = (pf != pf2); (void)b2;
     51   bool b3 = (pf == pf3); (void)b3;
     52   bool b4 = (pf != 0); (void)b4;
     53 }
     54 
     55 struct TheBase
     56 {
     57   void d();
     58 };
     59 
     60 struct HasMembers : TheBase
     61 {
     62   int i;
     63   void f();
     64 
     65   void g();
     66   void g(int);
     67   static void g(double);
     68 };
     69 
     70 namespace Fake
     71 {
     72   int i;
     73   void f();
     74 }
     75 
     76 void g() {
     77   HasMembers hm;
     78 
     79   int HasMembers::*pmi = &HasMembers::i;
     80   int *pni = &Fake::i;
     81   int *pmii = &hm.i;
     82 
     83   void (HasMembers::*pmf)() = &HasMembers::f;
     84   void (*pnf)() = &Fake::f;
     85   &hm.f; // expected-error {{cannot create a non-constant pointer to member function}}
     86 
     87   void (HasMembers::*pmgv)() = &HasMembers::g;
     88   void (HasMembers::*pmgi)(int) = &HasMembers::g;
     89   void (*pmgd)(double) = &HasMembers::g;
     90 
     91   void (HasMembers::*pmd)() = &HasMembers::d;
     92 }
     93 
     94 struct Incomplete;
     95 
     96 void h() {
     97   HasMembers hm, *phm = &hm;
     98 
     99   int HasMembers::*pi = &HasMembers::i;
    100   hm.*pi = 0;
    101   int i = phm->*pi;
    102   (void)&(hm.*pi);
    103   (void)&(phm->*pi);
    104   (void)&((&hm)->*pi);
    105 
    106   void (HasMembers::*pf)() = &HasMembers::f;
    107   (hm.*pf)();
    108   (phm->*pf)();
    109 
    110   (void)(hm->*pi); // expected-error {{left hand operand to ->* must be a pointer to class compatible with the right hand operand, but is 'HasMembers'}}
    111   (void)(phm.*pi); // expected-error {{left hand operand to .* must be a class compatible with the right hand operand, but is 'HasMembers *'}}
    112   (void)(i.*pi); // expected-error {{left hand operand to .* must be a class compatible with the right hand operand, but is 'int'}}
    113   int *ptr;
    114   (void)(ptr->*pi); // expected-error {{left hand operand to ->* must be a pointer to class compatible with the right hand operand, but is 'int *'}}
    115 
    116   int A::*pai = 0;
    117   D d, *pd = &d;
    118   (void)(d.*pai);
    119   (void)(pd->*pai);
    120   F f, *ptrf = &f;
    121   (void)(f.*pai); // expected-error {{ambiguous conversion from derived class 'F' to base class 'A'}}
    122   (void)(ptrf->*pai); // expected-error {{ambiguous conversion from derived class 'F' to base class 'A'}}
    123   H h, *ptrh = &h;
    124   (void)(h.*pai); // expected-error {{cannot cast 'H' to its private base class 'A'}}
    125   (void)(ptrh->*pai); // expected-error {{cannot cast 'H' to its private base class 'A'}}
    126 
    127   (void)(hm.*i); // expected-error {{pointer-to-member}}
    128   (void)(phm->*i); // expected-error {{pointer-to-member}}
    129 
    130   // Okay
    131   Incomplete *inc;
    132   int Incomplete::*pii = 0;
    133   (void)(inc->*pii);
    134 }
    135 
    136 struct OverloadsPtrMem
    137 {
    138   int operator ->*(const char *);
    139 };
    140 
    141 void i() {
    142   OverloadsPtrMem m;
    143   int foo = m->*"Awesome!";
    144 }
    145 
    146 namespace pr5985 {
    147   struct c {
    148     void h();
    149     void f() {
    150       void (c::*p)();
    151       p = &h; // expected-error {{must explicitly qualify}}
    152       p = &this->h; // expected-error {{cannot create a non-constant pointer to member function}}
    153       p = &(*this).h; // expected-error {{cannot create a non-constant pointer to member function}}
    154     }
    155   };
    156 }
    157 
    158 namespace pr6783 {
    159   struct Base {};
    160   struct X; // expected-note {{forward declaration}}
    161 
    162   int test1(int Base::* p2m, X* object)
    163   {
    164     return object->*p2m; // expected-error {{left hand operand to ->*}}
    165   }
    166 }
    167 
    168 namespace PR7176 {
    169   namespace base
    170   {
    171     struct Process
    172     { };
    173     struct Continuous : Process
    174     {
    175       bool cond();
    176     };
    177   }
    178 
    179   typedef bool( base::Process::*Condition )();
    180 
    181   void m()
    182   { (void)(Condition) &base::Continuous::cond; }
    183 }
    184 
    185 namespace rdar8358512 {
    186   // We can't call this with an overload set because we're not allowed
    187   // to look into overload sets unless the parameter has some kind of
    188   // function type.
    189   template <class F> void bind(F f); // expected-note 12 {{candidate template ignored}}
    190   template <class F, class T> void bindmem(F (T::*f)()); // expected-note 4 {{candidate template ignored}}
    191   template <class F> void bindfn(F (*f)()); // expected-note 4 {{candidate template ignored}}
    192 
    193   struct A {
    194     void nonstat();
    195     void nonstat(int);
    196 
    197     void mixed();
    198     static void mixed(int);
    199 
    200     static void stat();
    201     static void stat(int);
    202 
    203     template <typename T> struct Test0 {
    204       void test() {
    205         bind(&nonstat); // expected-error {{no matching function for call}}
    206         bind(&A::nonstat); // expected-error {{no matching function for call}}
    207 
    208         bind(&mixed); // expected-error {{no matching function for call}}
    209         bind(&A::mixed); // expected-error {{no matching function for call}}
    210 
    211         bind(&stat); // expected-error {{no matching function for call}}
    212         bind(&A::stat); // expected-error {{no matching function for call}}
    213       }
    214     };
    215 
    216     template <typename T> struct Test1 {
    217       void test() {
    218         bindmem(&nonstat); // expected-error {{no matching function for call}}
    219         bindmem(&A::nonstat);
    220 
    221         bindmem(&mixed); // expected-error {{no matching function for call}}
    222         bindmem(&A::mixed);
    223 
    224         bindmem(&stat); // expected-error {{no matching function for call}}
    225         bindmem(&A::stat); // expected-error {{no matching function for call}}
    226       }
    227     };
    228 
    229     template <typename T> struct Test2 {
    230       void test() {
    231         bindfn(&nonstat); // expected-error {{no matching function for call}}
    232         bindfn(&A::nonstat); // expected-error {{no matching function for call}}
    233 
    234         bindfn(&mixed); // expected-error {{no matching function for call}}
    235         bindfn(&A::mixed); // expected-error {{no matching function for call}}
    236 
    237         bindfn(&stat);
    238         bindfn(&A::stat);
    239       }
    240     };
    241   };
    242 
    243   template <class T> class B {
    244     void nonstat();
    245     void nonstat(int);
    246 
    247     void mixed();
    248     static void mixed(int);
    249 
    250     static void stat();
    251     static void stat(int);
    252 
    253     // None of these can be diagnosed yet, because the arguments are
    254     // still dependent.
    255     void test0a() {
    256       bind(&nonstat);
    257       bind(&B::nonstat);
    258 
    259       bind(&mixed);
    260       bind(&B::mixed);
    261 
    262       bind(&stat);
    263       bind(&B::stat);
    264     }
    265 
    266     void test0b() {
    267       bind(&nonstat); // expected-error {{no matching function for call}}
    268       bind(&B::nonstat); // expected-error {{no matching function for call}}
    269 
    270       bind(&mixed); // expected-error {{no matching function for call}}
    271       bind(&B::mixed); // expected-error {{no matching function for call}}
    272 
    273       bind(&stat); // expected-error {{no matching function for call}}
    274       bind(&B::stat); // expected-error {{no matching function for call}}
    275     }
    276   };
    277 
    278   template void B<int>::test0b(); // expected-note {{in instantiation}}
    279 }
    280 
    281 namespace PR9973 {
    282   template<class R, class T> struct dm
    283   {
    284     typedef R T::*F;
    285     F f_;
    286     template<class U> int & call(U u)
    287     { return u->*f_; } // expected-error{{reference to non-static member function must be called; did you mean to call it with no arguments?}} expected-error {{non-const lvalue reference to type 'int' cannot bind to a temporary of type 'int'}}
    288 
    289     template<class U> int operator()(U u)
    290     { call(u); } // expected-note{{in instantiation of}}
    291   };
    292 
    293   template<class R, class T>
    294   dm<R, T> mem_fn(R T::*) ;
    295 
    296   struct test
    297   { int nullary_v(); };
    298 
    299   void f()
    300   {
    301     test* t;
    302     mem_fn(&test::nullary_v)(t); // expected-note{{in instantiation of}}
    303   }
    304 }
    305 
    306 namespace test8 {
    307   struct A { int foo; };
    308   int test1() {
    309     // Verify that we perform (and check) an lvalue conversion on the operands here.
    310     return (*((A**) 0)) // expected-warning {{indirection of non-volatile null pointer will be deleted}} expected-note {{consider}}
    311              ->**(int A::**) 0; // expected-warning {{indirection of non-volatile null pointer will be deleted}} expected-note {{consider}}
    312   }
    313 
    314   int test2() {
    315     // Verify that we perform (and check) an lvalue conversion on the operands here.
    316     // TODO: the .* should itself warn about being a dereference of null.
    317     return (*((A*) 0))
    318              .**(int A::**) 0; // expected-warning {{indirection of non-volatile null pointer will be deleted}} expected-note {{consider}}
    319   }
    320 }
    321