From 507f8c8a73e2f373c2b50db6490688689fc88517 Mon Sep 17 00:00:00 2001 From: Nirbheek Chauhan Date: Tue, 15 Jul 2014 23:20:51 +0530 Subject: server: Make cleanup on server exit and EOS more reliable --- src/lib.c | 22 +++++++++++++++++++--- src/lib.h | 1 + src/main.c | 10 ++++------ 3 files changed, 24 insertions(+), 9 deletions(-) diff --git a/src/lib.c b/src/lib.c index bd5a8d6..062a8be 100644 --- a/src/lib.c +++ b/src/lib.c @@ -24,6 +24,13 @@ static void stp_disconnect_cleanup_client (TranscodeClientCtx *ctx); +static gboolean +invoke_g_hash_table_remove (TranscodeServerCtx *ctx) +{ + g_hash_table_remove (ctx->parent_ctx_table, ctx->path); + return FALSE; +} + gboolean stp_on_gst_bus_message (GstBus *bus, GstMessage *msg, @@ -44,12 +51,19 @@ stp_on_gst_bus_message (GstBus *bus, * hasn't already finished, so we check that */ if (!ctx->stream_finished) soup_message_set_status (ctx->msg, SOUP_STATUS_INTERNAL_SERVER_ERROR); - /* FIXME: hash tables are not threadsafe */ - g_hash_table_remove (ctx->parent_ctx_table, ctx->path); + /* Cleanup in the default main context, + * because GHashTable is not thread-safe */ + g_main_context_invoke_full (NULL, G_PRIORITY_HIGH, + (GSourceFunc)invoke_g_hash_table_remove, + ctx, NULL); break; case GST_MESSAGE_EOS: g_debug ("End of file"); - g_hash_table_remove (ctx->parent_ctx_table, ctx->path); + /* Cleanup in the default main context, + * because GHashTable is not thread-safe */ + g_main_context_invoke_full (NULL, G_PRIORITY_HIGH, + (GSourceFunc)invoke_g_hash_table_remove, + ctx, NULL); break; default: //stp_print_status ("%s\n", gst_message_type_get_name (msg->type)); @@ -146,6 +160,8 @@ stp_disconnect_cleanup_client (TranscodeClientCtx *ctx) soup_message_body_complete (ctx->msg->response_body); g_source_remove (ctx->timeout_handler_id); + /* Don't call the "finished" handler and do a double-free */ + g_signal_handler_disconnect (ctx->msg, ctx->finished_handler_id); g_free (ctx); } diff --git a/src/lib.h b/src/lib.h index 6894c0b..ea6b5f0 100644 --- a/src/lib.h +++ b/src/lib.h @@ -59,6 +59,7 @@ struct _TranscodeClientCtx { gboolean keyframe_found; guint timeout_handler_id; + gulong finished_handler_id; guint seconds_since_write; /* The transcode server context; we don't hold a ref to this */ TranscodeServerCtx *server_ctx; diff --git a/src/main.c b/src/main.c index 44b3201..3b9c243 100644 --- a/src/main.c +++ b/src/main.c @@ -178,10 +178,7 @@ client_finished_cb (SoupMessage *msg, TranscodeClientCtx *ctx) { stp_print_status ("Client finished/aborted, doing cleanup...\n"); - /* Make sure not to double-free. If the server - * has shut down, this will be 0. */ - if (ctx->timeout_handler_id) - stp_cleanup_transcode_client_ctx (ctx); + stp_cleanup_transcode_client_ctx (ctx); } static void @@ -344,8 +341,9 @@ nostreamheader: G_CALLBACK (client_eos_cb), client_ctx); g_signal_connect (client_ctx->msg, "wrote-chunk", G_CALLBACK (can_write_next_client_chunk_cb), client_ctx); - g_signal_connect (client_ctx->msg, "finished", - G_CALLBACK (client_finished_cb), client_ctx); + client_ctx->finished_handler_id = + g_signal_connect (client_ctx->msg, "finished", + G_CALLBACK (client_finished_cb), client_ctx); client_ctx->timeout_handler_id = \ g_timeout_add_seconds (2, (GSourceFunc)increment_write_timer, client_ctx); -- cgit v0.11.2-2-gd1dd