Removing dependency of ode package.
[apps/native/starter.git] / src / dbus_util.c
1 /*
2  * Copyright (c) 2000 - 2015 Samsung Electronics Co., Ltd. All rights reserved.
3  *
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
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
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.
15  */
16
17 #include <E_DBus.h>
18
19 #include "dbus_util.h"
20 #include "util.h"
21
22 #define DBUS_REPLY_TIMEOUT (120 * 1000)
23
24 #define POWEROFF_BUS_NAME       "org.tizen.system.popup"
25 #define POWEROFF_OBJECT_PATH    "/Org/Tizen/System/Popup/Powerkey"
26 #define POWEROFF_INTERFACE_NAME POWEROFF_BUS_NAME".Powerkey"
27 #define METHOD_POWEROFF_NAME    "PopupLaunch"
28
29 static E_DBus_Connection *g_e_conn;
30
31 static E_DBus_Connection *_get_e_dbus_connection(void)
32 {
33         if (!g_e_conn)
34                 g_e_conn = e_dbus_bus_get(DBUS_BUS_SYSTEM);
35
36         return g_e_conn;
37 }
38
39 static int _append_variant(DBusMessageIter *iter, const char *sig, char *param[])
40 {
41         char *ch;
42         int i;
43         int int_type;
44         uint64_t int64_type;
45
46         if (!sig || !param)
47                 return 0;
48
49         for (ch = (char*)sig, i = 0; *ch != '\0'; ++i, ++ch) {
50                 switch (*ch) {
51                 case 'i':
52                         int_type = atoi(param[i]);
53                         dbus_message_iter_append_basic(iter, DBUS_TYPE_INT32, &int_type);
54                         break;
55                 case 'u':
56                         int_type = atoi(param[i]);
57                         dbus_message_iter_append_basic(iter, DBUS_TYPE_UINT32, &int_type);
58                         break;
59                 case 't':
60                         int64_type = (uint64_t) atoi(param[i]);
61                         dbus_message_iter_append_basic(iter, DBUS_TYPE_UINT64, &int64_type);
62                         break;
63                 case 's':
64                         dbus_message_iter_append_basic(iter, DBUS_TYPE_STRING, &param[i]);
65                         break;
66                 default:
67                         return -EINVAL;
68                 }
69         }
70
71         return 0;
72 }
73
74
75
76 static int _invoke_dbus_method_sync(const char *dest, const char *path,
77                 const char *interface, const char *method,
78                 int size, char *param[])
79 {
80         DBusConnection *conn;
81         DBusMessage *msg = NULL;
82         DBusMessage *reply;
83         DBusMessageIter iter, aiter, piter;
84         DBusError err;
85         int ret, result, i;
86
87         conn = dbus_bus_get(DBUS_BUS_SYSTEM, NULL);
88         if (!conn) {
89                 ret = 0;
90                 _E("Failed to dbus_bus_get.");
91                 return -EPERM;
92         }
93
94         msg = dbus_message_new_method_call(dest, path, interface, method);
95         if (!msg) {
96                 _E("Failed to dbus_message_new_method_call(%s:%s-%s).", path, interface, method);
97                 dbus_connection_unref(conn);
98                 return -EBADMSG;
99         }
100
101         dbus_message_iter_init_append(msg, &iter);
102         dbus_message_iter_open_container(&iter, DBUS_TYPE_ARRAY, "{ss}", &aiter);
103         for (i = 0 ; i < size ; i = i + 2) {
104                 char *key = param[i];
105                 char *value = param[i+1];
106                 _I("key=%s value=%s", key, value);
107                 dbus_message_iter_open_container(&aiter, DBUS_TYPE_DICT_ENTRY, NULL, &piter);
108                 dbus_message_iter_append_basic(&piter, DBUS_TYPE_STRING, &key);
109                 dbus_message_iter_append_basic(&piter, DBUS_TYPE_STRING, &value);
110                 dbus_message_iter_close_container(&aiter, &piter);
111         }
112
113         dbus_message_iter_close_container(&iter, &aiter);
114         dbus_error_init(&err);
115
116         reply = dbus_connection_send_with_reply_and_block(conn, msg, DBUS_REPLY_TIMEOUT, &err);
117         dbus_message_unref(msg);
118         if (!reply) {
119                 _E("Failed to dbus_connection_send. dest=%s %s:%s-%s. err.name=%s: %s", dest, path, interface, method, err.name, err.message);
120                 dbus_connection_unref(conn);
121                 dbus_error_free(&err);
122                 return -ECOMM;
123         }
124
125         ret = dbus_message_get_args(reply, &err, DBUS_TYPE_INT32, &result, DBUS_TYPE_INVALID);
126         dbus_message_unref(reply);
127         if (!ret) {
128                 _E("No message dest=%s %s:%s-%s. err.name=%s: %s", dest, path, interface, method, err.name, err.message);
129                 dbus_connection_unref(conn);
130                 dbus_error_free(&err);
131                 return -ENOMSG;
132         }
133
134         dbus_connection_unref(conn);
135         return result;
136 }
137
138
139
140 static void dbus_util_broadcast_signal(const char *path, const char *interface, const char *name, const char *type, char *signal[])
141 {
142         DBusMessage *msg;
143         DBusMessageIter iter;
144         DBusConnection *conn = NULL;
145         int r;
146
147         msg = dbus_message_new_signal(path, interface, name);
148         if (!msg) {
149                 _E("Failed to new signal");
150                 return;
151         }
152
153         dbus_message_iter_init_append(msg, &iter);
154         r = _append_variant(&iter, type, signal);
155         if (r < 0) {
156                 _E("Failed to append variant[%d]", r);
157                 dbus_message_unref(msg);
158                 return;
159         }
160
161         conn = dbus_bus_get(DBUS_BUS_SYSTEM, NULL);
162         if (conn == NULL) {
163                 _E("Failed to get bus");
164                 dbus_message_unref(msg);
165                 return;
166         }
167
168         r = dbus_connection_send(conn, msg, NULL);
169         if (!r)
170                 _E("Failed to send message[%s][%s][%s]", path, interface, name);
171         else
172                 _D("dbus_util_broadcast_signal success");
173
174         dbus_message_unref(msg);
175         dbus_connection_unref(conn);
176 }
177
178
179
180 void dbus_util_send_perceptible_signal(int pid)
181 {
182         char *signal[1] = { 0, };
183         char buf[16] = { 0, };
184
185         if (pid <= 0) {
186                 _E("Invalid parameter pid[%d]", pid);
187                 return;
188         }
189
190         snprintf(buf, sizeof(buf), "%d", pid);
191         signal[0] = buf;
192
193         dbus_util_broadcast_signal(RESOURCED_OOM_PATH, RESOURCED_OOM_INTERFACE, SET_PERCEPTIBLE_NAME, "i", &signal[0]);
194 }
195
196
197
198 void dbus_util_send_poweroff_signal(void)
199 {
200         int ret = 0;
201         char *param[2];
202
203         param[0] = "_SYSPOPUP_CONTENT_";
204         param[1] = "powerkey";
205
206         ret = _invoke_dbus_method_sync(POWEROFF_BUS_NAME, POWEROFF_OBJECT_PATH, POWEROFF_INTERFACE_NAME,
207                         METHOD_POWEROFF_NAME, sizeof(param)/sizeof(param[0]), param);
208         ret_if(!ret);
209
210         _D("%s-%s", POWEROFF_INTERFACE_NAME, METHOD_POWEROFF_NAME);
211 }
212
213
214
215 void dbus_util_send_sys_lock_teminate_signal(void)
216 {
217         DBusConnection *conn = NULL;
218         DBusMessage *msg;
219         int ret = 1;
220
221
222         conn = dbus_bus_get(DBUS_BUS_SYSTEM, NULL);
223         if (conn == NULL) {
224                 _E("Failed to get bus");
225                 return;
226         }
227
228         msg = dbus_message_new_signal(SYS_LOCK_OBJECT_PATH,
229                         SYS_LOCK_INTERFACE_TERMINATE,
230                         SYS_LOCK_MEMBER_TERMINATE);
231         if (msg == NULL) {
232                 _E("Failed to dbus_message_new_signal");
233                 dbus_connection_unref(conn);
234                 return;
235         }
236
237         if (!dbus_message_append_args(msg, DBUS_TYPE_INT32, &ret, DBUS_TYPE_INVALID)) {
238                 _E("dbus_message_append_args error");
239         }
240
241         dbus_connection_send(conn, msg, NULL);
242         dbus_message_unref(msg);
243
244         _D("%s-%s", SYS_LOCK_INTERFACE_TERMINATE, SYS_LOCK_MEMBER_TERMINATE);
245         dbus_connection_unref(conn);
246 }
247
248
249
250 int dbus_util_receive_lcd_status(void (*changed_cb)(void *data, DBusMessage *msg), void *data)
251 {
252         E_DBus_Connection *conn;
253         E_DBus_Signal_Handler *handler;
254
255         conn = _get_e_dbus_connection();
256         if (conn == NULL) {
257                 _E("_get_e_dbus_connection error");
258                 return -1;
259         }
260
261         handler = e_dbus_signal_handler_add(conn, NULL, DISPLAY_OBJECT_PATH,
262                                                                 DEVICED_INTERFACE_DISPLAY, MEMBER_LCD_ON,
263                                                                 changed_cb, data);
264         if (handler == NULL) {
265                 _E("e_dbus_signal_handler_add error");
266                 return -1;
267         }
268
269         handler = e_dbus_signal_handler_add(conn, NULL, DISPLAY_OBJECT_PATH,
270                                                                 DEVICED_INTERFACE_DISPLAY, MEMBER_LCD_OFF,
271                                                                 changed_cb, data);
272         if (handler == NULL) {
273                 _E("e_dbus_signal_handler_add error");
274                 return -1;
275         }
276
277         return 0;
278 }
279
280
281
282 int dbus_util_receive_sys_lock_status(void (*changed_cb)(void *data, DBusMessage *msg), void *data)
283 {
284         E_DBus_Connection *conn;
285         E_DBus_Signal_Handler *handler;
286
287         conn = _get_e_dbus_connection();
288         if (conn == NULL) {
289                 _E("_get_e_dbus_connection error");
290                 return -1;
291         }
292
293         handler = e_dbus_signal_handler_add(conn, NULL, SYS_LOCK_OBJECT_PATH,
294                                                                 SYS_LOCK_INTERFACE_UNLOCK, SYS_LOCK_MEMBER_UNLOCK,
295                                                                 changed_cb, data);
296         if (handler == NULL) {
297                 _E("e_dbus_signal_handler_add error");
298                 return -1;
299         }
300
301         return 0;
302 }
303
304 char *dbus_util_msg_arg_get_str(DBusMessage *msg)
305 {
306         int ret = 0;
307         DBusError derror;
308         const char *state = NULL;
309         dbus_error_init(&derror);
310
311         ret = dbus_message_get_args(msg, &derror, DBUS_TYPE_STRING, &state, DBUS_TYPE_INVALID);
312         goto_if(!ret, ERROR);
313
314         dbus_error_free(&derror);
315
316         return strdup(state);
317
318 ERROR:
319         _E("Failed to get reply (%s:%s)", derror.name, derror.message);
320         dbus_error_free(&derror);
321
322         return NULL;
323 }
324
325 void dbus_util_resource_cleanup(void)
326 {
327         if (g_e_conn) {
328                 e_dbus_connection_close(g_e_conn);
329                 g_e_conn = NULL;
330         }
331 }