aboutsummaryrefslogtreecommitdiffstats
path: root/libempathy
diff options
context:
space:
mode:
authorXavier Claessens <xclaesse@src.gnome.org>2008-04-11 21:11:38 +0800
committerXavier Claessens <xclaesse@src.gnome.org>2008-04-11 21:11:38 +0800
commited0e0cf4f678d9e3b13570d217d7960b5ffebdac (patch)
treee6fe1d7460329c64110a89d07a435b7501a4790f /libempathy
parent86b1cd7924f9436c5060787b3025ff5b25679e82 (diff)
downloadgsoc2013-empathy-ed0e0cf4f678d9e3b13570d217d7960b5ffebdac.tar
gsoc2013-empathy-ed0e0cf4f678d9e3b13570d217d7960b5ffebdac.tar.gz
gsoc2013-empathy-ed0e0cf4f678d9e3b13570d217d7960b5ffebdac.tar.bz2
gsoc2013-empathy-ed0e0cf4f678d9e3b13570d217d7960b5ffebdac.tar.lz
gsoc2013-empathy-ed0e0cf4f678d9e3b13570d217d7960b5ffebdac.tar.xz
gsoc2013-empathy-ed0e0cf4f678d9e3b13570d217d7960b5ffebdac.tar.zst
gsoc2013-empathy-ed0e0cf4f678d9e3b13570d217d7960b5ffebdac.zip
We can't use *_run_* API from dbus signal cb or method implementation. To avoid problems move the code to a g_idle cb.
svn path=/trunk/; revision=922
Diffstat (limited to 'libempathy')
-rw-r--r--libempathy/empathy-chandler.c66
-rw-r--r--libempathy/empathy-contact-manager.c7
-rw-r--r--libempathy/empathy-filter.c77
-rw-r--r--libempathy/empathy-tp-contact-factory.c7
-rw-r--r--libempathy/empathy-utils.c96
-rw-r--r--libempathy/empathy-utils.h4
6 files changed, 218 insertions, 39 deletions
diff --git a/libempathy/empathy-chandler.c b/libempathy/empathy-chandler.c
index a294febf4..2fdb37294 100644
--- a/libempathy/empathy-chandler.c
+++ b/libempathy/empathy-chandler.c
@@ -44,17 +44,20 @@ G_DEFINE_TYPE_WITH_CODE (EmpathyChandler, empathy_chandler, G_TYPE_OBJECT,
G_IMPLEMENT_INTERFACE (EMP_TYPE_SVC_CHANDLER,
chandler_iface_init));
-static void
-my_handle_channel (EmpSvcChandler *self,
- const gchar *bus_name,
- const gchar *connection,
- const gchar *channel_type,
- const gchar *channel,
- guint handle_type,
- guint handle,
- DBusGMethodInvocation *context)
+typedef struct {
+ EmpathyChandler *chandler;
+ gchar *bus_name;
+ gchar *connection;
+ gchar *channel_type;
+ gchar *channel;
+ guint handle_type;
+ guint handle;
+} IdleData;
+
+static gboolean
+handle_channel_idle_cb (gpointer data)
{
- EmpathyChandler *chandler = EMPATHY_CHANDLER (self);
+ IdleData *idle_data = data;
TpChannel *chan;
TpConnection *conn;
static TpDBusDaemon *daemon = NULL;
@@ -63,17 +66,52 @@ my_handle_channel (EmpSvcChandler *self,
daemon = tp_dbus_daemon_new (tp_get_bus ());
}
- conn = tp_connection_new (daemon, bus_name, connection, NULL);
- chan = tp_channel_new (conn, channel, channel_type, handle_type, handle, NULL);
+ conn = tp_connection_new (daemon, idle_data->bus_name,
+ idle_data->connection, NULL);
+ chan = tp_channel_new (conn, idle_data->channel, idle_data->channel_type,
+ idle_data->handle_type, idle_data->handle, NULL);
tp_channel_run_until_ready (chan, NULL, NULL);
empathy_debug (DEBUG_DOMAIN, "New channel to be handled: "
"type=%s handle=%d",
- channel_type, handle);
- g_signal_emit (chandler, signals[NEW_CHANNEL], 0, chan);
+ idle_data->channel_type, idle_data->handle);
+ g_signal_emit (idle_data->chandler, signals[NEW_CHANNEL], 0, chan);
g_object_unref (chan);
g_object_unref (conn);
+ g_free (idle_data->bus_name);
+ g_free (idle_data->connection);
+ g_free (idle_data->channel_type);
+ g_free (idle_data->channel);
+ g_slice_free (IdleData, idle_data);
+
+ return FALSE;
+}
+
+static void
+my_handle_channel (EmpSvcChandler *self,
+ const gchar *bus_name,
+ const gchar *connection,
+ const gchar *channel_type,
+ const gchar *channel,
+ guint handle_type,
+ guint handle,
+ DBusGMethodInvocation *context)
+{
+ EmpathyChandler *chandler = EMPATHY_CHANDLER (self);
+ IdleData *data;
+
+ data = g_slice_new (IdleData);
+ data->chandler = chandler;
+ data->bus_name = g_strdup (bus_name);
+ data->connection = g_strdup (connection);
+ data->channel_type = g_strdup (channel_type);
+ data->channel = g_strdup (channel);
+ data->handle_type = handle_type;
+ data->handle = handle;
+ g_idle_add_full (G_PRIORITY_HIGH,
+ handle_channel_idle_cb,
+ data, NULL);
emp_svc_chandler_return_from_handle_channel (context);
}
diff --git a/libempathy/empathy-contact-manager.c b/libempathy/empathy-contact-manager.c
index 1ef3b683a..a151dbd26 100644
--- a/libempathy/empathy-contact-manager.c
+++ b/libempathy/empathy-contact-manager.c
@@ -225,10 +225,9 @@ empathy_contact_manager_init (EmpathyContactManager *manager)
priv->mc = empathy_mission_control_new ();
- dbus_g_proxy_connect_signal (DBUS_G_PROXY (priv->mc),
- "AccountStatusChanged",
- G_CALLBACK (contact_manager_status_changed_cb),
- manager, NULL);
+ empathy_connect_to_account_status_changed (priv->mc,
+ G_CALLBACK (contact_manager_status_changed_cb),
+ manager, NULL);
/* Get ContactList for existing connections */
accounts = mission_control_get_online_connections (priv->mc, NULL);
diff --git a/libempathy/empathy-filter.c b/libempathy/empathy-filter.c
index a5d0757d5..08f9ee6c7 100644
--- a/libempathy/empathy-filter.c
+++ b/libempathy/empathy-filter.c
@@ -53,19 +53,22 @@ G_DEFINE_TYPE_WITH_CODE (EmpathyFilter, empathy_filter, G_TYPE_OBJECT,
G_IMPLEMENT_INTERFACE (EMP_TYPE_SVC_FILTER,
filter_iface_init));
-static void
-my_filter_channel (EmpSvcFilter *self,
- const gchar *bus_name,
- const gchar *connection,
- const gchar *channel_type,
- const gchar *channel,
- guint handle_type,
- guint handle,
- guint id,
- DBusGMethodInvocation *context)
+typedef struct {
+ EmpathyFilter *filter;
+ gchar *bus_name;
+ gchar *connection;
+ gchar *channel_type;
+ gchar *channel;
+ guint handle_type;
+ guint handle;
+ guint id;
+} IdleData;
+
+static gboolean
+filter_channel_idle_cb (gpointer data)
{
- EmpathyFilter *filter = EMPATHY_FILTER (self);
- EmpathyFilterPriv *priv = GET_PRIV (filter);
+ IdleData *idle_data = data;
+ EmpathyFilterPriv *priv = GET_PRIV (idle_data->filter);
TpChannel *chan;
TpConnection *conn;
static TpDBusDaemon *daemon = NULL;
@@ -74,19 +77,58 @@ my_filter_channel (EmpSvcFilter *self,
daemon = tp_dbus_daemon_new (tp_get_bus ());
}
- conn = tp_connection_new (daemon, bus_name, connection, NULL);
- chan = tp_channel_new (conn, channel, channel_type, handle_type, handle, NULL);
+ conn = tp_connection_new (daemon, idle_data->bus_name,
+ idle_data->connection, NULL);
+ tp_connection_run_until_ready (conn, FALSE, NULL, NULL);
+ chan = tp_channel_new (conn, idle_data->channel, idle_data->channel_type,
+ idle_data->handle_type, idle_data->handle, NULL);
tp_channel_run_until_ready (chan, NULL, NULL);
- g_hash_table_insert (priv->table, chan, GUINT_TO_POINTER (id));
+ g_hash_table_insert (priv->table, chan, GUINT_TO_POINTER (idle_data->id));
empathy_debug (DEBUG_DOMAIN, "New channel to be filtred: "
"type=%s handle=%d id=%d",
- channel_type, handle, id);
+ idle_data->channel_type, idle_data->handle,
+ idle_data->id);
- g_signal_emit (filter, signals[NEW_CHANNEL], 0, chan);
+ g_signal_emit (idle_data->filter, signals[NEW_CHANNEL], 0, chan);
g_object_unref (conn);
+ g_free (idle_data->bus_name);
+ g_free (idle_data->connection);
+ g_free (idle_data->channel_type);
+ g_free (idle_data->channel);
+ g_slice_free (IdleData, idle_data);
+
+ return FALSE;
+}
+
+static void
+my_filter_channel (EmpSvcFilter *self,
+ const gchar *bus_name,
+ const gchar *connection,
+ const gchar *channel_type,
+ const gchar *channel,
+ guint handle_type,
+ guint handle,
+ guint id,
+ DBusGMethodInvocation *context)
+{
+ EmpathyFilter *filter = EMPATHY_FILTER (self);
+ IdleData *data;
+
+ data = g_slice_new (IdleData);
+ data->filter = filter;
+ data->bus_name = g_strdup (bus_name);
+ data->connection = g_strdup (connection);
+ data->channel_type = g_strdup (channel_type);
+ data->channel = g_strdup (channel);
+ data->handle_type = handle_type;
+ data->handle = handle;
+ data->id = id;
+ g_idle_add_full (G_PRIORITY_HIGH,
+ filter_channel_idle_cb,
+ data, NULL);
emp_svc_filter_return_from_filter_channel (context);
}
@@ -181,6 +223,7 @@ empathy_filter_new (const gchar *bus_name,
G_OBJECT (filter));
mc = empathy_mission_control_new ();
+
mission_control_register_filter (mc,
bus_name,
object_path,
diff --git a/libempathy/empathy-tp-contact-factory.c b/libempathy/empathy-tp-contact-factory.c
index 91a4a83a7..678e53b36 100644
--- a/libempathy/empathy-tp-contact-factory.c
+++ b/libempathy/empathy-tp-contact-factory.c
@@ -1277,10 +1277,9 @@ empathy_tp_contact_factory_init (EmpathyTpContactFactory *tp_factory)
EmpathyTpContactFactoryPriv *priv = GET_PRIV (tp_factory);
priv->mc = empathy_mission_control_new ();
- dbus_g_proxy_connect_signal (DBUS_G_PROXY (priv->mc),
- "AccountStatusChanged",
- G_CALLBACK (tp_contact_factory_status_changed_cb),
- tp_factory, NULL);
+ empathy_connect_to_account_status_changed (priv->mc,
+ G_CALLBACK (tp_contact_factory_status_changed_cb),
+ tp_factory, NULL);
}
EmpathyTpContactFactory *
diff --git a/libempathy/empathy-utils.c b/libempathy/empathy-utils.c
index b4058cd38..46fb97027 100644
--- a/libempathy/empathy-utils.c
+++ b/libempathy/empathy-utils.c
@@ -633,3 +633,99 @@ empathy_channel_get_account (TpChannel *channel)
return account;
}
+
+typedef void (*AccountStatusChangedFunc) (MissionControl *mc,
+ TpConnectionStatus status,
+ McPresence presence,
+ TpConnectionStatusReason reason,
+ const gchar *unique_name,
+ gpointer *user_data);
+
+typedef struct {
+ AccountStatusChangedFunc handler;
+ gpointer user_data;
+ GClosureNotify free_func;
+} AccountStatusChangedData;
+
+typedef struct {
+ MissionControl *mc;
+ TpConnectionStatus status;
+ McPresence presence;
+ TpConnectionStatusReason reason;
+ gchar *unique_name;
+ AccountStatusChangedData *data;
+} InvocationData;
+
+static void
+account_status_changed_data_free (gpointer ptr,
+ GClosure *closure)
+{
+ AccountStatusChangedData *data = ptr;
+
+ if (data->free_func) {
+ data->free_func (data->user_data, closure);
+ }
+ g_slice_free (AccountStatusChangedData, data);
+}
+
+static gboolean
+account_status_changed_invoke_callback (gpointer data)
+{
+ InvocationData *invocation_data = data;
+
+ invocation_data->data->handler (invocation_data->mc,
+ invocation_data->status,
+ invocation_data->presence,
+ invocation_data->reason,
+ invocation_data->unique_name,
+ invocation_data->data->user_data);
+
+ g_free (invocation_data->unique_name);
+ g_slice_free (InvocationData, invocation_data);
+
+ return FALSE;
+}
+
+static void
+account_status_changed_cb (MissionControl *mc,
+ TpConnectionStatus status,
+ McPresence presence,
+ TpConnectionStatusReason reason,
+ const gchar *unique_name,
+ AccountStatusChangedData *data)
+{
+ InvocationData *invocation_data;
+
+ invocation_data = g_slice_new (InvocationData);
+ invocation_data->mc = mc;
+ invocation_data->status = status;
+ invocation_data->presence = presence;
+ invocation_data->reason = reason;
+ invocation_data->unique_name = g_strdup (unique_name);
+ invocation_data->data = data;
+ g_idle_add_full (G_PRIORITY_HIGH,
+ account_status_changed_invoke_callback,
+ invocation_data, NULL);
+}
+
+void
+empathy_connect_to_account_status_changed (MissionControl *mc,
+ GCallback handler,
+ gpointer user_data,
+ GClosureNotify free_func)
+{
+ AccountStatusChangedData *data;
+
+ g_return_if_fail (IS_MISSIONCONTROL (mc));
+ g_return_if_fail (handler != NULL);
+
+ data = g_slice_new (AccountStatusChangedData);
+
+ data->handler = (AccountStatusChangedFunc) handler;
+ data->user_data = user_data;
+ data->free_func = free_func;
+ dbus_g_proxy_connect_signal (DBUS_G_PROXY (mc), "AccountStatusChanged",
+ G_CALLBACK (account_status_changed_cb),
+ data, account_status_changed_data_free);
+}
+
diff --git a/libempathy/empathy-utils.h b/libempathy/empathy-utils.h
index f717b845a..2b14374fb 100644
--- a/libempathy/empathy-utils.h
+++ b/libempathy/empathy-utils.h
@@ -102,6 +102,10 @@ void empathy_run_until_ready_full (gpointer object,
gpointer user_data,
GMainLoop **loop);
McAccount * empathy_channel_get_account (TpChannel *channel);
+void empathy_connect_to_account_status_changed (MissionControl *mc,
+ GCallback handler,
+ gpointer user_data,
+ GClosureNotify free_func);
G_END_DECLS