aboutsummaryrefslogtreecommitdiff
path: root/libstdc++-v3/src
diff options
context:
space:
mode:
authorBenjamin Kosnik <bkoz@gcc.gnu.org>2009-01-08 03:14:24 +0000
committerBenjamin Kosnik <bkoz@gcc.gnu.org>2009-01-08 03:14:24 +0000
commit9982752346aac68d257d258332591df1f7b7817d (patch)
treea6f1e0438084e4f64331de987399b0292a383367 /libstdc++-v3/src
parentf5651df1abb64343a5e18ed6af8cde899d4b2198 (diff)
downloadgcc-9982752346aac68d257d258332591df1f7b7817d.zip
gcc-9982752346aac68d257d258332591df1f7b7817d.tar.gz
gcc-9982752346aac68d257d258332591df1f7b7817d.tar.bz2
re PR libstdc++/36801 (config/cpu/generic/atomicity_mutex/atomicity.h incorrectly relies on global constructor ordering)
2009-01-07 Benjamin Kosnik <bkoz@redhat.com> Jonathan Larmour <jifl@eCosCentric.com> PR libstdc++/36801 * config/cpu/generic/atomicity_mutex/atomicity.h (get_atomic_mutex): New. (__gnu_cxx::__exchange_and_add): Use it. * src/atomic.cc (get_atomic_mutex): New. * src/debug.cc (get_safe_base_mutex): New. * src/locale.cc (get_locale_cache_mutex): New. * src/mt_allocator.cc (get_freelist): New. (get_freelist_mutex): New. * src/pool_allocator.cc (get_palloc_mutex): New. * include/std/mutex (__once_functor_lock): To (__get_once_functor_lock): ...this. * src/mutex.cc (__once_mutex): Don't export, use (get_once_mutex): ...this. * config/abi/pre/gnu.ver: Adjust exports. From-SVN: r143182
Diffstat (limited to 'libstdc++-v3/src')
-rw-r--r--libstdc++-v3/src/atomic.cc13
-rw-r--r--libstdc++-v3/src/debug.cc25
-rw-r--r--libstdc++-v3/src/locale.cc12
-rw-r--r--libstdc++-v3/src/mt_allocator.cc44
-rw-r--r--libstdc++-v3/src/mutex.cc26
-rw-r--r--libstdc++-v3/src/pool_allocator.cc11
6 files changed, 92 insertions, 39 deletions
diff --git a/libstdc++-v3/src/atomic.cc b/libstdc++-v3/src/atomic.cc
index 9e6444d..5cb3919 100644
--- a/libstdc++-v3/src/atomic.cc
+++ b/libstdc++-v3/src/atomic.cc
@@ -1,6 +1,6 @@
// Support for atomic operations -*- C++ -*-
-// Copyright (C) 2008
+// Copyright (C) 2008, 2009
// Free Software Foundation, Inc.
//
// This file is part of the GNU ISO C++ Library. This library is free
@@ -37,7 +37,12 @@
namespace
{
#if defined(_GLIBCXX_HAS_GTHREADS) && defined(_GLIBCXX_USE_C99_STDINT_TR1)
- std::mutex atomic_mutex;
+ std::mutex&
+ get_atomic_mutex()
+ {
+ static std::mutex atomic_mutex;
+ return atomic_mutex;
+ }
#endif
std::__atomic_flag_base volatile flag_table[ 1 << LOGSIZE ] =
@@ -57,7 +62,7 @@ namespace std
atomic_flag::test_and_set(memory_order) volatile
{
#if defined(_GLIBCXX_HAS_GTHREADS) && defined(_GLIBCXX_USE_C99_STDINT_TR1)
- lock_guard<mutex> __lock(atomic_mutex);
+ lock_guard<mutex> __lock(get_atomic_mutex());
#endif
bool result = _M_i;
_M_i = true;
@@ -68,7 +73,7 @@ namespace std
atomic_flag::clear(memory_order) volatile
{
#if defined(_GLIBCXX_HAS_GTHREADS) && defined(_GLIBCXX_USE_C99_STDINT_TR1)
- lock_guard<mutex> __lock(atomic_mutex);
+ lock_guard<mutex> __lock(get_atomic_mutex());
#endif
_M_i = false;
}
diff --git a/libstdc++-v3/src/debug.cc b/libstdc++-v3/src/debug.cc
index 0391368..4b7fac7 100644
--- a/libstdc++-v3/src/debug.cc
+++ b/libstdc++-v3/src/debug.cc
@@ -1,6 +1,6 @@
// Debugging mode support code -*- C++ -*-
-// Copyright (C) 2003, 2004, 2005, 2006, 2007
+// Copyright (C) 2003, 2004, 2005, 2006, 2007, 2009
// Free Software Foundation, Inc.
//
// This file is part of the GNU ISO C++ Library. This library is free
@@ -42,7 +42,12 @@ using namespace std;
namespace
{
- __gnu_cxx::__mutex safe_base_mutex;
+ __gnu_cxx::__mutex&
+ get_safe_base_mutex()
+ {
+ static __gnu_cxx::__mutex safe_base_mutex;
+ return safe_base_mutex;
+ }
} // anonymous namespace
namespace __gnu_debug
@@ -112,7 +117,7 @@ namespace __gnu_debug
_Safe_sequence_base::
_M_detach_all()
{
- __gnu_cxx::__scoped_lock sentry(safe_base_mutex);
+ __gnu_cxx::__scoped_lock sentry(_M_get_mutex());
for (_Safe_iterator_base* __iter = _M_iterators; __iter;)
{
_Safe_iterator_base* __old = __iter;
@@ -132,7 +137,7 @@ namespace __gnu_debug
_Safe_sequence_base::
_M_detach_singular()
{
- __gnu_cxx::__scoped_lock sentry(safe_base_mutex);
+ __gnu_cxx::__scoped_lock sentry(_M_get_mutex());
for (_Safe_iterator_base* __iter = _M_iterators; __iter;)
{
_Safe_iterator_base* __old = __iter;
@@ -154,7 +159,7 @@ namespace __gnu_debug
_Safe_sequence_base::
_M_revalidate_singular()
{
- __gnu_cxx::__scoped_lock sentry(safe_base_mutex);
+ __gnu_cxx::__scoped_lock sentry(_M_get_mutex());
for (_Safe_iterator_base* __iter = _M_iterators; __iter;
__iter = __iter->_M_next)
__iter->_M_version = _M_version;
@@ -168,7 +173,7 @@ namespace __gnu_debug
_Safe_sequence_base::
_M_swap(_Safe_sequence_base& __x)
{
- __gnu_cxx::__scoped_lock sentry(safe_base_mutex);
+ __gnu_cxx::__scoped_lock sentry(_M_get_mutex());
swap(_M_iterators, __x._M_iterators);
swap(_M_const_iterators, __x._M_const_iterators);
swap(_M_version, __x._M_version);
@@ -186,13 +191,13 @@ namespace __gnu_debug
__gnu_cxx::__mutex&
_Safe_sequence_base::
_M_get_mutex()
- { return safe_base_mutex; }
+ { return get_safe_base_mutex(); }
void
_Safe_iterator_base::
_M_attach(_Safe_sequence_base* __seq, bool __constant)
{
- __gnu_cxx::__scoped_lock sentry(safe_base_mutex);
+ __gnu_cxx::__scoped_lock sentry(_M_get_mutex());
_M_attach_single(__seq, __constant);
}
@@ -229,7 +234,7 @@ namespace __gnu_debug
_Safe_iterator_base::
_M_detach()
{
- __gnu_cxx::__scoped_lock sentry(safe_base_mutex);
+ __gnu_cxx::__scoped_lock sentry(_M_get_mutex());
_M_detach_single();
}
@@ -273,7 +278,7 @@ namespace __gnu_debug
__gnu_cxx::__mutex&
_Safe_iterator_base::
_M_get_mutex()
- { return safe_base_mutex; }
+ { return get_safe_base_mutex(); }
void
_Error_formatter::_Parameter::
diff --git a/libstdc++-v3/src/locale.cc b/libstdc++-v3/src/locale.cc
index a760994..7c30fc0 100644
--- a/libstdc++-v3/src/locale.cc
+++ b/libstdc++-v3/src/locale.cc
@@ -1,4 +1,5 @@
-// Copyright (C) 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006
+// Copyright (C) 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006,
+// 2009
// Free Software Foundation, Inc.
//
// This file is part of the GNU ISO C++ Library. This library is free
@@ -36,7 +37,12 @@
namespace
{
- __gnu_cxx::__mutex locale_cache_mutex;
+ __gnu_cxx::__mutex&
+ get_locale_cache_mutex()
+ {
+ static __gnu_cxx::__mutex locale_cache_mutex;
+ return locale_cache_mutex;
+ }
} // anonymous namespace
// XXX GLIBCXX_ABI Deprecated
@@ -389,7 +395,7 @@ _GLIBCXX_BEGIN_NAMESPACE(std)
locale::_Impl::
_M_install_cache(const facet* __cache, size_t __index)
{
- __gnu_cxx::__scoped_lock sentry(locale_cache_mutex);
+ __gnu_cxx::__scoped_lock sentry(get_locale_cache_mutex());
if (_M_caches[__index] != 0)
{
// Some other thread got in first.
diff --git a/libstdc++-v3/src/mt_allocator.cc b/libstdc++-v3/src/mt_allocator.cc
index 1e64227..3430ad3 100644
--- a/libstdc++-v3/src/mt_allocator.cc
+++ b/libstdc++-v3/src/mt_allocator.cc
@@ -1,6 +1,6 @@
// Allocator details.
-// Copyright (C) 2004, 2005, 2006 Free Software Foundation, Inc.
+// Copyright (C) 2004, 2005, 2006, 2009 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
@@ -57,21 +57,34 @@ namespace
}
};
- // Ensure freelist is constructed first.
- static __freelist freelist;
- __gnu_cxx::__mutex freelist_mutex;
+ __freelist&
+ get_freelist()
+ {
+ static __freelist freelist;
+ return freelist;
+ }
+
+ __gnu_cxx::__mutex&
+ get_freelist_mutex()
+ {
+ static __gnu_cxx::__mutex freelist_mutex;
+ return freelist_mutex;
+ }
static void
_M_destroy_thread_key(void* __id)
{
// Return this thread id record to the front of thread_freelist.
- __gnu_cxx::__scoped_lock sentry(freelist_mutex);
- size_t _M_id = reinterpret_cast<size_t>(__id);
-
- typedef __gnu_cxx::__pool<true>::_Thread_record _Thread_record;
- _Thread_record* __tr = &freelist._M_thread_freelist_array[_M_id - 1];
- __tr->_M_next = freelist._M_thread_freelist;
- freelist._M_thread_freelist = __tr;
+ __freelist& freelist = get_freelist();
+ {
+ __gnu_cxx::__scoped_lock sentry(get_freelist_mutex());
+ size_t _M_id = reinterpret_cast<size_t>(__id);
+
+ typedef __gnu_cxx::__pool<true>::_Thread_record _Thread_record;
+ _Thread_record* __tr = &freelist._M_thread_freelist_array[_M_id - 1];
+ __tr->_M_next = freelist._M_thread_freelist;
+ freelist._M_thread_freelist = __tr;
+ }
}
#endif
} // anonymous namespace
@@ -496,8 +509,9 @@ _GLIBCXX_BEGIN_NAMESPACE(__gnu_cxx)
// directly and have no need for this.
if (__gthread_active_p())
{
+ __freelist& freelist = get_freelist();
{
- __gnu_cxx::__scoped_lock sentry(freelist_mutex);
+ __gnu_cxx::__scoped_lock sentry(get_freelist_mutex());
if (!freelist._M_thread_freelist_array
|| freelist._M_max_threads < _M_options._M_max_threads)
@@ -613,12 +627,13 @@ _GLIBCXX_BEGIN_NAMESPACE(__gnu_cxx)
// returns its id.
if (__gthread_active_p())
{
+ __freelist& freelist = get_freelist();
void* v = __gthread_getspecific(freelist._M_key);
size_t _M_id = (size_t)v;
if (_M_id == 0)
{
{
- __gnu_cxx::__scoped_lock sentry(freelist_mutex);
+ __gnu_cxx::__scoped_lock sentry(get_freelist_mutex());
if (freelist._M_thread_freelist)
{
_M_id = freelist._M_thread_freelist->_M_id;
@@ -689,8 +704,9 @@ _GLIBCXX_BEGIN_NAMESPACE(__gnu_cxx)
// directly and have no need for this.
if (__gthread_active_p())
{
+ __freelist& freelist = get_freelist();
{
- __gnu_cxx::__scoped_lock sentry(freelist_mutex);
+ __gnu_cxx::__scoped_lock sentry(get_freelist_mutex());
if (!freelist._M_thread_freelist_array
|| freelist._M_max_threads < _M_options._M_max_threads)
diff --git a/libstdc++-v3/src/mutex.cc b/libstdc++-v3/src/mutex.cc
index 8fae030..26435a2 100644
--- a/libstdc++-v3/src/mutex.cc
+++ b/libstdc++-v3/src/mutex.cc
@@ -1,6 +1,6 @@
// mutex -*- C++ -*-
-// Copyright (C) 2008 Free Software Foundation, Inc.
+// Copyright (C) 2008, 2009 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
@@ -30,6 +30,17 @@
#include <mutex>
#if defined(_GLIBCXX_HAS_GTHREADS) && defined(_GLIBCXX_USE_C99_STDINT_TR1)
+#ifndef _GLIBCXX_HAVE_TLS
+namespace
+{
+ std::mutex&
+ get_once_mutex()
+ {
+ static std::mutex once_mutex;
+ return once_mutex;
+ }
+}
+#endif
namespace std
{
@@ -45,11 +56,16 @@ namespace std
__thread void* __once_callable;
__thread void (*__once_call)();
#else
- // explicit instantiation due to -fno-implicit-instantiation
+ // Explicit instantiation due to -fno-implicit-instantiation.
template class function<void()>;
function<void()> __once_functor;
- mutex __once_mutex;
- unique_lock<mutex> __once_functor_lock(__once_mutex, defer_lock);
+
+ unique_lock<mutex>&
+ __get_once_functor_lock()
+ {
+ static unique_lock<mutex> once_functor_lock(get_once_mutex(), defer_lock);
+ return once_functor_lock;
+ }
#endif
extern "C"
@@ -58,7 +74,7 @@ namespace std
{
#ifndef _GLIBCXX_HAVE_TLS
function<void()> __once_call = std::move(__once_functor);
- __once_functor_lock.unlock();
+ __get_once_functor_lock().unlock();
#endif
__once_call();
}
diff --git a/libstdc++-v3/src/pool_allocator.cc b/libstdc++-v3/src/pool_allocator.cc
index c759327..bcf9d36 100644
--- a/libstdc++-v3/src/pool_allocator.cc
+++ b/libstdc++-v3/src/pool_allocator.cc
@@ -1,6 +1,6 @@
// Allocator details.
-// Copyright (C) 2004, 2005, 2006 Free Software Foundation, Inc.
+// Copyright (C) 2004, 2005, 2006, 2009 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
@@ -37,7 +37,12 @@
namespace
{
- __gnu_cxx::__mutex palloc_init_mutex;
+ __gnu_cxx::__mutex&
+ get_palloc_mutex()
+ {
+ static __gnu_cxx::__mutex palloc_mutex;
+ return palloc_mutex;
+ }
} // anonymous namespace
_GLIBCXX_BEGIN_NAMESPACE(__gnu_cxx)
@@ -52,7 +57,7 @@ _GLIBCXX_BEGIN_NAMESPACE(__gnu_cxx)
__mutex&
__pool_alloc_base::_M_get_mutex()
- { return palloc_init_mutex; }
+ { return get_palloc_mutex(); }
// Allocate memory in large chunks in order to avoid fragmenting the
// heap too much. Assume that __n is properly aligned. We hold the