1 /* vi: set et sw=4 ts=4 cino=t0,(0: */
2 /* -*- Mode: C; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
4 * This file is part of gsignond
6 * Copyright (C) 2013 Intel Corporation.
8 * Contact: Amarnath Valluri <amarnath.valluri@linux.intel.com>
10 * This library is free software; you can redistribute it and/or
11 * modify it under the terms of the GNU Lesser General Public
12 * License as published by the Free Software Foundation; either
13 * version 2.1 of the License, or (at your option) any later version.
15 * This library is distributed in the hope that it will be useful, but
16 * WITHOUT ANY WARRANTY; without even the implied warranty of
17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
18 * Lesser General Public License for more details.
20 * You should have received a copy of the GNU Lesser General Public
21 * License along with this library; if not, write to the Free Software
22 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
26 #include "gsignond-dbus-signonui-adapter.h"
27 #include "gsignond/gsignond-log.h"
28 #include "gsignond-dbus.h"
30 struct _GSignondDbusSignonuiAdapterPrivate
32 GDBusConnection *connection;
34 gulong connection_close_signal_id;
37 G_DEFINE_TYPE (GSignondDbusSignonuiAdapter, gsignond_dbus_signonui_adapter, G_TYPE_OBJECT)
44 static guint _signals[SIG_MAX];
46 #define GSIGNOND_DBUS_SIGNONUI_ADAPTER_GET_PRIV(obj) \
47 G_TYPE_INSTANCE_GET_PRIVATE ((obj), GSIGNOND_TYPE_DBUS_SIGNONUI_ADAPTER, GSignondDbusSignonuiAdapterPrivate)
51 GSignondDbusSignonuiAdapter *adapter;
57 _dispose (GObject *object)
59 GSignondDbusSignonuiAdapter *self = GSIGNOND_DBUS_SIGNONUI_ADAPTER (object);
61 if (self->priv->connection_close_signal_id) {
62 g_signal_handler_disconnect (self->priv->connection, self->priv->connection_close_signal_id);
63 self->priv->connection_close_signal_id = 0;
66 if (self->priv->connection) {
67 g_object_unref (self->priv->connection);
68 self->priv->connection = NULL;
71 if (self->priv->proxy) {
72 g_object_unref (self->priv->proxy);
73 self->priv->proxy = NULL;
76 G_OBJECT_CLASS (gsignond_dbus_signonui_adapter_parent_class)->dispose (object);
80 _finalize (GObject *object)
82 G_OBJECT_CLASS (gsignond_dbus_signonui_adapter_parent_class)->finalize (object);
86 gsignond_dbus_signonui_adapter_class_init (GSignondDbusSignonuiAdapterClass *klass)
88 GObjectClass* object_class = G_OBJECT_CLASS (klass);
90 g_type_class_add_private (object_class, sizeof (GSignondDbusSignonuiAdapterPrivate));
92 object_class->dispose = _dispose;
93 object_class->finalize = _finalize;
95 _signals[SIG_REFRESH] = g_signal_new ("refresh",
96 GSIGNOND_TYPE_DBUS_SIGNONUI_ADAPTER,
107 gsignond_dbus_signonui_adapter_init (GSignondDbusSignonuiAdapter *self)
109 self->priv = GSIGNOND_DBUS_SIGNONUI_ADAPTER_GET_PRIV(self);
110 self->priv->connection = 0;
111 self->priv->proxy = 0;
112 self->priv->connection_close_signal_id = 0;
116 _on_proxy_signal (GSignondDbusSignonuiAdapter *adapter,
122 gchar *request_id = NULL;
124 g_return_if_fail (adapter && signal_name && params);
126 /* Ignore other than 'refresh' signal */
127 if (g_strcmp0(signal_name, "refresh") != 0) return ;
129 if (!g_variant_is_of_type (params, G_VARIANT_TYPE_TUPLE)) {
130 WARN ("Expected 'tuple' type but got '%s' type",
131 g_variant_get_type_string (params));
135 g_variant_get (params, "(s)", &request_id);
138 g_signal_emit (adapter, _signals[SIG_REFRESH], 0, request_id);
144 _on_connection_closed (GSignondDbusSignonuiAdapter *adapter,
145 gboolean remote_peer_vanished,
149 g_return_if_fail (adapter);
151 DBG("UI Connection closed...");
153 g_signal_handler_disconnect (adapter->priv->connection, adapter->priv->connection_close_signal_id);
154 adapter->priv->connection_close_signal_id = 0;
156 g_clear_object (&adapter->priv->connection);
157 g_clear_object (&adapter->priv->proxy);
161 _setup_ui_connection (GSignondDbusSignonuiAdapter *adapter)
164 GVariant *reply = NULL;
165 gchar *ui_server_address = NULL;
166 GDBusConnection *session_bus = NULL;
168 g_return_val_if_fail (adapter, FALSE);
170 if (adapter->priv->connection) return TRUE;
172 session_bus = g_bus_get_sync (G_BUS_TYPE_SESSION, NULL, &err);
174 WARN ("Error getting session bus :%s", err->message);
178 reply = g_dbus_connection_call_sync (session_bus, SIGNONUI_SERVICE, SIGNONUI_OBJECTPATH,
179 SIGNONUI_IFACE, "getBusAddress", g_variant_new ("()"),
180 G_VARIANT_TYPE_TUPLE, G_DBUS_CALL_FLAGS_NONE, -1, NULL, &err);
182 WARN ("Failed to get signon ui bus address : %s", err->message);
186 g_variant_get(reply, "(s)", &ui_server_address);
188 DBG ("Connecting to UI Server at : %s", ui_server_address);
190 adapter->priv->connection = g_dbus_connection_new_for_address_sync (ui_server_address,
191 G_DBUS_CONNECTION_FLAGS_AUTHENTICATION_CLIENT, NULL, NULL, &err);
192 g_free (ui_server_address);
194 WARN ("Failed to connect UI server at address '%s' : %s", ui_server_address,
199 adapter->priv->connection_close_signal_id =
200 g_signal_connect_swapped (adapter->priv->connection,
201 "closed", G_CALLBACK(_on_connection_closed), adapter);
203 adapter->priv->proxy = g_dbus_proxy_new_sync (adapter->priv->connection,
204 G_DBUS_PROXY_FLAGS_DO_NOT_LOAD_PROPERTIES,
207 SIGNONUI_DIALOG_OBJECTPATH,
208 SIGNONUI_DIALOG_IFACE,
212 WARN ("failed to get ui object : %s", err->message);
216 g_signal_connect_swapped (adapter->priv->proxy, "g-signal", G_CALLBACK (_on_proxy_signal), adapter);
220 if (err) g_error_free (err);
225 _on_query_dialog_ready (GObject *proxy, GAsyncResult *res, gpointer user_data)
227 GError *error = NULL;
228 GVariant *reply = NULL;
229 _SignonuiDbusInfo *info = (_SignonuiDbusInfo *)user_data;
231 reply = g_dbus_proxy_call_finish (G_DBUS_PROXY (proxy), res, &error);
235 GVariant *out_params = NULL;
238 g_variant_get (reply, "(@a{sv})", &out_params);
240 ((GSignondDbusSignonuiQueryDialogCb)info->cb) (out_params, error, info->data);
241 if(out_params) g_variant_unref (out_params);
243 g_object_unref (info->adapter);
244 g_slice_free (_SignonuiDbusInfo, info);
247 if (error) g_error_free (error);
248 if (reply) g_variant_unref (reply);
252 gsignond_dbus_signonui_adapter_query_dialog (GSignondDbusSignonuiAdapter *adapter,
254 const GSignondDbusSignonuiQueryDialogCb callback,
257 if (!adapter || !GSIGNOND_IS_DBUS_SIGNONUI_ADAPTER (adapter)) {
258 WARN ("assert (!adapter ||!GSIGNOND_IS_DBUS_SIGNONUI_ADAPTER (adapter)) failed");
261 if (!adapter->priv->proxy && !_setup_ui_connection(adapter)) {
262 WARN ("Failed to setup ui connection");
265 _SignonuiDbusInfo *info = g_slice_new0 (_SignonuiDbusInfo);
267 info->adapter = g_object_ref (adapter);
269 info->data = user_data;
271 g_dbus_proxy_call (adapter->priv->proxy, "queryDialog",
272 g_variant_new ("(@a{sv})", params), G_DBUS_CALL_FLAGS_NONE, G_MAXINT, NULL,
273 _on_query_dialog_ready, (gpointer)info);
279 _on_refresh_dialog_ready (GObject *proxy, GAsyncResult *res, gpointer user_data)
281 GError *error = NULL;
282 GVariant *reply = NULL;
283 _SignonuiDbusInfo *info = (_SignonuiDbusInfo *)user_data;
285 reply = g_dbus_proxy_call_finish (G_DBUS_PROXY (proxy), res, &error);
289 ((GSignondDbusSignonuiRefreshDialogCb)info->cb) (error, info->data);
290 g_object_unref (info->adapter);
291 g_slice_free (_SignonuiDbusInfo, info);
294 if (reply) g_variant_unref (reply);
295 if (error) g_error_free (error);
299 gsignond_dbus_signonui_adapter_refresh_dialog (GSignondDbusSignonuiAdapter *adapter,
301 const GSignondDbusSignonuiRefreshDialogCb callback,
304 if (!adapter || !GSIGNOND_IS_DBUS_SIGNONUI_ADAPTER (adapter)) {
305 WARN ("assert (!adapter ||!GSIGNOND_IS_DBUS_SIGNONUI_ADAPTER (adapter)) failed");
308 if (!adapter->priv->proxy && !_setup_ui_connection(adapter)) {
309 WARN ("Failed to setup ui connection");
313 _SignonuiDbusInfo *info = g_slice_new0 (_SignonuiDbusInfo);
315 info->adapter = g_object_ref (adapter);
317 info->data = user_data;
319 g_dbus_proxy_call (adapter->priv->proxy, "refreshDialog",
320 g_variant_new ("(a{sv})", params), G_DBUS_CALL_FLAGS_NONE, -1, NULL,
321 _on_refresh_dialog_ready, (gpointer)info);
327 _on_cancel_request_ready (GObject *proxy, GAsyncResult *res, gpointer user_data)
329 GError *error = NULL;
330 GVariant *reply = NULL;
331 _SignonuiDbusInfo *info = (_SignonuiDbusInfo *)user_data;
333 reply = g_dbus_proxy_call_finish (G_DBUS_PROXY (proxy), res, &error);
337 ((GSignondDbusSignonuiCancelRequestCb)info->cb) (error, info->data);
338 g_object_unref (info->adapter);
339 g_slice_free (_SignonuiDbusInfo, info);
342 if (reply) g_variant_unref (reply);
343 if (error) g_error_free (error);
347 gsignond_dbus_signonui_adapter_cancel_request (GSignondDbusSignonuiAdapter *adapter,
348 const gchar *request_id,
349 const GSignondDbusSignonuiCancelRequestCb callback,
352 if (!adapter || !GSIGNOND_IS_DBUS_SIGNONUI_ADAPTER (adapter)) {
353 WARN ("assert (!adapter ||!GSIGNOND_IS_DBUS_SIGNONUI_ADAPTER (adapter)) failed");
356 if (!adapter->priv->proxy && !_setup_ui_connection(adapter)) {
357 WARN ("Failed to setup ui connection");
360 _SignonuiDbusInfo *info = g_slice_new0 (_SignonuiDbusInfo);
362 info->adapter = g_object_ref (adapter);
364 info->data = user_data;
366 g_dbus_proxy_call (adapter->priv->proxy, "cancelUiRequest",
367 g_variant_new ("(s)", request_id), G_DBUS_CALL_FLAGS_NONE, -1, NULL,
368 _on_cancel_request_ready, (gpointer)info);
374 * gsignond_dbus_signonui_adapter_new:
376 * Creates new instance of #GSignondDbusSignonuiAdapter
378 * Retrurns: (transfer full) new instance of #GSignondDbusSignonuiAdapter
380 GSignondDbusSignonuiAdapter *
381 gsignond_dbus_signonui_adapter_new ()
383 GSignondDbusSignonuiAdapter *adapter = GSIGNOND_DBUS_SIGNONUI_ADAPTER (
384 g_object_new (GSIGNOND_TYPE_DBUS_SIGNONUI_ADAPTER, NULL));
386 if (!_setup_ui_connection (adapter)) {
387 g_object_unref (adapter);