|
|
2ca4f1 |
From 2bad3cb3bf8f0cc3f45057061f9a538ecf7742b6 Mon Sep 17 00:00:00 2001
|
|
|
2ca4f1 |
From: =?UTF-8?q?Sebastian=20Dr=C3=B6ge?= <sebastian@centricular.com>
|
|
|
2ca4f1 |
Date: Thu, 14 Feb 2019 17:46:33 +0200
|
|
|
2ca4f1 |
Subject: [PATCH 1/5] Use atomic reference counting for GSource
|
|
|
2ca4f1 |
|
|
|
2ca4f1 |
If attached to a context already it would use a mutex instead but at
|
|
|
2ca4f1 |
least before that the reference counting is not thread-safe currently.
|
|
|
2ca4f1 |
---
|
|
|
2ca4f1 |
glib/gmain.c | 50 +++++++++++++++-----------------------------------
|
|
|
2ca4f1 |
1 file changed, 15 insertions(+), 35 deletions(-)
|
|
|
2ca4f1 |
|
|
|
2ca4f1 |
diff --git a/glib/gmain.c b/glib/gmain.c
|
|
|
2ca4f1 |
index 26e68823d..5b91c3117 100644
|
|
|
2ca4f1 |
--- a/glib/gmain.c
|
|
|
2ca4f1 |
+++ b/glib/gmain.c
|
|
|
2ca4f1 |
@@ -374,15 +374,6 @@ typedef struct _GSourceIter
|
|
|
2ca4f1 |
#define SOURCE_DESTROYED(source) (((source)->flags & G_HOOK_FLAG_ACTIVE) == 0)
|
|
|
2ca4f1 |
#define SOURCE_BLOCKED(source) (((source)->flags & G_SOURCE_BLOCKED) != 0)
|
|
|
2ca4f1 |
|
|
|
2ca4f1 |
-#define SOURCE_UNREF(source, context) \
|
|
|
2ca4f1 |
- G_STMT_START { \
|
|
|
2ca4f1 |
- if ((source)->ref_count > 1) \
|
|
|
2ca4f1 |
- (source)->ref_count--; \
|
|
|
2ca4f1 |
- else \
|
|
|
2ca4f1 |
- g_source_unref_internal ((source), (context), TRUE); \
|
|
|
2ca4f1 |
- } G_STMT_END
|
|
|
2ca4f1 |
-
|
|
|
2ca4f1 |
-
|
|
|
2ca4f1 |
/* Forward declarations */
|
|
|
2ca4f1 |
|
|
|
2ca4f1 |
static void g_source_unref_internal (GSource *source,
|
|
|
2ca4f1 |
@@ -977,10 +968,10 @@ g_source_iter_next (GSourceIter *iter, GSource **source)
|
|
|
2ca4f1 |
*/
|
|
|
2ca4f1 |
|
|
|
2ca4f1 |
if (iter->source && iter->may_modify)
|
|
|
2ca4f1 |
- SOURCE_UNREF (iter->source, iter->context);
|
|
|
2ca4f1 |
+ g_source_unref_internal (iter->source, iter->context, TRUE);
|
|
|
2ca4f1 |
iter->source = next_source;
|
|
|
2ca4f1 |
if (iter->source && iter->may_modify)
|
|
|
2ca4f1 |
- iter->source->ref_count++;
|
|
|
2ca4f1 |
+ g_source_ref (iter->source);
|
|
|
2ca4f1 |
|
|
|
2ca4f1 |
*source = iter->source;
|
|
|
2ca4f1 |
return *source != NULL;
|
|
|
2ca4f1 |
@@ -994,7 +985,7 @@ g_source_iter_clear (GSourceIter *iter)
|
|
|
2ca4f1 |
{
|
|
|
2ca4f1 |
if (iter->source && iter->may_modify)
|
|
|
2ca4f1 |
{
|
|
|
2ca4f1 |
- SOURCE_UNREF (iter->source, iter->context);
|
|
|
2ca4f1 |
+ g_source_unref_internal (iter->source, iter->context, TRUE);
|
|
|
2ca4f1 |
iter->source = NULL;
|
|
|
2ca4f1 |
}
|
|
|
2ca4f1 |
}
|
|
|
2ca4f1 |
@@ -1135,7 +1126,7 @@ g_source_attach_unlocked (GSource *source,
|
|
|
2ca4f1 |
|
|
|
2ca4f1 |
source->context = context;
|
|
|
2ca4f1 |
source->source_id = id;
|
|
|
2ca4f1 |
- source->ref_count++;
|
|
|
2ca4f1 |
+ g_source_ref (source);
|
|
|
2ca4f1 |
|
|
|
2ca4f1 |
g_hash_table_insert (context->sources, GUINT_TO_POINTER (id), source);
|
|
|
2ca4f1 |
|
|
|
2ca4f1 |
@@ -1675,7 +1666,7 @@ g_source_set_funcs (GSource *source,
|
|
|
2ca4f1 |
{
|
|
|
2ca4f1 |
g_return_if_fail (source != NULL);
|
|
|
2ca4f1 |
g_return_if_fail (source->context == NULL);
|
|
|
2ca4f1 |
- g_return_if_fail (source->ref_count > 0);
|
|
|
2ca4f1 |
+ g_return_if_fail (g_atomic_int_get (&source->ref_count) > 0);
|
|
|
2ca4f1 |
g_return_if_fail (funcs != NULL);
|
|
|
2ca4f1 |
|
|
|
2ca4f1 |
source->source_funcs = funcs;
|
|
|
2ca4f1 |
@@ -2050,19 +2041,9 @@ g_source_set_name_by_id (guint tag,
|
|
|
2ca4f1 |
GSource *
|
|
|
2ca4f1 |
g_source_ref (GSource *source)
|
|
|
2ca4f1 |
{
|
|
|
2ca4f1 |
- GMainContext *context;
|
|
|
2ca4f1 |
-
|
|
|
2ca4f1 |
g_return_val_if_fail (source != NULL, NULL);
|
|
|
2ca4f1 |
|
|
|
2ca4f1 |
- context = source->context;
|
|
|
2ca4f1 |
-
|
|
|
2ca4f1 |
- if (context)
|
|
|
2ca4f1 |
- LOCK_CONTEXT (context);
|
|
|
2ca4f1 |
-
|
|
|
2ca4f1 |
- source->ref_count++;
|
|
|
2ca4f1 |
-
|
|
|
2ca4f1 |
- if (context)
|
|
|
2ca4f1 |
- UNLOCK_CONTEXT (context);
|
|
|
2ca4f1 |
+ g_atomic_int_inc (&source->ref_count);
|
|
|
2ca4f1 |
|
|
|
2ca4f1 |
return source;
|
|
|
2ca4f1 |
}
|
|
|
2ca4f1 |
@@ -2078,12 +2059,11 @@ g_source_unref_internal (GSource *source,
|
|
|
2ca4f1 |
GSourceCallbackFuncs *old_cb_funcs = NULL;
|
|
|
2ca4f1 |
|
|
|
2ca4f1 |
g_return_if_fail (source != NULL);
|
|
|
2ca4f1 |
-
|
|
|
2ca4f1 |
+
|
|
|
2ca4f1 |
if (!have_lock && context)
|
|
|
2ca4f1 |
LOCK_CONTEXT (context);
|
|
|
2ca4f1 |
|
|
|
2ca4f1 |
- source->ref_count--;
|
|
|
2ca4f1 |
- if (source->ref_count == 0)
|
|
|
2ca4f1 |
+ if (g_atomic_int_dec_and_test (&source->ref_count))
|
|
|
2ca4f1 |
{
|
|
|
2ca4f1 |
TRACE (GLIB_SOURCE_BEFORE_FREE (source, context,
|
|
|
2ca4f1 |
source->source_funcs->finalize));
|
|
|
2ca4f1 |
@@ -2107,20 +2087,20 @@ g_source_unref_internal (GSource *source,
|
|
|
2ca4f1 |
{
|
|
|
2ca4f1 |
/* Temporarily increase the ref count again so that GSource methods
|
|
|
2ca4f1 |
* can be called from finalize(). */
|
|
|
2ca4f1 |
- source->ref_count++;
|
|
|
2ca4f1 |
+ g_atomic_int_inc (&source->ref_count);
|
|
|
2ca4f1 |
if (context)
|
|
|
2ca4f1 |
UNLOCK_CONTEXT (context);
|
|
|
2ca4f1 |
source->source_funcs->finalize (source);
|
|
|
2ca4f1 |
if (context)
|
|
|
2ca4f1 |
LOCK_CONTEXT (context);
|
|
|
2ca4f1 |
- source->ref_count--;
|
|
|
2ca4f1 |
+ g_atomic_int_add (&source->ref_count, -1);
|
|
|
2ca4f1 |
}
|
|
|
2ca4f1 |
|
|
|
2ca4f1 |
if (old_cb_funcs)
|
|
|
2ca4f1 |
{
|
|
|
2ca4f1 |
/* Temporarily increase the ref count again so that GSource methods
|
|
|
2ca4f1 |
* can be called from callback_funcs.unref(). */
|
|
|
2ca4f1 |
- source->ref_count++;
|
|
|
2ca4f1 |
+ g_atomic_int_inc (&source->ref_count);
|
|
|
2ca4f1 |
if (context)
|
|
|
2ca4f1 |
UNLOCK_CONTEXT (context);
|
|
|
2ca4f1 |
|
|
|
2ca4f1 |
@@ -2128,7 +2108,7 @@ g_source_unref_internal (GSource *source,
|
|
|
2ca4f1 |
|
|
|
2ca4f1 |
if (context)
|
|
|
2ca4f1 |
LOCK_CONTEXT (context);
|
|
|
2ca4f1 |
- source->ref_count--;
|
|
|
2ca4f1 |
+ g_atomic_int_add (&source->ref_count, -1);
|
|
|
2ca4f1 |
}
|
|
|
2ca4f1 |
|
|
|
2ca4f1 |
g_free (source->name);
|
|
|
2ca4f1 |
@@ -3201,7 +3181,7 @@ g_main_dispatch (GMainContext *context)
|
|
|
2ca4f1 |
}
|
|
|
2ca4f1 |
}
|
|
|
2ca4f1 |
|
|
|
2ca4f1 |
- SOURCE_UNREF (source, context);
|
|
|
2ca4f1 |
+ g_source_unref_internal (source, context, TRUE);
|
|
|
2ca4f1 |
}
|
|
|
2ca4f1 |
|
|
|
2ca4f1 |
g_ptr_array_set_size (context->pending_dispatches, 0);
|
|
|
2ca4f1 |
@@ -3440,7 +3420,7 @@ g_main_context_prepare (GMainContext *context,
|
|
|
2ca4f1 |
for (i = 0; i < context->pending_dispatches->len; i++)
|
|
|
2ca4f1 |
{
|
|
|
2ca4f1 |
if (context->pending_dispatches->pdata[i])
|
|
|
2ca4f1 |
- SOURCE_UNREF ((GSource *)context->pending_dispatches->pdata[i], context);
|
|
|
2ca4f1 |
+ g_source_unref_internal ((GSource *)context->pending_dispatches->pdata[i], context, TRUE);
|
|
|
2ca4f1 |
}
|
|
|
2ca4f1 |
g_ptr_array_set_size (context->pending_dispatches, 0);
|
|
|
2ca4f1 |
|
|
|
2ca4f1 |
@@ -3788,7 +3768,7 @@ g_main_context_check (GMainContext *context,
|
|
|
2ca4f1 |
|
|
|
2ca4f1 |
if (source->flags & G_SOURCE_READY)
|
|
|
2ca4f1 |
{
|
|
|
2ca4f1 |
- source->ref_count++;
|
|
|
2ca4f1 |
+ g_source_ref (source);
|
|
|
2ca4f1 |
g_ptr_array_add (context->pending_dispatches, source);
|
|
|
2ca4f1 |
|
|
|
2ca4f1 |
n_ready++;
|
|
|
2ca4f1 |
--
|
|
|
2ca4f1 |
2.31.1
|
|
|
2ca4f1 |
|