[glib] Relax g_thread_init() requirements



commit 0df3ca8f9bbb624b219ecdb25d3fe8aa4a51d953
Author: Alexander Larsson <alexl redhat com>
Date:   Tue Jan 12 21:16:59 2010 +0100

    Relax g_thread_init() requirements
    
    We now allow g_thread_init(NULL) to be called after other glib calls (with
    some minor limitations). This is mainly a documentation change as this
    really was already possible.
    
    We also allow g_thread_init() to be called multiple times. Only the
    first call actually initializes the threading system, further calls
    are ignored (but print a warning if the argument is not NULL).
    
    https://bugzilla.gnome.org/show_bug.cgi?id=606775

 docs/reference/glib/tmpl/threads.sgml |   55 +++++++++++---------------------
 gthread/gthread-impl.c                |    7 +++-
 2 files changed, 25 insertions(+), 37 deletions(-)
---
diff --git a/docs/reference/glib/tmpl/threads.sgml b/docs/reference/glib/tmpl/threads.sgml
index 58c62bd..baf79a1 100644
--- a/docs/reference/glib/tmpl/threads.sgml
+++ b/docs/reference/glib/tmpl/threads.sgml
@@ -33,25 +33,22 @@ primitives to portably create and manage threads (#GThread).
 </para>
 
 <para>
-You must call g_thread_init() before executing any other GLib
-functions (except g_mem_set_vtable()) in a GLib program if
-g_thread_init() will be called at all. This is a requirement even if
-no threads are in fact ever created by the process. It is enough that
-g_thread_init() is called. If other GLib functions have been called
-before that, the behaviour of the program is undefined. An exception
-is g_mem_set_vtable() which may be called before g_thread_init().
-
-Failing this requirement can lead to hangs or crashes, apparently more
-easily on Windows than on Linux, for example.
-
-Please note that if you call functions in some GLib-using library, in
-particular those above the GTK+ stack, that library might well call
-g_thread_init() itself, or call some other library that calls
-g_thread_init(). Thus, if you use some GLib-based library that is
-above the GTK+ stack, it is safest to call g_thread_init() in your
-application's main() before calling any GLib functions or functions in
-GLib-using libraries.
+The threading system is initialized with g_thread_init(), which takes
+an optional custom thread implementation or %NULL for the default implementation.
+If you want to call g_thread_init() with a non-%NULL argument this must be done
+before executing any other GLib functions (except g_mem_set_vtable()). This is a
+requirement even if no threads are in fact ever created by the process.
+</para>
+
+<para>
+Calling g_thread_init() with a %NULL argument is somewhat more relaxed. You
+may call any other glib functions in the main thread before g_thread_init() as
+long as g_thread_init() is not called from a glib callback, or with any locks held.
+However, many libraries above glib does not support late initialization of
+threads, so doing this should be avoided if possible.
+</para>
 
+<para>
 After calling g_thread_init(), GLib is completely
 thread safe (all global data is automatically locked), but individual
 data structure instances are not automatically locked for performance
@@ -198,24 +195,10 @@ may report unreliable times.
 </para></note>
 
 <para>
-g_thread_init() might only be called once. On the second call
-it will abort with an error. If you want to make sure that the thread
-system is initialized, you can do this:
-</para>
-
-<para>
-<informalexample>
-<programlisting>
-if (!g_thread_supported (<!-- -->)) g_thread_init (NULL);
-</programlisting>
-</informalexample>
-</para>
-
-<para>
-After that line, either the thread system is initialized or, if no
-thread system is available in GLib (i.e. either #G_THREADS_ENABLED is
-not defined or #G_THREADS_IMPL_NONE is defined), the program will
-abort.
+Calling g_thread_init() multiple times is allowed (since version
+2.24), but nothing happens except for the first call. If the argument
+is non-%NULL on such a call a warning will be printed, but otherwise
+the argument is ignored.
 </para>
 
 <para>
diff --git a/gthread/gthread-impl.c b/gthread/gthread-impl.c
index 24eb3c4..f0f2be0 100644
--- a/gthread/gthread-impl.c
+++ b/gthread/gthread-impl.c
@@ -294,7 +294,12 @@ g_thread_init (GThreadFunctions* init)
   gboolean supported;
 
   if (thread_system_already_initialized)
-    g_error ("GThread system may only be initialized once.");
+    {
+      if (init != NULL)
+	g_warning ("GThread system already initialized, ignoring custom thread implementation.");
+
+      return;
+    }
 
   thread_system_already_initialized = TRUE;
 



[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]