2 * Copyright (c) 2018 Samsung Electronics Co., Ltd. All rights reserved.
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
8 * http://www.apache.org/licenses/LICENSE-2.0
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
18 #include <comp_gdbus.h>
19 #include <sys/types.h>
21 #define DBUS_SERVICE_DBUS "org.freedesktop.DBus"
22 #define DBUS_INTERFACE_DBUS "org.freedesktop.DBus"
24 static Group *group_skeleton;
25 static Enabler *enabler_skeleton;
27 Group *group_dbus_get_object()
29 return group_skeleton;
32 static bool __group_init(GDBusConnection *connection)
37 GDBusObjectManagerServer *group;
39 // Add interface to default object path
40 group_skeleton = group_skeleton_new();
42 // Register for method callbacks as signal callbacks
43 g_signal_connect(group_skeleton,
45 G_CALLBACK(group_create),
48 g_signal_connect(group_skeleton,
50 G_CALLBACK(group_find),
53 g_signal_connect(group_skeleton,
54 "handle-get-found-groups",
55 G_CALLBACK(group_get_found_groups),
58 g_signal_connect(group_skeleton,
60 G_CALLBACK(group_join),
63 g_signal_connect(group_skeleton,
65 G_CALLBACK(group_leave),
68 g_signal_connect(group_skeleton,
70 G_CALLBACK(group_delete),
73 g_signal_connect(group_skeleton,
75 G_CALLBACK(group_device_find),
78 g_signal_connect(group_skeleton,
80 G_CALLBACK(group_invite),
83 g_signal_connect(group_skeleton,
85 G_CALLBACK(group_eject),
88 g_signal_connect(group_skeleton,
89 "handle-device-invite",
90 G_CALLBACK(group_device_invite),
93 g_signal_connect(group_skeleton,
94 "handle-device-eject",
95 G_CALLBACK(group_device_eject),
98 g_signal_connect(group_skeleton,
99 "handle-get-remote-device",
100 G_CALLBACK(group_get_remote_device),
103 g_signal_connect(group_skeleton,
104 "handle-pair-resource",
105 G_CALLBACK(group_pair_resource),
108 g_signal_connect(group_skeleton,
109 "handle-unpair-resource",
110 G_CALLBACK(group_unpair_resource),
113 g_signal_connect(group_skeleton,
115 G_CALLBACK(group_send_data),
118 g_signal_connect(group_skeleton,
119 "handle-find-mowned-devices",
120 G_CALLBACK(group_find_mowned_devices),
123 g_signal_connect(group_skeleton,
124 "handle-get-mowned-device",
125 G_CALLBACK(group_get_mowned_device),
128 g_signal_connect(group_skeleton,
129 "handle-get-my-mowned-device",
130 G_CALLBACK(group_get_my_mowned_device),
133 g_signal_connect(group_skeleton,
134 "handle-get-my-uuid",
135 G_CALLBACK(group_get_my_uuid),
138 g_signal_connect(group_skeleton,
139 "handle-request-create-group",
140 G_CALLBACK(group_request_create_group),
143 g_signal_connect(group_skeleton,
144 "handle-request-invite",
145 G_CALLBACK(group_request_invite),
148 g_signal_connect(group_skeleton,
149 "handle-request-eject",
150 G_CALLBACK(group_request_eject),
153 g_signal_connect(group_skeleton,
154 "handle-request-delete-group",
155 G_CALLBACK(group_request_delete_group),
158 group = g_dbus_object_manager_server_new(COMP_DBUS_GROUP_PATH);
160 // Set connection to 'manager'
161 g_dbus_object_manager_server_set_connection(group, connection);
163 // Export 'group' interface on companion-manager DBUS
164 ret = g_dbus_interface_skeleton_export(G_DBUS_INTERFACE_SKELETON(group_skeleton),
165 connection, COMP_DBUS_GROUP_PATH, &error);
168 LOG_DEBUG("Can not skeleton_export %s", error->message);
175 static void _app_conn_destroyed_cb(GDBusConnection *conn, const gchar *Name,
176 const gchar *path, const gchar *interface, const gchar *sig,
177 GVariant *param, gpointer user_data)
182 comp_conn_destroy_data *data = user_data;
183 comp_context_t *comp_ctx = comp_context_get_context();
188 g_variant_get(param, "(sss)", &name, &old, &new);
190 if (g_strcmp0(name, data->conn_name) == 0 && *new == '\0') {
191 LOG_DEBUG("App %s Destroyed: name %s id %d", data->conn_name, name,
194 comp_ctx->ref_count -= 1;
196 g_dbus_connection_signal_unsubscribe(data->connection, data->conn_id);
202 g_free(data->conn_name);
205 if (comp_ctx->ref_count == 0) {
206 LOG_DEBUG("No app remaining quit comapnion-manager");
207 g_main_loop_quit(comp_ctx->main_loop);
213 static gboolean _register_comp_conn_destroy_signal(Enabler *enabler,
216 comp_conn_destroy_data *data;
217 GDBusConnection *connection = NULL;
219 connection = g_dbus_interface_skeleton_get_connection(
220 (GDBusInterfaceSkeleton *)enabler_skeleton);
221 if (NULL == connection) {
222 LOG_ERR("Failed to get GDbus connection");
226 data = g_try_malloc0(sizeof(comp_conn_destroy_data));
228 LOG_ERR("Failed to Allocate memory");
232 data->conn_name = g_strdup(name);
233 data->connection = connection;
235 data->conn_id = g_dbus_connection_signal_subscribe(connection,
236 DBUS_SERVICE_DBUS, DBUS_INTERFACE_DBUS,
237 "NameOwnerChanged", NULL, name,
238 G_DBUS_SIGNAL_FLAGS_NONE, _app_conn_destroyed_cb,
244 gboolean enabler_add_ref(Enabler *enabler, GDBusMethodInvocation *invocation,
245 gchar *name, gpointer user_data)
247 LOG_DEBUG("Add Reference for %s", name);
249 if (TRUE == _register_comp_conn_destroy_signal(enabler, name)) {
250 comp_context_t *comp_ctx = comp_context_get_context();
251 comp_ctx->ref_count += 1;
253 enabler_complete_add_ref(enabler, invocation, 0);
255 LOG_ERR("Failed to register connection destroy signal");
256 enabler_complete_add_ref(enabler, invocation,
257 COMP_ERROR_OPERATION_FAILED);
263 static bool __enabler_init(GDBusConnection *connection)
265 gboolean ret = FALSE;
266 GError *error = NULL;
268 GDBusObjectManagerServer *enabler;
270 // Add interface to default object path
271 enabler_skeleton = enabler_skeleton_new();
273 // Register for method callbacks as signal callbacks
274 g_signal_connect(enabler_skeleton,
276 G_CALLBACK(enabler_add_ref),
279 enabler = g_dbus_object_manager_server_new(COMP_DBUS_ENABLER_PATH);
281 // Set connection to 'enabler'
282 g_dbus_object_manager_server_set_connection(enabler, connection);
284 // Export 'enabler' interface on companion DBUS
285 ret = g_dbus_interface_skeleton_export(
286 G_DBUS_INTERFACE_SKELETON(enabler_skeleton), connection,
287 COMP_DBUS_ENABLER_PATH, &error);
290 LOG_DEBUG("Can not skeleton_export %s", error->message);
298 static void on_bus_acquired(GDBusConnection *connection, const gchar *path,
301 if (__group_init(connection) == false)
302 LOG_DEBUG("Can not signal connect");
304 if (__enabler_init(connection) == false)
305 LOG_ERR("Can't signal connect");
308 static void on_name_acquired(GDBusConnection *connection, const gchar *name,
311 LOG_DEBUG("on_name_acquired : %s", name);
314 static void on_name_lost(GDBusConnection *connnection, const gchar *name,
317 LOG_DEBUG("on_name_lost : %s", name);
320 int comp_gdbus_init()
322 g_bus_own_name(G_BUS_TYPE_SYSTEM, COMP_DBUS_SERVICE, G_BUS_NAME_OWNER_FLAGS_NONE,
323 on_bus_acquired, on_name_acquired, on_name_lost, NULL, NULL);