The standard does not require const-correct comparisons in list::sort.

Tested powerpc64le-linux, committed to trunk.


libstdc++-v3/ChangeLog:

        PR libstdc++/66742
        * include/bits/list.tcc (list::sort): Use mutable iterators for
        comparisons.
        * include/bits/stl_list.h (_Scratch_list::_Ptr_cmp): Likewise.
        * testsuite/23_containers/list/operations/66742.cc: Check
        non-const comparisons.
---
 libstdc++-v3/include/bits/list.tcc            |  4 ++--
 libstdc++-v3/include/bits/stl_list.h          |  8 +++----
 .../23_containers/list/operations/66742.cc    | 23 +++++++++++++++++++
 3 files changed, 29 insertions(+), 6 deletions(-)

diff --git a/libstdc++-v3/include/bits/list.tcc 
b/libstdc++-v3/include/bits/list.tcc
index 7f4e1569ab1..cc750c98a2d 100644
--- a/libstdc++-v3/include/bits/list.tcc
+++ b/libstdc++-v3/include/bits/list.tcc
@@ -499,7 +499,7 @@ _GLIBCXX_BEGIN_NAMESPACE_CONTAINER
        _Scratch_list* __fill = __tmp;
        _Scratch_list* __counter;
 
-       _Scratch_list::_Ptr_cmp<const_iterator, void> __ptr_comp;
+       _Scratch_list::_Ptr_cmp<iterator, void> __ptr_comp;
 
        __try
          {
@@ -623,7 +623,7 @@ _GLIBCXX_BEGIN_NAMESPACE_CONTAINER
          _Scratch_list* __fill = __tmp;
          _Scratch_list* __counter;
 
-       _Scratch_list::_Ptr_cmp<const_iterator, _StrictWeakOrdering> __ptr_comp
+       _Scratch_list::_Ptr_cmp<iterator, _StrictWeakOrdering> __ptr_comp
          = { __comp };
 
          __try
diff --git a/libstdc++-v3/include/bits/stl_list.h 
b/libstdc++-v3/include/bits/stl_list.h
index 96d2a2f0f69..ffaaa6dfd97 100644
--- a/libstdc++-v3/include/bits/stl_list.h
+++ b/libstdc++-v3/include/bits/stl_list.h
@@ -174,8 +174,8 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
          _Cmp _M_cmp;
 
          bool
-         operator()(const __detail::_List_node_base* __lhs,
-                    const __detail::_List_node_base* __rhs) /* not const */
+         operator()(__detail::_List_node_base* __lhs,
+                    __detail::_List_node_base* __rhs) /* not const */
          { return _M_cmp(*_Iter(__lhs), *_Iter(__rhs)); }
        };
 
@@ -183,8 +183,8 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
        struct _Ptr_cmp<_Iter, void>
        {
          bool
-         operator()(const __detail::_List_node_base* __lhs,
-                    const __detail::_List_node_base* __rhs) const
+         operator()(__detail::_List_node_base* __lhs,
+                    __detail::_List_node_base* __rhs) const
          { return *_Iter(__lhs) < *_Iter(__rhs); }
        };
 
diff --git a/libstdc++-v3/testsuite/23_containers/list/operations/66742.cc 
b/libstdc++-v3/testsuite/23_containers/list/operations/66742.cc
index 24bda3920d8..94a37a31de7 100644
--- a/libstdc++-v3/testsuite/23_containers/list/operations/66742.cc
+++ b/libstdc++-v3/testsuite/23_containers/list/operations/66742.cc
@@ -48,8 +48,31 @@ test01()
   VERIFY( is_sorted(l, std::greater<int>()) );
 }
 
+void
+test02()
+{
+  // The standard doesn't require comparisons to be const-correct.
+  // The initial fix for PR 66742 caused a regression here.
+
+  struct X
+  {
+    bool operator<(X&) /* non-const */ { return false; }
+  };
+
+  struct Cmp
+  {
+    bool operator()(X&, X&) /* non-const */ { return false; }
+  };
+
+  std::list<X> l;
+  l.sort();
+  Cmp c;
+  l.sort(c);
+}
+
 int
 main()
 {
   test01();
+  test02();
 }
-- 
2.31.1

Reply via email to