Home | History | Annotate | Download | only in over.over
      1 // RUN: %clang_cc1 -fsyntax-only -verify -Wno-bool-conversion %s
      2 
      3 typedef __typeof__(((int*)0)-((int*)0)) ptrdiff_t;
      4 
      5 namespace DontResolveTooEarly_WaitForOverloadResolution
      6 {
      7   template <class T> T* f(int);	// #1
      8   template <class T, class U> T& f(U); // #2
      9 
     10   void g() {
     11     int *ip = f<int>(1);	// calls #1
     12   }
     13 
     14   template <class T>
     15     T* f2(int);
     16   template <class T, class U>
     17     T& f2(U);
     18 
     19   void g2() {
     20     int*ip = (f2<int>)(1); // ok
     21   }
     22 
     23 } // End namespace
     24 
     25 namespace DontAllowUnresolvedOverloadedExpressionInAnUnusedExpression
     26 {
     27   void one() { }
     28   template<class T> void oneT() { }
     29 
     30   void two() { } // expected-note 2 {{possible target for call}}
     31   void two(int) { } // expected-note 2 {{possible target for call}}
     32   template<class T> void twoT() { }  // expected-note 2 {{possible target for call}}
     33   template<class T> void twoT(T) { }  // expected-note 2 {{possible target for call}}
     34 
     35   void check()
     36   {
     37     one; // expected-warning {{expression result unused}}
     38     two; // expected-error{{reference to overloaded function could not be resolved; did you mean to call it with no arguments?}}
     39     oneT<int>; // expected-warning {{expression result unused}}
     40     twoT<int>; // expected-error {{reference to overloaded function could not be resolved; did you mean to call it?}}
     41   }
     42 
     43   // check the template function case
     44   template<class T> void check()
     45   {
     46     one; // expected-warning {{expression result unused}}
     47     two; // expected-error{{reference to overloaded function could not be resolved; did you mean to call it with no arguments?}}
     48     oneT<int>; // expected-warning {{expression result unused}}
     49     twoT<int>; // expected-error {{reference to overloaded function could not be resolved; did you mean to call it?}}
     50 
     51   }
     52 
     53 }
     54 
     55   template<typename T>
     56     void twoT() { }
     57   template<typename T, typename U>
     58     void twoT(T) { }
     59 
     60 
     61   void two() { }; //expected-note 5{{candidate}}
     62   void two(int) { }; //expected-note 5{{candidate}}
     63 
     64 
     65 
     66   void one() { }
     67   template<class T>
     68     void oneT() { }
     69 
     70   template<class T>
     71   void cant_resolve() { } //expected-note 3{{candidate}}
     72 
     73   template<class T> void cant_resolve(T) { }//expected-note 3{{candidate}}
     74 
     75 
     76 int main()
     77 {
     78 
     79   { static_cast<void>(one); }
     80   { (void)(one); }
     81   { static_cast<void>(oneT<int>); }
     82   { (void)(oneT<int>); }
     83 
     84   { static_cast<void>(two); } // expected-error {{address of overloaded function 'two' cannot be static_cast to type 'void'}}
     85   { (void)(two); } // expected-error {{address of overloaded function 'two' cannot be cast to type 'void'}}
     86   { static_cast<void>(twoT<int>); }
     87   { (void)(twoT<int>); }
     88 
     89 
     90   { ptrdiff_t x = reinterpret_cast<ptrdiff_t>(oneT<int>); }
     91   { (void) reinterpret_cast<int (*)(char, double)>(oneT<int>); }
     92   { (void) reinterpret_cast<ptrdiff_t>(one); }
     93   { (void) reinterpret_cast<int (*)(char, double)>(one); }
     94 
     95   { ptrdiff_t x = reinterpret_cast<ptrdiff_t>(twoT<int>); }
     96   { (void) reinterpret_cast<int (*)(char, double)>(twoT<int>); }
     97   { (void) reinterpret_cast<void (*)(int)>(two); } //expected-error {{reinterpret_cast}}
     98   { (void) static_cast<void (*)(int)>(two); } //ok
     99 
    100   { (void) reinterpret_cast<int>(two); } //expected-error {{reinterpret_cast}}
    101   { (void) reinterpret_cast<int (*)(char, double)>(two); } //expected-error {{reinterpret_cast}}
    102 
    103   { bool b = (twoT<int>); }
    104   { bool b = (twoT<int, int>); }
    105 
    106   { bool b = &twoT<int>; //&foo<int>; }
    107     b = &(twoT<int>); }
    108 
    109   { ptrdiff_t x = (ptrdiff_t) &twoT<int>;
    110       x = (ptrdiff_t) &twoT<int>; }
    111 
    112   { ptrdiff_t x = (ptrdiff_t) twoT<int>;
    113       x = (ptrdiff_t) twoT<int>; }
    114 
    115 
    116   { ptrdiff_t x = (ptrdiff_t) &twoT<int,int>;
    117   x = (ptrdiff_t) &twoT<int>; }
    118 
    119   { oneT<int>;   &oneT<int>; } //expected-warning 2{{expression result unused}}
    120   { static_cast<void>(cant_resolve<int>); } // expected-error {{address of overload}}
    121   { bool b = cant_resolve<int>; } // expected-error {{address of overload}}
    122   { (void) cant_resolve<int>; } // expected-error {{address of overload}}
    123 
    124 }
    125 
    126 namespace member_pointers {
    127   struct S {
    128     template <typename T> bool f(T) { return false; }
    129     template <typename T> static bool g(T) { return false; }
    130 
    131     template <typename T> bool h(T) { return false; }  // expected-note 3 {{possible target for call}}
    132     template <int N> static bool h(int) { return false; } // expected-note 3 {{possible target for call}}
    133   };
    134 
    135   void test(S s) {
    136     if (S::f<char>) return; // expected-error {{call to non-static member function without an object argument}}
    137     if (S::f<int>) return; // expected-error {{call to non-static member function without an object argument}}
    138     if (&S::f<char>) return;
    139     if (&S::f<int>) return;
    140     if (s.f<char>) return; // expected-error {{reference to non-static member function must be called}}
    141     if (s.f<int>) return; // expected-error {{reference to non-static member function must be called}}
    142     if (&s.f<char>) return; // expected-error {{cannot create a non-constant pointer to member function}}
    143     if (&s.f<int>) return; // expected-error {{cannot create a non-constant pointer to member function}}
    144 
    145     if (S::g<char>) return;
    146     if (S::g<int>) return;
    147     if (&S::g<char>) return;
    148     if (&S::g<int>) return;
    149     if (s.g<char>) return;
    150     if (s.g<int>) return;
    151     if (&s.g<char>) return;
    152     if (&s.g<int>) return;
    153 
    154     if (S::h<42>) return;
    155     if (S::h<int>) return; // expected-error {{reference to overloaded function could not be resolved; did you mean to call it?}}
    156     if (&S::h<42>) return;
    157     if (&S::h<int>) return;
    158     if (s.h<42>) return;
    159     if (s.h<int>) return; // expected-error {{reference to overloaded function could not be resolved; did you mean to call it?}}
    160     if (&s.h<42>) return;
    161     if (&s.h<int>) return; // expected-error {{reference to overloaded function could not be resolved; did you mean to call it?}}
    162 
    163     { bool b = S::f<char>; } // expected-error {{call to non-static member function without an object argument}}
    164     { bool b = S::f<int>; } // expected-error {{call to non-static member function without an object argument}}
    165     { bool b = &S::f<char>; }
    166     { bool b = &S::f<int>; }
    167     // These next two errors are terrible.
    168     { bool b = s.f<char>; } // expected-error {{reference to non-static member function must be called}}
    169     { bool b = s.f<int>; } // expected-error {{reference to non-static member function must be called}}
    170     { bool b = &s.f<char>; } // expected-error {{cannot create a non-constant pointer to member function}}
    171     { bool b = &s.f<int>; } // expected-error {{cannot create a non-constant pointer to member function}}
    172 
    173     { bool b = S::g<char>; }
    174     { bool b = S::g<int>; }
    175     { bool b = &S::g<char>; }
    176     { bool b = &S::g<int>; }
    177     { bool b = s.g<char>; }
    178     { bool b = s.g<int>; }
    179     { bool b = &s.g<char>; }
    180     { bool b = &s.g<int>; }
    181 
    182     { bool b = S::h<42>; }
    183     { bool b = S::h<int>; } // expected-error {{can't form member pointer of type 'bool' without '&' and class name}}
    184     { bool b = &S::h<42>; }
    185     { bool b = &S::h<int>; }
    186     { bool b = s.h<42>; }
    187     { bool b = s.h<int>; } // expected-error {{can't form member pointer of type 'bool' without '&' and class name}}
    188     { bool b = &s.h<42>; }
    189     { bool b = &s.h<int>; } // expected-error {{can't form member pointer of type 'bool' without '&' and class name}}
    190   }
    191 }
    192