re PR libstdc++/29426 (static __recursive_mutex init vs __GTHREAD_RECURSIVE_MUTEX_I...
authorBenjamin Kosnik <bkoz@redhat.com>
Wed, 11 Oct 2006 20:18:36 +0000 (20:18 +0000)
committerBenjamin Kosnik <bkoz@gcc.gnu.org>
Wed, 11 Oct 2006 20:18:36 +0000 (20:18 +0000)
2006-10-11  Benjamin Kosnik  <bkoz@redhat.com>

PR libstdc++/29426
* libsupc++/guard.cc (get_static_mutex): New.
(mutex_wrapper::mutex_wrapper): Use it to get properly initialized
recursive mutex without ordering issues.

* src/locale_init.cc (__get_locale_mutex): No need to
uglify. Change to get_locale_mutex.

From-SVN: r117643

libstdc++-v3/ChangeLog
libstdc++-v3/libsupc++/guard.cc
libstdc++-v3/src/locale_init.cc

index 35d54f21146a5df521eba0f72a560110be899355..edb15979bb27edf86707ca31d887125f1d351ed6 100644 (file)
@@ -1,3 +1,13 @@
+2006-10-11  Benjamin Kosnik  <bkoz@redhat.com>
+
+       PR libstdc++/29426
+       * libsupc++/guard.cc (get_static_mutex): New. 
+       (mutex_wrapper::mutex_wrapper): Use it to get properly initialized
+       recursive mutex without ordering issues.
+
+       * src/locale_init.cc (__get_locale_mutex): No need to
+       uglify. Change to get_locale_mutex.
+       
 2006-10-11  Paolo Carlini  <pcarlini@suse.de>
 
        * testsuite/22_locale/num_put/put/char/11.cc: New.
index a56fe15e7eea3fa408ef739e608bace6d36d2688..eb6421689b3ab9076e6b651033ba08dddc9fbc4a 100644 (file)
@@ -32,6 +32,7 @@
 #include <bits/c++config.h>
 #include <cxxabi.h>
 #include <exception>
+#include <new>
 #include <ext/atomicity.h>
 #include <ext/concurrence.h>
 
 namespace
 {
   // A single mutex controlling all static initializations.
-  __gnu_cxx::__recursive_mutex static_mutex;
+  static __gnu_cxx::__recursive_mutex* static_mutex;  
+
+  typedef char fake_recursive_mutex[sizeof(__gnu_cxx::__recursive_mutex)]
+  __attribute__ ((aligned(__alignof__(__gnu_cxx::__recursive_mutex))));
+  fake_recursive_mutex fake_mutex;
+
+  static void init()
+  { static_mutex =  new (&fake_mutex) __gnu_cxx::__recursive_mutex(); }
+
+  __gnu_cxx::__recursive_mutex&
+  get_static_mutex()
+  {
+    static __gthread_once_t once = __GTHREAD_ONCE_INIT;
+    __gthread_once(&once, init);
+    return *static_mutex;
+  }
 }
 
 #ifndef _GLIBCXX_GUARD_TEST_AND_ACQUIRE
@@ -98,18 +114,14 @@ namespace __cxxabiv1
 {
   static inline int
   recursion_push (__guard* g)
-  {
-    return ((char *)g)[1]++;
-  }
+  { return ((char *)g)[1]++; }
 
   static inline void
   recursion_pop (__guard* g)
-  {
-    --((char *)g)[1];
-  }
+  { --((char *)g)[1]; }
 
   static int
-  acquire_1 (__guard *g)
+  acquire (__guard *g)
   {
     if (_GLIBCXX_GUARD_TEST (g))
       return 0;
@@ -142,18 +154,18 @@ namespace __cxxabiv1
        struct mutex_wrapper
        {
          bool unlock;
-         mutex_wrapper (): unlock(true)
-         {
-           static_mutex.lock();
-         }
-         ~mutex_wrapper ()
+         mutex_wrapper() : unlock(true)
+         { get_static_mutex().lock(); }
+
+         ~mutex_wrapper()
          {
            if (unlock)
-             static_mutex.unlock();
+             static_mutex->unlock();
          }
-       } mw;
+       };
 
-       if (acquire_1 (g))
+       mutex_wrapper mw;
+       if (acquire (g))
          {
            mw.unlock = false;
            return 1;
@@ -163,7 +175,7 @@ namespace __cxxabiv1
       }
 #endif
 
-    return acquire_1 (g);
+    return acquire (g);
   }
 
   extern "C"
@@ -172,7 +184,7 @@ namespace __cxxabiv1
     recursion_pop (g);
 #ifdef __GTHREADS
     if (__gthread_active_p ())
-      static_mutex.unlock();
+      static_mutex->unlock();
 #endif
   }
 
@@ -183,7 +195,7 @@ namespace __cxxabiv1
     _GLIBCXX_GUARD_SET_AND_RELEASE (g);
 #ifdef __GTHREADS
     if (__gthread_active_p ())
-      static_mutex.unlock();
+      static_mutex->unlock();
 #endif
   }
 }
index a2c18dd84cb0212c3156463e359ebc908459cd50..28ee484112f80d1a4c2f3e47ed67657f101f755c 100644 (file)
@@ -37,7 +37,7 @@
 namespace 
 {
   __gnu_cxx::__mutex&
-  __get_locale_mutex()
+  get_locale_mutex()
   {
     static __gnu_cxx::__mutex locale_mutex;
     return locale_mutex;
@@ -212,7 +212,7 @@ _GLIBCXX_BEGIN_NAMESPACE(std)
   locale::locale() throw() : _M_impl(0)
   { 
     _S_initialize();
-    __gnu_cxx::__scoped_lock sentry(__get_locale_mutex());
+    __gnu_cxx::__scoped_lock sentry(get_locale_mutex());
     _S_global->_M_add_reference();
     _M_impl = _S_global;
   }
@@ -223,7 +223,7 @@ _GLIBCXX_BEGIN_NAMESPACE(std)
     _S_initialize();
     _Impl* __old;
     {
-      __gnu_cxx::__scoped_lock sentry(__get_locale_mutex());
+      __gnu_cxx::__scoped_lock sentry(get_locale_mutex());
       __old = _S_global;
       __other._M_impl->_M_add_reference();
       _S_global = __other._M_impl;