https://gcc.gnu.org/bugzilla/show_bug.cgi?id=79706

Jonathan Wakely <redi at gcc dot gnu.org> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
           Keywords|                            |rejects-valid
             Status|UNCONFIRMED                 |NEW
   Last reconfirmed|                            |2017-02-24
     Ever confirmed|0                           |1

--- Comment #3 from Jonathan Wakely <redi at gcc dot gnu.org> ---
This means libstdc++ can't use SFINAE to check if a delete[] expression is
well-formed:


namespace std {
  template<typename T> T&& declval();

  template<typename, typename = void> struct result_of { };
  template<typename F, typename A>
    struct result_of<F(A), decltype(declval<F>()(declval<A>()))>
    {
      using type = decltype(declval<F>()(declval<A>()));
    };
}

template<bool _Array, typename _Yp, typename = void>
  struct can_delete { };

template<typename _Yp>
  struct can_delete<true, _Yp, decltype(delete[] std::declval<_Yp*>())>
  { void operator()(_Yp*) const; };

template<typename _Yp>
  struct can_delete<false, _Yp, decltype(delete std::declval<_Yp*>())>
  { void operator()(_Yp*) const; };

struct A {
  void operator delete[](void*) = delete;
  void operator delete(void*) = delete;
};

std::result_of<can_delete<true, A>(A*)> r;


The result_of primary template should be used, but instead we get errors (or
one error, five times) while trying to match the partial specialization:

sp.cc: In instantiation of ‘struct can_delete<true, A>’:
sp.cc:6:49:   required by substitution of ‘template<class F, class A> struct
std::result_of<F(A), decltype (declval<F>()(declval<A>()))> [with F =
can_delete<true, A>; A = A*]’
sp.cc:28:41:   required from here
sp.cc:17:3: error: use of deleted function ‘static void A::operator delete
[](void*)’
   { void operator()(_Yp*) const; };
   ^
sp.cc:24:8: note: declared here
   void operator delete[](void*) = delete;
        ^~~~~~~~
sp.cc:17:3: error: use of deleted function ‘static void A::operator delete
[](void*)’
   { void operator()(_Yp*) const; };
   ^
sp.cc:24:8: note: declared here
   void operator delete[](void*) = delete;
        ^~~~~~~~
sp.cc:17:10: error: use of deleted function ‘static void A::operator delete
[](void*)’
   { void operator()(_Yp*) const; };
          ^~~~~~~~
sp.cc:24:8: note: declared here
   void operator delete[](void*) = delete;
        ^~~~~~~~
sp.cc:17:10: error: use of deleted function ‘static void A::operator delete
[](void*)’
   { void operator()(_Yp*) const; };
          ^~~~~~~~
sp.cc:24:8: note: declared here
   void operator delete[](void*) = delete;
        ^~~~~~~~
sp.cc:17:27: error: use of deleted function ‘static void A::operator delete
[](void*)’
   { void operator()(_Yp*) const; };
                           ^~~~~
sp.cc:24:8: note: declared here
   void operator delete[](void*) = delete;
        ^~~~~~~~

Reply via email to