Commit 99827523 by Benjamin Kosnik

re PR libstdc++/36801 (config/cpu/generic/atomicity_mutex/atomicity.h…

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
parent f5651df1
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.
2009-01-07 Jakub Jelinek <jakub@redhat.com> 2009-01-07 Jakub Jelinek <jakub@redhat.com>
PR libstdc++/38732 PR libstdc++/38732
...@@ -53,12 +72,12 @@ ...@@ -53,12 +72,12 @@
PR libstdc++/38384 PR libstdc++/38384
* crossconfig.m4: Define HAVE_FABSF for hpux crosses. * crossconfig.m4: Define HAVE_FABSF for hpux crosses.
* configure: Regenerate. * configure: Regenerate.
2009-01-05 Ben Elliston <bje@au.ibm.com> 2009-01-05 Ben Elliston <bje@au.ibm.com>
* configure.ac (GLIBCXX_CHECK_STANDARD_LAYOUT): Remove invocation. * configure.ac (GLIBCXX_CHECK_STANDARD_LAYOUT): Remove invocation.
* configure: Regenerate. * configure: Regenerate.
2009-01-05 Ben Elliston <bje@au.ibm.com> 2009-01-05 Ben Elliston <bje@au.ibm.com>
...@@ -141,12 +160,12 @@ ...@@ -141,12 +160,12 @@
2008-12-17 Jack Howarth <howarth@bromo.med.uc.edu> 2008-12-17 Jack Howarth <howarth@bromo.med.uc.edu>
* testsuite/26_numerics/headers/cmath/c99_classification_macros_c.cc: * testsuite/26_numerics/headers/cmath/c99_classification_macros_c.cc:
Don't xfail test on darwin8 or later. Don't xfail test on darwin8 or later.
2008-12-16 Jack Howarth <howarth@bromo.med.uc.edu> 2008-12-16 Jack Howarth <howarth@bromo.med.uc.edu>
* testsuite/26_numerics/headers/cmath/c99_classification_macros_c.cc: * testsuite/26_numerics/headers/cmath/c99_classification_macros_c.cc:
Don't xfail excessive errors on darwin8 or later. Don't xfail excessive errors on darwin8 or later.
2008-12-15 Benjamin Kosnik <bkoz@redhat.com> 2008-12-15 Benjamin Kosnik <bkoz@redhat.com>
......
## Linker script for GNU versioning (GNU ld 2.13.91+ only.) ## Linker script for GNU versioning (GNU ld 2.13.91+ only.)
## ##
## Copyright (C) 2002, 2003, 2004, 2005, 2006, 2007, 2008 ## Copyright (C) 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009
## Free Software Foundation, Inc. ## Free Software Foundation, Inc.
## ##
## This file is part of the GNU ISO C++ Library. This library is free ## This file is part of the GNU ISO C++ Library. This library is free
...@@ -884,9 +884,7 @@ GLIBCXX_3.4.11 { ...@@ -884,9 +884,7 @@ GLIBCXX_3.4.11 {
_ZSt11__once_call; _ZSt11__once_call;
_ZSt15__once_callable; _ZSt15__once_callable;
_ZSt14__once_functor; _ZSt14__once_functor;
_ZSt19__once_functor_lock; _ZSt23__get_once_functor_lockv;
_ZSt11__once_lock;
_ZSt12__once_mutex;
__once_proxy; __once_proxy;
# condition_variable # condition_variable
......
// Low-level functions for atomic operations: Generic version -*- C++ -*- // Low-level functions for atomic operations: Generic version -*- C++ -*-
// Copyright (C) 1999, 2001, 2002, 2003, 2004, 2005, 2006 // Copyright (C) 1999, 2001, 2002, 2003, 2004, 2005, 2006, 2009
// Free Software Foundation, Inc. // Free Software Foundation, Inc.
// //
// This file is part of the GNU ISO C++ Library. This library is free // This file is part of the GNU ISO C++ Library. This library is free
...@@ -37,7 +37,12 @@ ...@@ -37,7 +37,12 @@
namespace namespace
{ {
__gnu_cxx::__mutex atomic_mutex; __gnu_cxx::__mutex&
get_atomic_mutex()
{
static __gnu_cxx::__mutex atomic_mutex;
return atomic_mutex;
}
} // anonymous namespace } // anonymous namespace
_GLIBCXX_BEGIN_NAMESPACE(__gnu_cxx) _GLIBCXX_BEGIN_NAMESPACE(__gnu_cxx)
...@@ -46,7 +51,7 @@ _GLIBCXX_BEGIN_NAMESPACE(__gnu_cxx) ...@@ -46,7 +51,7 @@ _GLIBCXX_BEGIN_NAMESPACE(__gnu_cxx)
__attribute__ ((__unused__)) __attribute__ ((__unused__))
__exchange_and_add(volatile _Atomic_word* __mem, int __val) __exchange_and_add(volatile _Atomic_word* __mem, int __val)
{ {
__gnu_cxx::__scoped_lock sentry(atomic_mutex); __gnu_cxx::__scoped_lock sentry(get_atomic_mutex());
_Atomic_word __result; _Atomic_word __result;
__result = *__mem; __result = *__mem;
*__mem += __val; *__mem += __val;
......
// <mutex> -*- C++ -*- // <mutex> -*- C++ -*-
// Copyright (C) 2003, 2004, 2005, 2006, 2007, 2008 // Copyright (C) 2003, 2004, 2005, 2006, 2007, 2008, 2009
// Free Software Foundation, Inc. // Free Software Foundation, Inc.
// //
// This file is part of the GNU ISO C++ Library. This library is free // This file is part of the GNU ISO C++ Library. This library is free
...@@ -709,13 +709,16 @@ namespace std ...@@ -709,13 +709,16 @@ namespace std
extern __thread void (*__once_call)(); extern __thread void (*__once_call)();
template<typename _Callable> template<typename _Callable>
void __once_call_impl() inline void
__once_call_impl()
{ {
(*(_Callable*)__once_callable)(); (*(_Callable*)__once_callable)();
} }
#else #else
extern function<void()> __once_functor; extern function<void()> __once_functor;
extern unique_lock<mutex> __once_functor_lock;
extern unique_lock<mutex>&
__get_once_functor_lock();
#endif #endif
extern "C" void __once_proxy(); extern "C" void __once_proxy();
...@@ -729,15 +732,16 @@ namespace std ...@@ -729,15 +732,16 @@ namespace std
__once_callable = &__bound_functor; __once_callable = &__bound_functor;
__once_call = &__once_call_impl<decltype(__bound_functor)>; __once_call = &__once_call_impl<decltype(__bound_functor)>;
#else #else
__once_functor_lock.lock(); unique_lock<mutex>& __functor_lock = __get_once_functor_lock();
__functor_lock.lock();
__once_functor = bind(__f, __args...); __once_functor = bind(__f, __args...);
#endif #endif
int __e = __gthread_once(&(__once._M_once), &__once_proxy); int __e = __gthread_once(&(__once._M_once), &__once_proxy);
#ifndef _GLIBCXX_HAVE_TLS #ifndef _GLIBCXX_HAVE_TLS
if (__once_functor_lock) if (__functor_lock)
__once_functor_lock.unlock(); __functor_lock.unlock();
#endif #endif
if (__e) if (__e)
......
// Support for atomic operations -*- C++ -*- // Support for atomic operations -*- C++ -*-
// Copyright (C) 2008 // Copyright (C) 2008, 2009
// Free Software Foundation, Inc. // Free Software Foundation, Inc.
// //
// This file is part of the GNU ISO C++ Library. This library is free // This file is part of the GNU ISO C++ Library. This library is free
...@@ -37,7 +37,12 @@ ...@@ -37,7 +37,12 @@
namespace namespace
{ {
#if defined(_GLIBCXX_HAS_GTHREADS) && defined(_GLIBCXX_USE_C99_STDINT_TR1) #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 #endif
std::__atomic_flag_base volatile flag_table[ 1 << LOGSIZE ] = std::__atomic_flag_base volatile flag_table[ 1 << LOGSIZE ] =
...@@ -57,7 +62,7 @@ namespace std ...@@ -57,7 +62,7 @@ namespace std
atomic_flag::test_and_set(memory_order) volatile atomic_flag::test_and_set(memory_order) volatile
{ {
#if defined(_GLIBCXX_HAS_GTHREADS) && defined(_GLIBCXX_USE_C99_STDINT_TR1) #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 #endif
bool result = _M_i; bool result = _M_i;
_M_i = true; _M_i = true;
...@@ -68,7 +73,7 @@ namespace std ...@@ -68,7 +73,7 @@ namespace std
atomic_flag::clear(memory_order) volatile atomic_flag::clear(memory_order) volatile
{ {
#if defined(_GLIBCXX_HAS_GTHREADS) && defined(_GLIBCXX_USE_C99_STDINT_TR1) #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 #endif
_M_i = false; _M_i = false;
} }
......
// Debugging mode support code -*- C++ -*- // Debugging mode support code -*- C++ -*-
// Copyright (C) 2003, 2004, 2005, 2006, 2007 // Copyright (C) 2003, 2004, 2005, 2006, 2007, 2009
// Free Software Foundation, Inc. // Free Software Foundation, Inc.
// //
// This file is part of the GNU ISO C++ Library. This library is free // This file is part of the GNU ISO C++ Library. This library is free
...@@ -42,7 +42,12 @@ using namespace std; ...@@ -42,7 +42,12 @@ using namespace std;
namespace 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 } // anonymous namespace
namespace __gnu_debug namespace __gnu_debug
...@@ -112,7 +117,7 @@ namespace __gnu_debug ...@@ -112,7 +117,7 @@ namespace __gnu_debug
_Safe_sequence_base:: _Safe_sequence_base::
_M_detach_all() _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;) for (_Safe_iterator_base* __iter = _M_iterators; __iter;)
{ {
_Safe_iterator_base* __old = __iter; _Safe_iterator_base* __old = __iter;
...@@ -132,7 +137,7 @@ namespace __gnu_debug ...@@ -132,7 +137,7 @@ namespace __gnu_debug
_Safe_sequence_base:: _Safe_sequence_base::
_M_detach_singular() _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;) for (_Safe_iterator_base* __iter = _M_iterators; __iter;)
{ {
_Safe_iterator_base* __old = __iter; _Safe_iterator_base* __old = __iter;
...@@ -154,7 +159,7 @@ namespace __gnu_debug ...@@ -154,7 +159,7 @@ namespace __gnu_debug
_Safe_sequence_base:: _Safe_sequence_base::
_M_revalidate_singular() _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; for (_Safe_iterator_base* __iter = _M_iterators; __iter;
__iter = __iter->_M_next) __iter = __iter->_M_next)
__iter->_M_version = _M_version; __iter->_M_version = _M_version;
...@@ -168,7 +173,7 @@ namespace __gnu_debug ...@@ -168,7 +173,7 @@ namespace __gnu_debug
_Safe_sequence_base:: _Safe_sequence_base::
_M_swap(_Safe_sequence_base& __x) _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_iterators, __x._M_iterators);
swap(_M_const_iterators, __x._M_const_iterators); swap(_M_const_iterators, __x._M_const_iterators);
swap(_M_version, __x._M_version); swap(_M_version, __x._M_version);
...@@ -186,13 +191,13 @@ namespace __gnu_debug ...@@ -186,13 +191,13 @@ namespace __gnu_debug
__gnu_cxx::__mutex& __gnu_cxx::__mutex&
_Safe_sequence_base:: _Safe_sequence_base::
_M_get_mutex() _M_get_mutex()
{ return safe_base_mutex; } { return get_safe_base_mutex(); }
void void
_Safe_iterator_base:: _Safe_iterator_base::
_M_attach(_Safe_sequence_base* __seq, bool __constant) _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); _M_attach_single(__seq, __constant);
} }
...@@ -229,7 +234,7 @@ namespace __gnu_debug ...@@ -229,7 +234,7 @@ namespace __gnu_debug
_Safe_iterator_base:: _Safe_iterator_base::
_M_detach() _M_detach()
{ {
__gnu_cxx::__scoped_lock sentry(safe_base_mutex); __gnu_cxx::__scoped_lock sentry(_M_get_mutex());
_M_detach_single(); _M_detach_single();
} }
...@@ -273,7 +278,7 @@ namespace __gnu_debug ...@@ -273,7 +278,7 @@ namespace __gnu_debug
__gnu_cxx::__mutex& __gnu_cxx::__mutex&
_Safe_iterator_base:: _Safe_iterator_base::
_M_get_mutex() _M_get_mutex()
{ return safe_base_mutex; } { return get_safe_base_mutex(); }
void void
_Error_formatter::_Parameter:: _Error_formatter::_Parameter::
......
// 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. // Free Software Foundation, Inc.
// //
// This file is part of the GNU ISO C++ Library. This library is free // This file is part of the GNU ISO C++ Library. This library is free
...@@ -36,7 +37,12 @@ ...@@ -36,7 +37,12 @@
namespace 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 } // anonymous namespace
// XXX GLIBCXX_ABI Deprecated // XXX GLIBCXX_ABI Deprecated
...@@ -389,7 +395,7 @@ _GLIBCXX_BEGIN_NAMESPACE(std) ...@@ -389,7 +395,7 @@ _GLIBCXX_BEGIN_NAMESPACE(std)
locale::_Impl:: locale::_Impl::
_M_install_cache(const facet* __cache, size_t __index) _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) if (_M_caches[__index] != 0)
{ {
// Some other thread got in first. // Some other thread got in first.
......
// Allocator details. // 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 // 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 // software; you can redistribute it and/or modify it under the
...@@ -57,21 +57,34 @@ namespace ...@@ -57,21 +57,34 @@ namespace
} }
}; };
// Ensure freelist is constructed first. __freelist&
static __freelist freelist; get_freelist()
__gnu_cxx::__mutex freelist_mutex; {
static __freelist freelist;
return freelist;
}
__gnu_cxx::__mutex&
get_freelist_mutex()
{
static __gnu_cxx::__mutex freelist_mutex;
return freelist_mutex;
}
static void static void
_M_destroy_thread_key(void* __id) _M_destroy_thread_key(void* __id)
{ {
// Return this thread id record to the front of thread_freelist. // Return this thread id record to the front of thread_freelist.
__gnu_cxx::__scoped_lock sentry(freelist_mutex); __freelist& freelist = get_freelist();
size_t _M_id = reinterpret_cast<size_t>(__id); {
__gnu_cxx::__scoped_lock sentry(get_freelist_mutex());
typedef __gnu_cxx::__pool<true>::_Thread_record _Thread_record; size_t _M_id = reinterpret_cast<size_t>(__id);
_Thread_record* __tr = &freelist._M_thread_freelist_array[_M_id - 1];
__tr->_M_next = freelist._M_thread_freelist; typedef __gnu_cxx::__pool<true>::_Thread_record _Thread_record;
freelist._M_thread_freelist = __tr; _Thread_record* __tr = &freelist._M_thread_freelist_array[_M_id - 1];
__tr->_M_next = freelist._M_thread_freelist;
freelist._M_thread_freelist = __tr;
}
} }
#endif #endif
} // anonymous namespace } // anonymous namespace
...@@ -496,8 +509,9 @@ _GLIBCXX_BEGIN_NAMESPACE(__gnu_cxx) ...@@ -496,8 +509,9 @@ _GLIBCXX_BEGIN_NAMESPACE(__gnu_cxx)
// directly and have no need for this. // directly and have no need for this.
if (__gthread_active_p()) 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 if (!freelist._M_thread_freelist_array
|| freelist._M_max_threads < _M_options._M_max_threads) || freelist._M_max_threads < _M_options._M_max_threads)
...@@ -613,12 +627,13 @@ _GLIBCXX_BEGIN_NAMESPACE(__gnu_cxx) ...@@ -613,12 +627,13 @@ _GLIBCXX_BEGIN_NAMESPACE(__gnu_cxx)
// returns its id. // returns its id.
if (__gthread_active_p()) if (__gthread_active_p())
{ {
__freelist& freelist = get_freelist();
void* v = __gthread_getspecific(freelist._M_key); void* v = __gthread_getspecific(freelist._M_key);
size_t _M_id = (size_t)v; size_t _M_id = (size_t)v;
if (_M_id == 0) if (_M_id == 0)
{ {
{ {
__gnu_cxx::__scoped_lock sentry(freelist_mutex); __gnu_cxx::__scoped_lock sentry(get_freelist_mutex());
if (freelist._M_thread_freelist) if (freelist._M_thread_freelist)
{ {
_M_id = freelist._M_thread_freelist->_M_id; _M_id = freelist._M_thread_freelist->_M_id;
...@@ -689,8 +704,9 @@ _GLIBCXX_BEGIN_NAMESPACE(__gnu_cxx) ...@@ -689,8 +704,9 @@ _GLIBCXX_BEGIN_NAMESPACE(__gnu_cxx)
// directly and have no need for this. // directly and have no need for this.
if (__gthread_active_p()) 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 if (!freelist._M_thread_freelist_array
|| freelist._M_max_threads < _M_options._M_max_threads) || freelist._M_max_threads < _M_options._M_max_threads)
......
// mutex -*- C++ -*- // 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 // 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 // software; you can redistribute it and/or modify it under the
...@@ -30,6 +30,17 @@ ...@@ -30,6 +30,17 @@
#include <mutex> #include <mutex>
#if defined(_GLIBCXX_HAS_GTHREADS) && defined(_GLIBCXX_USE_C99_STDINT_TR1) #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 namespace std
{ {
...@@ -45,11 +56,16 @@ namespace std ...@@ -45,11 +56,16 @@ namespace std
__thread void* __once_callable; __thread void* __once_callable;
__thread void (*__once_call)(); __thread void (*__once_call)();
#else #else
// explicit instantiation due to -fno-implicit-instantiation // Explicit instantiation due to -fno-implicit-instantiation.
template class function<void()>; template class function<void()>;
function<void()> __once_functor; 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 #endif
extern "C" extern "C"
...@@ -58,7 +74,7 @@ namespace std ...@@ -58,7 +74,7 @@ namespace std
{ {
#ifndef _GLIBCXX_HAVE_TLS #ifndef _GLIBCXX_HAVE_TLS
function<void()> __once_call = std::move(__once_functor); function<void()> __once_call = std::move(__once_functor);
__once_functor_lock.unlock(); __get_once_functor_lock().unlock();
#endif #endif
__once_call(); __once_call();
} }
......
// Allocator details. // 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 // 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 // software; you can redistribute it and/or modify it under the
...@@ -37,7 +37,12 @@ ...@@ -37,7 +37,12 @@
namespace namespace
{ {
__gnu_cxx::__mutex palloc_init_mutex; __gnu_cxx::__mutex&
get_palloc_mutex()
{
static __gnu_cxx::__mutex palloc_mutex;
return palloc_mutex;
}
} // anonymous namespace } // anonymous namespace
_GLIBCXX_BEGIN_NAMESPACE(__gnu_cxx) _GLIBCXX_BEGIN_NAMESPACE(__gnu_cxx)
...@@ -52,7 +57,7 @@ _GLIBCXX_BEGIN_NAMESPACE(__gnu_cxx) ...@@ -52,7 +57,7 @@ _GLIBCXX_BEGIN_NAMESPACE(__gnu_cxx)
__mutex& __mutex&
__pool_alloc_base::_M_get_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 // Allocate memory in large chunks in order to avoid fragmenting the
// heap too much. Assume that __n is properly aligned. We hold the // heap too much. Assume that __n is properly aligned. We hold the
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment