[glib: 2/4] gdbusobjectmanagerclient: Call GetManagedObjects async
- From: Philip Withnall <pwithnall src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [glib: 2/4] gdbusobjectmanagerclient: Call GetManagedObjects async
- Date: Mon, 28 Jun 2021 16:43:15 +0000 (UTC)
commit c548ac0796cbc208751d0eb6761626f0091faf26
Author: Guido Günther <agx sigxcpu org>
Date: Wed May 26 21:14:39 2021 +0200
gdbusobjectmanagerclient: Call GetManagedObjects async
This helps to void deadlocks when two processes call interfaces on each
other one of them being org.freedesktop.DBus.ObjectManager.
Signed-off-by: Guido Günther <agx sigxcpu org>
gio/gdbusobjectmanagerclient.c | 95 ++++++++++++++++++++++++++----------------
1 file changed, 60 insertions(+), 35 deletions(-)
---
diff --git a/gio/gdbusobjectmanagerclient.c b/gio/gdbusobjectmanagerclient.c
index 80b716bc7..bc3fd3d5f 100644
--- a/gio/gdbusobjectmanagerclient.c
+++ b/gio/gdbusobjectmanagerclient.c
@@ -1259,6 +1259,57 @@ weak_ref_free (GWeakRef *weak_ref)
g_free (weak_ref);
}
+static void
+on_get_managed_objects_finish (GObject *source,
+ GAsyncResult *result,
+ gpointer user_data)
+{
+
+ GDBusProxy *proxy = G_DBUS_PROXY (source);
+ GWeakRef *manager_weak = user_data;
+ GDBusObjectManagerClient *manager;
+ GError *error = NULL;
+ GVariant *value = NULL;
+ gchar *new_name_owner = NULL;
+
+ value = g_dbus_proxy_call_finish (proxy, result, &error);
+
+ manager = G_DBUS_OBJECT_MANAGER_CLIENT (g_weak_ref_get (manager_weak));
+ /* Manager got disposed, nothing to do */
+ if (manager == NULL)
+ {
+ goto out;
+ }
+
+ new_name_owner = g_dbus_proxy_get_name_owner (manager->priv->control_proxy);
+ if (value == NULL)
+ {
+ maybe_unsubscribe_signals (manager);
+ g_warning ("Error calling GetManagedObjects() when name owner %s for name %s came back: %s",
+ new_name_owner,
+ manager->priv->name,
+ error->message);
+ }
+ else
+ {
+ process_get_all_result (manager, value, new_name_owner);
+ }
+
+ /* do the :name-owner notify *AFTER* emitting ::object-proxy-added signals - this
+ * way the user knows that the signals were emitted because the name owner came back
+ */
+ g_mutex_lock (&manager->priv->lock);
+ manager->priv->name_owner = g_steal_pointer (&new_name_owner);
+ g_mutex_unlock (&manager->priv->lock);
+ g_object_notify (G_OBJECT (manager), "name-owner");
+
+ g_object_unref (manager);
+ out:
+ g_clear_error (&error);
+ g_clear_pointer (&value, g_variant_unref);
+ weak_ref_free (manager_weak);
+}
+
static void
on_notify_g_name_owner (GObject *object,
GParamSpec *pspec,
@@ -1313,46 +1364,20 @@ on_notify_g_name_owner (GObject *object,
if (new_name_owner != NULL)
{
- GError *error;
- GVariant *value;
-
//g_debug ("repopulating for %s", new_name_owner);
- /* TODO: do this async! */
subscribe_signals (manager,
new_name_owner);
- error = NULL;
- value = g_dbus_proxy_call_sync (manager->priv->control_proxy,
- "GetManagedObjects",
- NULL, /* parameters */
- G_DBUS_CALL_FLAGS_NONE,
- -1,
- NULL,
- &error);
- if (value == NULL)
- {
- maybe_unsubscribe_signals (manager);
- g_warning ("Error calling GetManagedObjects() when name owner %s for name %s came back: %s",
- new_name_owner,
- manager->priv->name,
- error->message);
- g_error_free (error);
- }
- else
- {
- process_get_all_result (manager, value, new_name_owner);
- g_variant_unref (value);
- }
-
- /* do the :name-owner notify *AFTER* emitting ::object-proxy-added signals - this
- * way the user knows that the signals were emitted because the name owner came back
- */
- g_mutex_lock (&manager->priv->lock);
- manager->priv->name_owner = new_name_owner;
- g_mutex_unlock (&manager->priv->lock);
- g_object_notify (G_OBJECT (manager), "name-owner");
-
+ g_dbus_proxy_call (manager->priv->control_proxy,
+ "GetManagedObjects",
+ NULL, /* parameters */
+ G_DBUS_CALL_FLAGS_NONE,
+ -1,
+ NULL,
+ on_get_managed_objects_finish,
+ weak_ref_new (G_OBJECT (manager)));
}
+ g_free (new_name_owner);
g_free (old_name_owner);
g_object_unref (manager);
}
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]