diff options
author | François Dumont <fdumont@gcc.gnu.org> | 2011-09-17 09:12:24 +0000 |
---|---|---|
committer | François Dumont <fdumont@gcc.gnu.org> | 2011-09-17 09:12:24 +0000 |
commit | 1c56f7cb72978a9b92beb1903a6f5b2f371c0ebd (patch) | |
tree | 61b2d732f425b25d21ff17fc77c5100c1255f1cf | |
parent | ab2fd9953bad95e662e70215b955d13db538fd2d (diff) | |
download | gcc-1c56f7cb72978a9b92beb1903a6f5b2f371c0ebd.zip gcc-1c56f7cb72978a9b92beb1903a6f5b2f371c0ebd.tar.gz gcc-1c56f7cb72978a9b92beb1903a6f5b2f371c0ebd.tar.bz2 |
hashtable.h (_Hashtable<>::__rehash_policy(const _RehashPolicy&)): Commit the modification of the policy only if no exception occured.
2011-09-17 François Dumont <fdumont@gcc.gnu.org>
* include/bits/hashtable.h (_Hashtable<>::__rehash_policy(const
_RehashPolicy&)): Commit the modification of the policy only if no
exception occured.
* testsuite/23_containers/unordered_set/max_load_factor/robustness.cc:
New.
From-SVN: r178927
-rw-r--r-- | libstdc++-v3/ChangeLog | 8 | ||||
-rw-r--r-- | libstdc++-v3/include/bits/hashtable.h | 4 | ||||
-rw-r--r-- | libstdc++-v3/testsuite/23_containers/unordered_set/max_load_factor/robustness.cc | 77 |
3 files changed, 87 insertions, 2 deletions
diff --git a/libstdc++-v3/ChangeLog b/libstdc++-v3/ChangeLog index 910fafc..4e0ddf4 100644 --- a/libstdc++-v3/ChangeLog +++ b/libstdc++-v3/ChangeLog @@ -1,3 +1,11 @@ +2011-09-17 François Dumont <fdumont@gcc.gnu.org> + + * include/bits/hashtable.h (_Hashtable<>::__rehash_policy(const + _RehashPolicy&)): Commit the modification of the policy only if no + exception occured. + * testsuite/23_containers/unordered_set/max_load_factor/robustness.cc: + New. + 2011-09-16 Paolo Carlini <paolo.carlini@oracle.com> * testsuite/23_containers/array/comparison_operators/ diff --git a/libstdc++-v3/include/bits/hashtable.h b/libstdc++-v3/include/bits/hashtable.h index b097ee7..5c74066 100644 --- a/libstdc++-v3/include/bits/hashtable.h +++ b/libstdc++-v3/include/bits/hashtable.h @@ -741,10 +741,10 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION _H1, _H2, _Hash, _RehashPolicy, __chc, __cit, __uk>:: __rehash_policy(const _RehashPolicy& __pol) { - _M_rehash_policy = __pol; size_type __n_bkt = __pol._M_bkt_for_elements(_M_element_count); if (__n_bkt > _M_bucket_count) - _M_rehash(__n_bkt, __pol._M_next_resize); + _M_rehash(__n_bkt, _M_rehash_policy._M_next_resize); + _M_rehash_policy = __pol; } template<typename _Key, typename _Value, diff --git a/libstdc++-v3/testsuite/23_containers/unordered_set/max_load_factor/robustness.cc b/libstdc++-v3/testsuite/23_containers/unordered_set/max_load_factor/robustness.cc new file mode 100644 index 0000000..7db51f7 --- /dev/null +++ b/libstdc++-v3/testsuite/23_containers/unordered_set/max_load_factor/robustness.cc @@ -0,0 +1,77 @@ +// { dg-options "-std=gnu++0x" } + +// Copyright (C) 2011 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/>. + +#include <unordered_set> +#include <limits> +#include <ext/throw_allocator.h> +#include <testsuite_hooks.h> + +void test01() +{ + bool test __attribute__((unused)) = true; + + typedef std::numeric_limits<std::size_t> nl_size_t; + std::unordered_set<int, std::hash<int>, std::equal_to<int>, + __gnu_cxx::throw_allocator_limit<int> > us; + int val = 0; + for (; val != 100; ++val) + { + VERIFY( us.insert(val).second) ; + VERIFY( us.load_factor() <= us.max_load_factor() ); + } + + float cur_max_load_factor = us.max_load_factor(); + int counter = 0; + std::size_t thrown_exceptions = 0; + while (true) + { + __gnu_cxx::limit_condition::set_limit(counter++); + bool do_break = false; + try + { + us.max_load_factor(.5f); + do_break = true; + } + catch (const __gnu_cxx::forced_error&) + { + VERIFY( us.max_load_factor() == cur_max_load_factor ); + ++thrown_exceptions; + } + // Lets check that unordered_set will still be correctly resized + // when needed + __gnu_cxx::limit_condition::set_limit(nl_size_t::max()); + for (;;) + { + VERIFY( us.load_factor() <= us.max_load_factor() ); + size_t nbkts = us.bucket_count(); + VERIFY( us.insert(val++).second ); + if (us.bucket_count() != nbkts) + break; + } + if (do_break) + break; + } + VERIFY( thrown_exceptions > 0 ); +} + +int main() +{ + test01(); + return 0; +} |