From 55b4f238f405e4f5e3ef98283cfb71ae35c4b86e Mon Sep 17 00:00:00 2001 From: Xavier Claessens Date: Sat, 19 Apr 2008 21:04:06 +0000 Subject: Add tubes handler svn path=/trunk/; revision=973 --- src/empathy-tubes-chandler.c | 259 +++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 259 insertions(+) create mode 100644 src/empathy-tubes-chandler.c (limited to 'src/empathy-tubes-chandler.c') diff --git a/src/empathy-tubes-chandler.c b/src/empathy-tubes-chandler.c new file mode 100644 index 000000000..a611b32cc --- /dev/null +++ b/src/empathy-tubes-chandler.c @@ -0,0 +1,259 @@ +/* + * Copyright (C) 2008 Collabora Ltd. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * + * Authors: Elliot Fairweather + */ + + +#include +#include +#include +#include + +#include + +#include +#include +#include +#include +#include + +#define DEBUG_DOMAIN "EmpathyTubesChandler" + +static void +empathy_tubes_chandler_async_cb (TpProxy *proxy, + const GError *error, + gpointer data, + GObject *weak_object) +{ + if (error) + empathy_debug (DEBUG_DOMAIN, "Error %s: %s", data, error->message); +} + + +static void +empathy_tubes_chandler_new_tube_cb (EmpathyTubes *tubes, + EmpathyTube *tube, + gpointer data) +{ + GHashTable *channels = (GHashTable *) data; + TpChannel *channel; + TpConnection *connection; + gchar *channel_path; + gchar *connection_name; + gchar *connection_path; + guint handle_type; + guint handle; + gpointer value; + guint number; + + TpProxy *thandler; + gchar *thandler_bus_name; + gchar *thandler_object_path; + + guint id; + guint type; + gchar *service; + guint state; + + g_object_get (G_OBJECT (tubes), "channel", &channel, NULL); + g_object_get (G_OBJECT (channel), "connection", &connection, "object-path", + &channel_path, NULL); + + value = g_hash_table_lookup (channels, channel_path); + + if (!value) + { + g_hash_table_insert (channels, g_strdup (channel_path), + (GUINT_TO_POINTER (1))); + empathy_debug (DEBUG_DOMAIN, + "Started tube count for channel %s - total: 1", channel_path); + } + else + { + number = GPOINTER_TO_UINT (value); + g_hash_table_replace (channels, g_strdup (channel_path), + GUINT_TO_POINTER (++number)); + empathy_debug (DEBUG_DOMAIN, + "Increased tube count for channel %s - total: %d", + channel_path, number); + } + + g_object_get (G_OBJECT (tube), "state", &state, NULL); + + if (state != TP_TUBE_STATE_LOCAL_PENDING) + { + g_free (channel_path); + g_object_unref (channel); + g_object_unref (connection); + return; + } + + g_object_get (G_OBJECT (tube), "service", &service, "type", &type, NULL); + + if (type == TP_TUBE_TYPE_DBUS) + { + thandler_bus_name = + g_strdup_printf ("org.gnome.Empathy.DTube.%s", service); + thandler_object_path = + g_strdup_printf ("/org/gnome/Empathy/DTube/%s", service); + } + else if (type == TP_TUBE_TYPE_STREAM) + { + thandler_bus_name = + g_strdup_printf ("org.gnome.Empathy.StreamTube.%s", service); + thandler_object_path = + g_strdup_printf ("/org/gnome/Empathy/StreamTube/%s", service); + } + else + { + g_free (channel_path); + g_object_unref (channel); + g_object_unref (connection); + return; + } + + thandler = g_object_new (TP_TYPE_PROXY, "bus-name", thandler_bus_name, + "dbus-connection", tp_get_bus (), "object-path", thandler_object_path, + NULL); + tp_proxy_add_interface_by_id (thandler, EMP_IFACE_QUARK_TUBE_HANDLER); + + g_object_get (G_OBJECT (tube), "id", &id, NULL); + g_object_get (G_OBJECT (channel), "handle-type", &handle_type, + "handle", &handle, NULL); + g_object_get (G_OBJECT (connection), "bus-name", &connection_name, + "object-path", &connection_path, NULL); + + empathy_debug (DEBUG_DOMAIN, "Dispatching new tube to %s", + thandler_bus_name); + + emp_cli_tube_handler_call_handle_tube (thandler, -1, connection_name, + connection_path, channel_path, handle_type, handle, id, + empathy_tubes_chandler_async_cb, "handling tube", NULL, NULL); + + g_free (connection_path); + g_free (connection_name); + g_free (service); + + g_free (thandler_bus_name); + g_free (thandler_object_path); + g_object_unref (thandler); + + g_free (channel_path); + g_object_unref (channel); + g_object_unref (connection); +} + + +static void +empathy_tubes_chandler_tube_closed_cb (EmpathyTubes *tubes, + guint tube_id, + gpointer data) +{ + TpChannel *channel; + gchar *channel_path; + gpointer value; + guint number; + GHashTable *channels = (GHashTable *) data; + + g_object_get (G_OBJECT (tubes), "channel", &channel, NULL); + g_object_get (G_OBJECT (channel), "object-path", &channel_path, NULL); + + value = g_hash_table_lookup (channels, channel_path); + + if (value) + { + number = GPOINTER_TO_UINT (value); + + if (number == 1) + { + g_hash_table_remove (channels, channel_path); + empathy_tubes_close (tubes); + empathy_debug (DEBUG_DOMAIN, + "Ended tube count for channel %s - total: 0", channel_path); + empathy_debug (DEBUG_DOMAIN, "Closing channel"); + } + else if (number > 1) + { + g_hash_table_replace (channels, channel_path, + GUINT_TO_POINTER (--number)); + empathy_debug (DEBUG_DOMAIN, + "Decreased tube count for channel %s - total: %d", + channel_path, number); + } + } + + g_free (channel_path); + g_object_unref (channel); +} + + +static void +empathy_tubes_new_channel_cb (EmpathyChandler *chandler, + TpChannel *channel, + gpointer data) +{ + EmpathyTubes *tubes = empathy_tubes_new (channel); + GHashTable *channels = (GHashTable *) data; + GSList *tube_list, *list; + + empathy_debug (DEBUG_DOMAIN, "Handling new channel"); + + g_signal_connect (G_OBJECT (tubes), "new-tube", + G_CALLBACK (empathy_tubes_chandler_new_tube_cb), (gpointer) channels); + g_signal_connect (G_OBJECT (tubes), "tube-closed", + G_CALLBACK (empathy_tubes_chandler_tube_closed_cb), (gpointer) channels); + + tube_list = empathy_tubes_list_tubes (tubes); + + for (list = tube_list; list != NULL; list = g_slist_next (list)) + { + EmpathyTube *tube = EMPATHY_TUBE (list->data); + empathy_tubes_chandler_new_tube_cb (tubes, tube, (gpointer) channels); + g_object_unref (tube); + } + + g_slist_free (tube_list); +} + + +int main (int argc, char *argv[]) +{ + EmpathyChandler *chandler; + GMainLoop *loop; + GHashTable *channels; + + g_type_init (); + emp_cli_init (); + + channels = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, NULL); + + chandler = empathy_chandler_new ("org.gnome.Empathy.TubesChandler", + "/org/gnome/Empathy/TubesChandler"); + g_signal_connect (chandler, "new-channel", + G_CALLBACK (empathy_tubes_new_channel_cb), (gpointer) channels); + + empathy_debug (DEBUG_DOMAIN, "Ready to handle new tubes channels"); + + loop = g_main_loop_new (NULL, FALSE); + g_main_loop_run (loop); + + g_hash_table_unref (channels); + g_object_unref (chandler); + + return 0; +} -- cgit v1.2.3