[gnome-software: 8/14] gs-application: Use asynchronous setup for the plugin loader
- From: Philip Withnall <pwithnall src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gnome-software: 8/14] gs-application: Use asynchronous setup for the plugin loader
- Date: Wed, 2 Mar 2022 11:47:37 +0000 (UTC)
commit 5c6f856da9c55dddc732f365dbac43c05231c9d6
Author: Philip Withnall <pwithnall endlessos org>
Date: Tue Mar 1 14:35:12 2022 +0000
gs-application: Use asynchronous setup for the plugin loader
This ensures that file monitors and other long-lived objects which
reference the thread-default `GMainContext` at their time of
construction, end up referencing the *correct* thread-default
`GMainContext`.
See the previous commit message for more details.
Signed-off-by: Philip Withnall <pwithnall endlessos org>
Fixes: #1661
src/gs-application.c | 41 ++++++++++++++++++++++++++++++++++++-----
1 file changed, 36 insertions(+), 5 deletions(-)
---
diff --git a/src/gs-application.c b/src/gs-application.c
index 04f100362..477cce9b9 100644
--- a/src/gs-application.c
+++ b/src/gs-application.c
@@ -159,6 +159,19 @@ gs_application_init (GsApplication *application)
g_application_add_main_option_entries (G_APPLICATION (application), options);
}
+static void
+async_result_cb (GObject *source_object,
+ GAsyncResult *result,
+ gpointer user_data)
+{
+ GAsyncResult **result_out = user_data;
+
+ g_assert (*result_out == NULL);
+ *result_out = g_object_ref (result);
+
+ g_main_context_wakeup (g_main_context_get_thread_default ());
+}
+
static void
gs_application_initialize_plugins (GsApplication *app)
{
@@ -167,6 +180,7 @@ gs_application_initialize_plugins (GsApplication *app)
g_auto(GStrv) plugin_allowlist = NULL;
g_autoptr(GError) error = NULL;
const gchar *tmp;
+ g_autoptr(GAsyncResult) setup_result = NULL;
if (initialized)
return;
@@ -184,11 +198,28 @@ gs_application_initialize_plugins (GsApplication *app)
app->plugin_loader = gs_plugin_loader_new ();
if (g_file_test (LOCALPLUGINDIR, G_FILE_TEST_EXISTS))
gs_plugin_loader_add_location (app->plugin_loader, LOCALPLUGINDIR);
- if (!gs_plugin_loader_setup (app->plugin_loader,
- plugin_allowlist,
- plugin_blocklist,
- NULL,
- &error)) {
+
+ /* Set up the plugins. Manually iterate the thread-default #GMainContext
+ * at this point to save refactoring all this code to be async (FIXME:
+ * we should do that in future).
+ *
+ * We can’t use gs_plugin_loader_setup() from gs-plugin-loader-sync.c
+ * here because that uses a custom #GMainContext, which means that a lot
+ * of objects in plugins are initialised with the wrong #GMainContext
+ * for subsequent callbacks. */
+ gs_plugin_loader_setup_async (app->plugin_loader,
+ (const gchar * const *) plugin_allowlist,
+ (const gchar * const *) plugin_blocklist,
+ NULL,
+ async_result_cb,
+ &setup_result);
+
+ while (setup_result == NULL)
+ g_main_context_iteration (g_main_context_get_thread_default (), TRUE);
+
+ if (!gs_plugin_loader_setup_finish (app->plugin_loader,
+ setup_result,
+ &error)) {
g_warning ("Failed to setup plugins: %s", error->message);
exit (1);
}
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]