The Library Working Group have approved a change to std::for_each_n that requires it to handle negative N gracefully, which we were not doing for random access iterators.
* include/bits/stl_algo.h (for_each_n): Handle negative count. * testsuite/25_algorithms/for_each/for_each_n_debug.cc: New test. Tested powerpc64le-linux, committed to trunk.
commit 8a968a0ad62d5beae36f8ac33c4327d6c5599a33 Author: Jonathan Wakely <jwak...@redhat.com> Date: Thu Nov 7 21:42:52 2019 +0000 libstdc++: make negative count safe with std::for_each_n The Library Working Group have approved a change to std::for_each_n that requires it to handle negative N gracefully, which we were not doing for random access iterators. * include/bits/stl_algo.h (for_each_n): Handle negative count. * testsuite/25_algorithms/for_each/for_each_n_debug.cc: New test. diff --git a/libstdc++-v3/include/bits/stl_algo.h b/libstdc++-v3/include/bits/stl_algo.h index 661db0264ea..24322b7188d 100644 --- a/libstdc++-v3/include/bits/stl_algo.h +++ b/libstdc++-v3/include/bits/stl_algo.h @@ -4011,6 +4011,8 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO using _Cat = typename iterator_traits<_InputIterator>::iterator_category; if constexpr (is_base_of_v<random_access_iterator_tag, _Cat>) { + if (__n2 <= 0) + return __first; auto __last = __first + __n2; std::for_each(__first, __last, std::move(__f)); return __last; diff --git a/libstdc++-v3/testsuite/25_algorithms/for_each/for_each_n_debug.cc b/libstdc++-v3/testsuite/25_algorithms/for_each/for_each_n_debug.cc new file mode 100644 index 00000000000..24c14efbbf9 --- /dev/null +++ b/libstdc++-v3/testsuite/25_algorithms/for_each/for_each_n_debug.cc @@ -0,0 +1,44 @@ +// Copyright (C) 2019 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-options "-std=gnu++17" } +// { dg-do run { target c++17 } } + +#include <algorithm> +#include <debug/vector> +#include <debug/list> + +void +test01() +{ + __gnu_debug::vector<int> v{1, 2, 3}; + std::for_each_n(v.begin(), -2, [](int){}); +} + +void +test02() +{ + __gnu_debug::list<int> l{1, 2, 3}; + std::for_each_n(l.begin(), -2, [](int){}); +} + +int +main() +{ + test01(); + test02(); +}