Add mutex protection when gsource_destroy 17/268717/1
authorJoonbum Ko <joonbum.ko@samsung.com>
Thu, 30 Dec 2021 04:56:12 +0000 (13:56 +0900)
committerJoonbum Ko <joonbum.ko@samsung.com>
Thu, 30 Dec 2021 07:32:01 +0000 (16:32 +0900)
Change-Id: I50e841fa3895e6f145249396574e6a8267f1e663
Signed-off-by: Joonbum Ko <joonbum.ko@samsung.com>
src/tpl_utils_gthread.c

index 41c5101..51a6dc7 100644 (file)
@@ -161,6 +161,7 @@ _thread_source_dispatch(GSource *source, GSourceFunc cb, gpointer data)
        tpl_gsource *gsource = (tpl_gsource *)source;
        gboolean ret         = G_SOURCE_CONTINUE;
        GIOCondition cond    = g_source_query_unix_fd(source, gsource->tag);
+       tpl_gthread *thread  = gsource->thread;
 
        TPL_IGNORE(cb);
 
@@ -183,7 +184,6 @@ _thread_source_dispatch(GSource *source, GSourceFunc cb, gpointer data)
                        gsource->intended_destroy == TPL_TRUE) {
                        tpl_gsource *del_source = (tpl_gsource *)gsource->data;
                        if (!g_source_is_destroyed(&del_source->gsource)) {
-                               tpl_gthread *thread = del_source->thread;
                                g_mutex_lock(&thread->thread_mutex);
 
                                __gsource_remove_and_destroy(del_source);
@@ -203,8 +203,10 @@ _thread_source_dispatch(GSource *source, GSourceFunc cb, gpointer data)
 
        if (gsource->type == SOURCE_TYPE_DISPOSABLE ||
                gsource->type == SOURCE_TYPE_FINALIZER) {
+               g_mutex_lock(&thread->thread_mutex);
                __gsource_remove_and_destroy(gsource);
                ret = G_SOURCE_REMOVE;
+               g_mutex_unlock(&thread->thread_mutex);
        }
 
        return ret;
@@ -290,6 +292,9 @@ tpl_gsource_create(tpl_gthread *thread, void *data, int fd,
 static void
 __gsource_remove_and_destroy(tpl_gsource *source)
 {
+       if (g_source_is_destroyed(&source->gsource))
+               return;
+
        TPL_DEBUG("[GSOURCE_DESTROY] tpl_gsource(%p) type(%d)",
                          source, source->type);
 
@@ -301,25 +306,24 @@ __gsource_remove_and_destroy(tpl_gsource *source)
 void
 tpl_gsource_destroy(tpl_gsource *source, tpl_bool_t destroy_in_thread)
 {
+       tpl_gthread *thread = source->thread;
+
        if (g_source_is_destroyed(&source->gsource)) {
                TPL_WARN("gsource(%p) already has been destroyed.",
                                 source);
                return;
        }
 
+       g_mutex_lock(&thread->thread_mutex);
        if (source->type == SOURCE_TYPE_NORMAL &&
                source->finalizer) {
                tpl_gsource *finalizer = source->finalizer;
 
                if (destroy_in_thread) {
-                       tpl_gthread *thread = source->thread;
-                       g_mutex_lock(&thread->thread_mutex);
-
                        finalizer->intended_destroy = TPL_TRUE;
                        tpl_gsource_send_message(finalizer, 1);
 
                        g_cond_wait(&thread->thread_cond, &thread->thread_mutex);
-                       g_mutex_unlock(&thread->thread_mutex);
                } else {
                        __gsource_remove_and_destroy(finalizer);
                        source->finalizer = NULL;
@@ -329,6 +333,7 @@ tpl_gsource_destroy(tpl_gsource *source, tpl_bool_t destroy_in_thread)
        if (!destroy_in_thread) {
                __gsource_remove_and_destroy(source);
        }
+       g_mutex_unlock(&thread->thread_mutex);
 }
 
 void