libstdc++: Fix <ext/pointer.h> incompatibilities with C++20
authorJonathan Wakely <jwakely@redhat.com>
Thu, 9 Jan 2020 21:31:55 +0000 (21:31 +0000)
committerJonathan Wakely <redi@gcc.gnu.org>
Thu, 9 Jan 2020 21:31:55 +0000 (21:31 +0000)
The equality operators for _ExtPtr_allocator are defined as non-const
member functions, which causes ambiguities in C++20 due to the
synthesized operator!= candidates. They should always have been const.

The _Pointer_adapter class template has both value_type and element_type
members, which makes readable_traits<_Pointer_adapter<T>> ambiguous. The
intended workaround is to add a specialization of readable_traits.

* include/ext/extptr_allocator.h (_ExtPtr_allocator::operator==)
(_ExtPtr_allocator::operator!=): Add missing const qualifiers.
* include/ext/pointer.h (readable_traits<_Pointer_adapter<S>>): Add
partial specialization to disambiguate the two constrained
specializations.

From-SVN: r280067

libstdc++-v3/ChangeLog
libstdc++-v3/include/ext/extptr_allocator.h
libstdc++-v3/include/ext/pointer.h

index 721b465b369a425e5f07b58db9432fe676313ab4..65cd480ddcc69710390ed93b99096cebf619095d 100644 (file)
@@ -1,5 +1,11 @@
 2020-01-09  Jonathan Wakely  <jwakely@redhat.com>
 
+       * include/ext/extptr_allocator.h (_ExtPtr_allocator::operator==)
+       (_ExtPtr_allocator::operator!=): Add missing const qualifiers.
+       * include/ext/pointer.h (readable_traits<_Pointer_adapter<S>>): Add
+       partial specialization to disambiguate the two constrained
+       specializations.
+
        * include/experimental/type_traits (experimental::is_pod_v): Disable
        -Wdeprecated-declarations warnings around reference to std::is_pod.
        * include/std/type_traits (is_pod_v): Likewise.
index 933bdb69a51b85586b844d47e20b001a8dde8aca..88090548b7cddec7cdd9bf9813f18d8ebfb1f90f 100644 (file)
@@ -131,20 +131,20 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
 
       template<typename _Up>
         inline bool
-        operator==(const _ExtPtr_allocator<_Up>& __rarg)
+        operator==(const _ExtPtr_allocator<_Up>& __rarg) const
         { return _M_real_alloc == __rarg._M_getUnderlyingImp(); }
 
       inline bool
-      operator==(const _ExtPtr_allocator& __rarg)
+      operator==(const _ExtPtr_allocator& __rarg) const
       { return _M_real_alloc == __rarg._M_real_alloc; }
 
       template<typename _Up>
         inline bool
-        operator!=(const _ExtPtr_allocator<_Up>& __rarg)
+        operator!=(const _ExtPtr_allocator<_Up>& __rarg) const
         { return _M_real_alloc != __rarg._M_getUnderlyingImp(); }
 
       inline bool
-      operator!=(const _ExtPtr_allocator& __rarg)
+      operator!=(const _ExtPtr_allocator& __rarg) const
       { return _M_real_alloc != __rarg._M_real_alloc; }
 
       template<typename _Up>
index 84d530054e6d4cfa2c1d7459852e2b1adeba96c8..02d3e60169f853be051646d92d44d7c580a89880 100644 (file)
@@ -46,6 +46,9 @@
 # include <bits/move.h>
 # include <bits/ptr_traits.h>
 #endif
+#if __cplusplus > 201703L
+# include <iterator> // for readable_traits
+#endif
 
 namespace __gnu_cxx _GLIBCXX_VISIBILITY(default)
 {
@@ -594,6 +597,14 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
       { return pointer(std::addressof(__r)); }
     };
 
+#if __cpp_lib_concepts
+  template<typename _Storage_policy>
+    struct readable_traits<__gnu_cxx::_Pointer_adapter<_Storage_policy>>
+    {
+      using value_type
+       = typename __gnu_cxx::_Pointer_adapter<_Storage_policy>::value_type;
+    };
+#endif
 _GLIBCXX_END_NAMESPACE_VERSION
 } // namespace
 #endif