diff options
author | Jonathan Wakely <jwakely@redhat.com> | 2017-03-16 14:32:07 +0000 |
---|---|---|
committer | Jonathan Wakely <redi@gcc.gnu.org> | 2017-03-16 14:32:07 +0000 |
commit | 8d85abab445d4f458826f4ef3acbc83091257c8b (patch) | |
tree | 92da033617f64f22ad263a8ad61b0ce6a424157e | |
parent | 7acc5349773cfe101d6ed116be30e15eb71b0d0f (diff) | |
download | gcc-8d85abab445d4f458826f4ef3acbc83091257c8b.zip gcc-8d85abab445d4f458826f4ef3acbc83091257c8b.tar.gz gcc-8d85abab445d4f458826f4ef3acbc83091257c8b.tar.bz2 |
PR libstdc++/80064 make heap algorithms work with function types
PR libstdc++/80064
* include/bits/stl_heap.h (__is_heap, push_heap, __adjust_heap)
(pop_heap, make_heap, sort_heap, is_heap_until, is_heap): Cope with
invalid instantiations using function types for _Compare argument.
* testsuite/25_algorithms/make_heap/80064.cc: New test.
From-SVN: r246197
-rw-r--r-- | libstdc++-v3/ChangeLog | 6 | ||||
-rw-r--r-- | libstdc++-v3/include/bits/stl_heap.h | 19 | ||||
-rw-r--r-- | libstdc++-v3/testsuite/25_algorithms/make_heap/80064.cc | 31 |
3 files changed, 49 insertions, 7 deletions
diff --git a/libstdc++-v3/ChangeLog b/libstdc++-v3/ChangeLog index 58b2522..63ed2da 100644 --- a/libstdc++-v3/ChangeLog +++ b/libstdc++-v3/ChangeLog @@ -1,5 +1,11 @@ 2017-03-16 Jonathan Wakely <jwakely@redhat.com> + PR libstdc++/80064 + * include/bits/stl_heap.h (__is_heap, push_heap, __adjust_heap) + (pop_heap, make_heap, sort_heap, is_heap_until, is_heap): Cope with + invalid instantiations using function types for _Compare argument. + * testsuite/25_algorithms/make_heap/80064.cc: New test. + PR libstdc++/67440 * python/libstdcxx/v6/printers.py (find_type): Avoid gdb.Type.name for GDB 7.6 compatibility, use gdb.Type.unqualified instead. diff --git a/libstdc++-v3/include/bits/stl_heap.h b/libstdc++-v3/include/bits/stl_heap.h index 3c102f1..f8cd0c0 100644 --- a/libstdc++-v3/include/bits/stl_heap.h +++ b/libstdc++-v3/include/bits/stl_heap.h @@ -100,7 +100,8 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION inline bool __is_heap(_RandomAccessIterator __first, _Compare __comp, _Distance __n) { - __gnu_cxx::__ops::_Iter_comp_iter<_Compare> __cmp(_GLIBCXX_MOVE(__comp)); + typedef __decltype(__comp) _Cmp; + __gnu_cxx::__ops::_Iter_comp_iter<_Cmp> __cmp(_GLIBCXX_MOVE(__comp)); return std::__is_heap_until(__first, __n, __cmp) == __n; } @@ -313,8 +314,8 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION if (__last - __first > 1) { - using __gnu_cxx::__ops::_Iter_comp_iter; - _Iter_comp_iter<_Compare> __cmp(_GLIBCXX_MOVE(__comp)); + typedef __decltype(__comp) _Cmp; + __gnu_cxx::__ops::_Iter_comp_iter<_Cmp> __cmp(_GLIBCXX_MOVE(__comp)); --__last; std::__pop_heap(__first, __last, __last, __cmp); } @@ -391,7 +392,8 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION __glibcxx_requires_valid_range(__first, __last); __glibcxx_requires_irreflexive_pred(__first, __last, __comp); - __gnu_cxx::__ops::_Iter_comp_iter<_Compare> __cmp(_GLIBCXX_MOVE(__comp)); + typedef __decltype(__comp) _Cmp; + __gnu_cxx::__ops::_Iter_comp_iter<_Cmp> __cmp(_GLIBCXX_MOVE(__comp)); std::__make_heap(__first, __last, __cmp); } @@ -454,7 +456,8 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION __glibcxx_requires_irreflexive_pred(__first, __last, __comp); __glibcxx_requires_heap_pred(__first, __last, __comp); - __gnu_cxx::__ops::_Iter_comp_iter<_Compare> __cmp(_GLIBCXX_MOVE(__comp)); + typedef __decltype(__comp) _Cmp; + __gnu_cxx::__ops::_Iter_comp_iter<_Cmp> __cmp(_GLIBCXX_MOVE(__comp)); std::__sort_heap(__first, __last, __cmp); } @@ -508,7 +511,8 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION __glibcxx_requires_valid_range(__first, __last); __glibcxx_requires_irreflexive_pred(__first, __last, __comp); - __gnu_cxx::__ops::_Iter_comp_iter<_Compare> __cmp(_GLIBCXX_MOVE(__comp)); + typedef __decltype(__comp) _Cmp; + __gnu_cxx::__ops::_Iter_comp_iter<_Cmp> __cmp(_GLIBCXX_MOVE(__comp)); return __first + std::__is_heap_until(__first, std::distance(__first, __last), __cmp); } @@ -545,7 +549,8 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION __glibcxx_requires_irreflexive_pred(__first, __last, __comp); const auto __dist = std::distance(__first, __last); - __gnu_cxx::__ops::_Iter_comp_iter<_Compare> __cmp(_GLIBCXX_MOVE(__comp)); + typedef __decltype(__comp) _Cmp; + __gnu_cxx::__ops::_Iter_comp_iter<_Cmp> __cmp(_GLIBCXX_MOVE(__comp)); return std::__is_heap_until(__first, __dist, __cmp) == __dist; } #endif diff --git a/libstdc++-v3/testsuite/25_algorithms/make_heap/80064.cc b/libstdc++-v3/testsuite/25_algorithms/make_heap/80064.cc new file mode 100644 index 0000000..eedcc32 --- /dev/null +++ b/libstdc++-v3/testsuite/25_algorithms/make_heap/80064.cc @@ -0,0 +1,31 @@ +// Copyright (C) 2017 Free Software Foundation, Inc. +// +// This file is part of the GNU ISO C++ Library. This library is free +// software; you can redistribute it and/or modify it under the +// terms of the GNU General Public License as published by the +// Free Software Foundation; either version 3, or (at your option) +// any later version. + +// This library is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. + +// You should have received a copy of the GNU General Public License along +// with this library; see the file COPYING3. If not see +// <http://www.gnu.org/licenses/>. + +// { dg-do compile } + +#include <algorithm> + +void +test01(int* first, int* last) +{ + extern bool cmp(int, int); + // PR libstdc++/80064 + // This is undefined, because [alg.sorting] requires the template argument + // Compare to be a function object type, and bool(int, int) is not an + // object type. We previously accepted it by accident, so keep doing so. + std::make_heap<int*, bool(int, int)>(first, last, cmp); +} |