4 * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved.
6 * Contact: Seungtaek Chung <seungtaek.chung@samsung.com>, Mi-Ju Lee <miju52.lee@samsung.com>, Xi Zhichan <zhichan.xi@samsung.com>
8 * Licensed under the Apache License, Version 2.0 (the "License");
9 * you may not use this file except in compliance with the License.
10 * You may obtain a copy of the License at
12 * http://www.apache.org/licenses/LICENSE-2.0
14 * Unless required by applicable law or agreed to in writing, software
15 * distributed under the License is distributed on an "AS IS" BASIS,
16 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
17 * See the License for the specific language governing permissions and
18 * limitations under the License.
27 #include <bundle_internal.h>
29 #include <notification_ipc.h>
30 #include <notification_db.h>
31 #include <notification_type.h>
32 #include <notification_private.h>
33 #include <notification_debug.h>
34 #include <notification_setting.h>
35 #include <notification_setting_internal.h>
36 #include <notification_internal.h>
40 #define PROVIDER_BUS_NAME "org.tizen.data_provider_service"
41 #define PROVIDER_OBJECT_PATH "/org/tizen/data_provider_service"
42 #define PROVIDER_NOTI_INTERFACE_NAME "org.tizen.data_provider_noti_service"
44 #define DBUS_SERVICE_DBUS "org.freedesktop.DBus"
45 #define DBUS_PATH_DBUS "/org/freedesktop/DBus"
46 #define DBUS_INTERFACE_DBUS "org.freedesktop.DBus"
48 static const gchar *_bus_name = NULL;
49 static GDBusConnection *_gdbus_conn = NULL;
50 static int monitor_id = 0;
51 static int provider_monitor_id = 0;
52 static int is_master_started = 0;
54 static const char *NOTI_DATA_STRING[] = {
55 "NOTIFICATION_DATA_TYPE_NOTI_TYPE",
56 "NOTIFICATION_DATA_TYPE_LAYOUT",
57 "NOTIFICATION_DATA_TYPE_GROUP_ID",
58 "NOTIFICATION_DATA_TYPE_INTERNAL_GROUP_ID",
59 "NOTIFICATION_DATA_TYPE_PRIV_ID",
60 "NOTIFICATION_DATA_TYPE_CALLER_PKGNAME",
61 "NOTIFICATION_DATA_TYPE_LAUNCH_PKGNAME",
62 "NOTIFICATION_DATA_TYPE_ARGS",
63 "NOTIFICATION_DATA_TYPE_GROUP_ARGS",
64 "NOTIFICATION_DATA_TYPE_EXECUTE_OPTION",
65 "NOTIFICATION_DATA_TYPE_SERVICE_RESPONDING",
66 "NOTIFICATION_DATA_TYPE_SERVICE_SINGLE_LAUNCH",
67 "NOTIFICATION_DATA_TYPE_SERVICE_MULTI_LAUNCH",
68 "NOTIFICATION_DATA_TYPE_BUTTON1_EVENT",
69 "NOTIFICATION_DATA_TYPE_BUTTON2_EVENT",
70 "NOTIFICATION_DATA_TYPE_BUTTON3_EVENT",
71 "NOTIFICATION_DATA_TYPE_BUTTON4_EVENT",
72 "NOTIFICATION_DATA_TYPE_BUTTON5_EVENT",
73 "NOTIFICATION_DATA_TYPE_BUTTON6_EVENT",
74 "NOTIFICATION_DATA_TYPE_ICON_EVENT",
75 "NOTIFICATION_DATA_TYPE_THUMBNAIL_EVENT",
76 "NOTIFICATION_DATA_TYPE_DOMAIN",
77 "NOTIFICATION_DATA_TYPE_DIR",
78 "NOTIFICATION_DATA_TYPE_TEXT",
79 "NOTIFICATION_DATA_TYPE_KEY",
80 "NOTIFICATION_DATA_TYPE_FORMAT_ARGS",
81 "NOTIFICATION_DATA_TYPE_NUM_FORMAT_ARGS",
82 "NOTIFICATION_DATA_TYPE_IMAGE_PATH",
83 "NOTIFICATION_DATA_TYPE_SOUND_TYPE",
84 "NOTIFICATION_DATA_TYPE_SOUND_PATH",
85 "NOTIFICATION_DATA_TYPE_VIBRATION_TYPE",
86 "NOTIFICATION_DATA_TYPE_VIBRATION_PATH",
87 "NOTIFICATION_DATA_TYPE_LED_OPERATION",
88 "NOTIFICATION_DATA_TYPE_LED_ARGB",
89 "NOTIFICATION_DATA_TYPE_LED_ON_MS",
90 "NOTIFICATION_DATA_TYPE_LED_OFF_MS",
91 "NOTIFICATION_DATA_TYPE_TIME",
92 "NOTIFICATION_DATA_TYPE_INSERT_TIME",
93 "NOTIFICATION_DATA_TYPE_FLAGS_FOR_PROPERTY",
94 "NOTIFICATION_DATA_TYPE_DISPLAY_APPLIST",
95 "NOTIFICATION_DATA_TYPE_PROGRESS_SIZE",
96 "NOTIFICATION_DATA_TYPE_PROGRESS_PERCENTAGE",
97 "NOTIFICATION_DATA_TYPE_APP_ICON_PATH",
98 "NOTIFICATION_DATA_TYPE_APP_NAME",
99 "NOTIFICATION_DATA_TYPE_TEMP_TITLE",
100 "NOTIFICATION_DATA_TYPE_TEMP_CONTENT",
101 "NOTIFICATION_DATA_TYPE_TAG",
102 "NOTIFICATION_DATA_TYPE_ONGOING_FLAG",
103 "NOTIFICATION_DATA_TYPE_AUTO_REMOVE",
107 typedef struct _result_cb_item {
108 void (*result_cb)(int priv_id, int result, void *data);
112 typedef struct _task_list task_list;
117 void (*task_cb) (void *data);
121 static task_list *g_task_list;
123 static int _ipc_monitor_register(void);
124 static int _ipc_monitor_deregister(void);
125 static void _do_deffered_task(void);
127 static void _print_noti(notification_h noti) {
128 char *pkgname = NULL;
130 char *content = NULL;
131 const char *tag = NULL;
133 notification_get_pkgname(noti, &pkgname);
134 notification_get_text(noti, NOTIFICATION_TEXT_TYPE_TITLE, &text);
135 notification_get_text(noti, NOTIFICATION_TEXT_TYPE_CONTENT, &content);
136 notification_get_tag(noti, &tag);
138 NOTIFICATION_DBG("client print_noti pkgname = %s ", pkgname );
139 NOTIFICATION_DBG("client print_noti title = %s ", text );
140 NOTIFICATION_DBG("client print_noti content = %s ", content );
141 NOTIFICATION_DBG("client print_noti tag = %s ", tag );
142 NOTIFICATION_DBG("client print_noti priv_id = %d ", noti->priv_id);
143 NOTIFICATION_DBG("client print_noti vibration_path = %s ", noti->vibration_path);
146 static inline char *_string_get(char *string)
151 if (string[0] == '\0')
158 int notification_ipc_is_master_ready(void)
164 result = g_dbus_connection_call_sync(
170 g_variant_new("(s)", PROVIDER_BUS_NAME),
171 G_VARIANT_TYPE("(b)"),
172 G_DBUS_CALL_FLAGS_NONE,
177 if (err || (result == NULL)) {
179 NOTIFICATION_ERR("No reply. error = %s", err->message);
182 is_master_started = 0;
184 g_variant_get(result, "(b)", &name_exist);
187 NOTIFICATION_ERR("Name not exist %s", PROVIDER_BUS_NAME);
188 NOTIFICATION_ERR("the master has been stopped");
189 is_master_started = 0;
191 NOTIFICATION_DBG("the master has been started");
192 is_master_started = 1;
197 g_variant_unref(result);
199 return is_master_started;
202 /* TODO: dbus activation isn't enough ? */
204 * store tasks when daemon stopped
206 int notification_ipc_add_deffered_task(
207 void (*deferred_task_cb)(void *data),
214 (task_list *) malloc(sizeof(task_list));
216 if (list_new == NULL)
217 return NOTIFICATION_ERROR_OUT_OF_MEMORY;
219 list_new->next = NULL;
220 list_new->prev = NULL;
222 list_new->task_cb = deferred_task_cb;
223 list_new->data = user_data;
225 if (g_task_list == NULL) {
226 g_task_list = list_new;
230 while (list->next != NULL)
233 list->next = list_new;
234 list_new->prev = list;
236 return NOTIFICATION_ERROR_NONE;
239 int notification_ipc_del_deffered_task(
240 void (*deferred_task_cb)(void *data))
243 task_list *list_prev;
244 task_list *list_next;
246 list_del = g_task_list;
248 if (list_del == NULL)
249 return NOTIFICATION_ERROR_INVALID_PARAMETER;
251 while (list_del->prev != NULL)
252 list_del = list_del->prev;
255 if (list_del->task_cb == deferred_task_cb) {
256 list_prev = list_del->prev;
257 list_next = list_del->next;
259 if (list_prev == NULL)
260 g_task_list = list_next;
262 list_prev->next = list_next;
264 if (list_next == NULL) {
265 if (list_prev != NULL)
266 list_prev->next = NULL;
268 list_next->prev = list_prev;
272 return NOTIFICATION_ERROR_NONE;
274 list_del = list_del->next;
275 } while (list_del != NULL);
277 return NOTIFICATION_ERROR_INVALID_PARAMETER;
280 static void _do_deffered_task(void)
283 task_list *list_temp;
285 if (g_task_list == NULL)
288 list_do = g_task_list;
291 while (list_do->prev != NULL)
292 list_do = list_do->prev;
294 while (list_do != NULL) {
295 if (list_do->task_cb != NULL) {
296 list_do->task_cb(list_do->data);
297 NOTIFICATION_DBG("called:%p", list_do->task_cb);
299 list_temp = list_do->next;
306 * functions to create operation list
308 static notification_op *_ipc_create_op(notification_op_type_e type,
309 int num_op, int *list_priv_id, int num_priv_id, notification_h *noti_list)
312 notification_op *op_list;
317 op_list = (notification_op *)malloc(sizeof(notification_op) * num_op);
319 if (op_list == NULL) {
320 NOTIFICATION_ERR("malloc failed");
324 memset(op_list, 0x0, sizeof(notification_op) * num_op);
326 for (i = 0; i < num_op; i++) {
327 (op_list + i)->type = type;
328 if (list_priv_id != NULL)
329 (op_list + i)->priv_id = *(list_priv_id + i);
330 if (noti_list != NULL)
331 (op_list + i)->noti = *(noti_list + i);
338 * utility functions creating notification packet
340 static inline char *_dup_string(const char *string)
346 if (string[0] == '\0')
349 ret = strdup(string);
351 NOTIFICATION_ERR("Error: %s\n", strerror(errno));
356 static inline bundle *_create_bundle_from_bundle_raw(bundle_raw *string)
360 if (string[0] == '\0')
363 return bundle_decode(string, strlen((char *)string));
366 static void _add_noti_notify(GVariant *parameters)
369 notification_op *noti_op;
370 GVariant *body = NULL;
372 NOTIFICATION_DBG("add noti notify");
373 noti = notification_create(NOTIFICATION_TYPE_NOTI);
375 NOTIFICATION_ERR("failed to create a notification");
379 g_variant_get(parameters, "(v)", &body);
380 notification_ipc_make_noti_from_gvariant(noti, body);
382 if (noti->flags_for_property & NOTIFICATION_PROP_DISABLE_UPDATE_ON_INSERT) {
383 NOTIFICATION_ERR("disable changed callback %d", noti->flags_for_property);
384 /* Disable changed cb */
386 /* Enable changed cb */
387 noti_op = _ipc_create_op(NOTIFICATION_OP_INSERT, 1, &(noti->priv_id), 1, ¬i);
389 if (noti_op != NULL) {
390 notification_call_changed_cb(noti_op, 1);
394 notification_free(noti);
397 static void _update_noti_notify(GVariant *parameters)
400 notification_op *noti_op;
401 GVariant *body = NULL;
403 noti = notification_create(NOTIFICATION_TYPE_NOTI);
405 NOTIFICATION_ERR("failed to create a notification");
408 g_variant_get(parameters, "(v)", &body);
409 notification_ipc_make_noti_from_gvariant(noti, body);
412 noti_op = _ipc_create_op(NOTIFICATION_OP_UPDATE, 1, &(noti->priv_id), 1, ¬i);
413 if (noti_op != NULL) {
414 notification_call_changed_cb(noti_op, 1);
417 notification_free(noti);
420 static void _refresh_noti_notify(GVariant *parameters)
422 notification_op *noti_op = _ipc_create_op(NOTIFICATION_OP_REFRESH, 1, NULL, 0, NULL);
424 if (noti_op != NULL) {
425 notification_call_changed_cb(noti_op, 1);
430 static void _delete_single_notify(GVariant *parameters)
434 notification_op *noti_op;
437 g_variant_get(parameters, "(ii)", &num_deleted, &priv_id);
439 noti_op = _ipc_create_op(NOTIFICATION_OP_DELETE, 1, &priv_id, 1, NULL);
440 if (noti_op != NULL) {
441 notification_call_changed_cb(noti_op, 1);
446 static void _delete_multiple_notify(GVariant *parameters)
450 notification_op *noti_op;
453 g_variant_get(parameters, "(a(i))", &iter);
454 while (g_variant_iter_loop(iter, "(i)", &buf[idx])) {
455 NOTIFICATION_DBG("delete_noti_multiple priv_id : %d", buf[idx]);
458 g_variant_iter_free(iter);
460 NOTIFICATION_DBG("data num deleted:%d", idx);
461 noti_op = _ipc_create_op(NOTIFICATION_OP_DELETE, idx, buf, idx, NULL);
463 if (noti_op == NULL) {
464 NOTIFICATION_ERR("_ipc_create_op failed");
467 notification_call_changed_cb(noti_op, idx);
471 static void _handle_noti_notify(GDBusConnection *connection,
472 const gchar *sender_name,
473 const gchar *object_path,
474 const gchar *interface_name,
475 const gchar *signal_name,
476 GVariant *parameters,
479 NOTIFICATION_DBG("signal_name: %s", signal_name);
481 if (g_strcmp0(signal_name, "add_noti_notify") == 0)
482 _add_noti_notify(parameters);
483 else if (g_strcmp0(signal_name, "update_noti_notify") == 0)
484 _update_noti_notify(parameters);
485 else if (g_strcmp0(signal_name, "delete_single_notify") == 0)
486 _delete_single_notify(parameters);
487 else if (g_strcmp0(signal_name, "delete_multiple_notify") == 0)
488 _delete_multiple_notify(parameters);
489 else if (g_strcmp0(signal_name, "refresh_noti_notify") == 0)
490 _refresh_noti_notify(parameters);
494 static int _dbus_signal_init()
497 int ret = NOTIFICATION_ERROR_NONE;
499 if (monitor_id == 0) {
500 id = g_dbus_connection_signal_subscribe(_gdbus_conn,
502 PROVIDER_NOTI_INTERFACE_NAME, /* interface */
504 PROVIDER_OBJECT_PATH, /* path */
506 G_DBUS_SIGNAL_FLAGS_NONE,
511 NOTIFICATION_DBG("subscribe id : %d", id);
513 ret = NOTIFICATION_ERROR_IO_ERROR;
514 NOTIFICATION_ERR("Failed to _register_noti_dbus_interface");
517 ret = NOTIFICATION_ERROR_NONE;
524 static int _dbus_init()
526 int ret = NOTIFICATION_ERROR_NONE;
527 GError *error = NULL;
529 if (_gdbus_conn == NULL) {
530 _gdbus_conn = g_bus_get_sync(G_BUS_TYPE_SYSTEM, NULL, &error);
532 if (_gdbus_conn == NULL) {
534 NOTIFICATION_ERR("Failed to get dbus [%s]", error->message);
537 return NOTIFICATION_ERROR_IO_ERROR;
539 _bus_name = g_dbus_connection_get_unique_name(_gdbus_conn);
540 NOTIFICATION_DBG("bus name : %s", _bus_name);
542 notification_error_quark();
544 ret = NOTIFICATION_ERROR_NONE;
549 static int _send_sync_noti(GVariant *body, GDBusMessage **reply, char *cmd)
551 int ret = NOTIFICATION_ERROR_NONE;
555 msg = g_dbus_message_new_method_call(
557 PROVIDER_OBJECT_PATH,
558 PROVIDER_NOTI_INTERFACE_NAME,
561 NOTIFICATION_ERR("Can't allocate new method call");
563 g_variant_unref(body);
564 return NOTIFICATION_ERROR_OUT_OF_MEMORY;
568 g_dbus_message_set_body(msg, body);
570 *reply = g_dbus_connection_send_message_with_reply_sync(
573 G_DBUS_SEND_MESSAGE_FLAGS_NONE,
582 ret = NOTIFICATION_ERROR_SERVICE_NOT_READY;
584 NOTIFICATION_ERR("No reply. cmd = %s, error = %s", cmd, err->message);
585 if (err->code == G_DBUS_ERROR_ACCESS_DENIED)
586 ret = NOTIFICATION_ERROR_PERMISSION_DENIED;
592 if (g_dbus_message_to_gerror(*reply, &err)) {
594 NOTIFICATION_ERR("_send_sync_noti cmd = %s, error %s", cmd, err->message);
598 NOTIFICATION_DBG("_send_sync_noti done !!");
599 return NOTIFICATION_ERROR_NONE;
603 static void _send_message_with_reply_async_cb(GDBusConnection *connection,
608 int result = NOTIFICATION_ERROR_NONE;
610 GDBusMessage *reply = NULL;
612 result_cb_item *cb_item = (result_cb_item *)user_data;
614 if (cb_item == NULL) {
615 NOTIFICATION_ERR("Failed to get a callback item");
619 reply = g_dbus_connection_send_message_with_reply_finish(
626 NOTIFICATION_ERR("No reply. error = %s", err->message);
629 result = NOTIFICATION_ERROR_SERVICE_NOT_READY;
631 } else if (g_dbus_message_to_gerror(reply, &err)) {
634 NOTIFICATION_ERR("_send_async_noti error %s", err->message);
637 NOTIFICATION_DBG("_send_async_noti done !![%d]", result);
639 if (result == NOTIFICATION_ERROR_NONE) {
640 body = g_dbus_message_get_body(reply);
641 g_variant_get(body, "(i)", &priv_id);
643 if (cb_item->result_cb)
644 cb_item->result_cb(priv_id, result, cb_item->data);
647 if (cb_item->result_cb)
648 cb_item->result_cb(NOTIFICATION_PRIV_ID_NONE, result, cb_item->data);
652 g_object_unref(reply);
656 static int _send_async_noti(GVariant *body, result_cb_item *cb_item, char *cmd)
660 msg = g_dbus_message_new_method_call(
662 PROVIDER_OBJECT_PATH,
663 PROVIDER_NOTI_INTERFACE_NAME,
666 NOTIFICATION_ERR("Can't allocate new method call");
667 return NOTIFICATION_ERROR_OUT_OF_MEMORY;
671 g_dbus_message_set_body(msg, body);
673 g_dbus_connection_send_message_with_reply(
676 G_DBUS_SEND_MESSAGE_FLAGS_NONE,
680 (GAsyncReadyCallback)_send_message_with_reply_async_cb,
683 NOTIFICATION_DBG("_send_async_noti done !!");
686 return NOTIFICATION_ERROR_NONE;
689 int notification_ipc_request_insert(notification_h noti, int *priv_id)
693 GDBusMessage *reply = NULL;
695 GVariant *reply_body;
697 result = _dbus_init();
698 if (result != NOTIFICATION_ERROR_NONE) {
699 NOTIFICATION_ERR("Can't init dbus %d", result);
703 /* Initialize private ID */
704 noti->priv_id = NOTIFICATION_PRIV_ID_NONE;
705 noti->group_id = NOTIFICATION_GROUP_ID_NONE;
706 noti->internal_group_id = NOTIFICATION_GROUP_ID_NONE;
709 body = notification_ipc_make_gvariant_from_noti(noti);
711 NOTIFICATION_ERR("cannot make gvariant");
712 return NOTIFICATION_ERROR_OUT_OF_MEMORY;
715 result = _send_sync_noti(body, &reply, "add_noti");
716 NOTIFICATION_DBG("_send_sync_noti %d", result);
718 if (result == NOTIFICATION_ERROR_NONE) {
719 reply_body = g_dbus_message_get_body(reply);
720 g_variant_get(reply_body, "(i)", &id);
727 g_object_unref(reply);
729 NOTIFICATION_DBG("notification_ipc_request_insert done [priv_id : %d, result: %d]", *priv_id, result);
733 int notification_ipc_request_update(notification_h noti)
738 GDBusMessage *reply = NULL;
740 GVariant *reply_body;
742 result = _dbus_init();
743 if (result != NOTIFICATION_ERROR_NONE) {
744 NOTIFICATION_ERR("Can't init dbus %d", result);
748 body = notification_ipc_make_gvariant_from_noti(noti);
750 NOTIFICATION_ERR("cannot make gvariant");
751 return NOTIFICATION_ERROR_OUT_OF_MEMORY;
754 result = _send_sync_noti(body, &reply, "update_noti");
755 if (result == NOTIFICATION_ERROR_NONE) {
756 reply_body = g_dbus_message_get_body(reply);
757 g_variant_get(reply_body, "(i)", &priv_id);
761 g_object_unref(reply);
763 NOTIFICATION_DBG("notification_ipc_request_update done [result: %d, priv_id :%d]", result, priv_id);
767 int notification_ipc_request_update_async(notification_h noti,
768 void (*result_cb)(int priv_id, int result, void *data), void *user_data)
771 result_cb_item *cb_item;
774 result = _dbus_init();
775 if (result != NOTIFICATION_ERROR_NONE) {
776 NOTIFICATION_ERR("Can't init dbus %d", result);
780 cb_item = calloc(1, sizeof(result_cb_item));
782 return NOTIFICATION_ERROR_OUT_OF_MEMORY;
784 cb_item->result_cb = result_cb;
785 cb_item->data = user_data;
787 body = notification_ipc_make_gvariant_from_noti(noti);
789 NOTIFICATION_ERR("cannot make gvariant");
791 return NOTIFICATION_ERROR_OUT_OF_MEMORY;
794 result = _send_async_noti(body, cb_item, "update_noti");
795 NOTIFICATION_DBG("notification_ipc_request_update_async done [result: %d]", result);
797 if (result != NOTIFICATION_ERROR_NONE) {
802 g_variant_unref(body);
807 int notification_ipc_request_refresh(void)
810 GDBusMessage *reply = NULL;
813 result = _dbus_init();
814 if (result != NOTIFICATION_ERROR_NONE) {
815 NOTIFICATION_ERR("Can't init dbus %d", result);
819 body = g_variant_new("(i)", NOTIFICATION_OP_REFRESH);
820 result = _send_sync_noti(body, &reply, "refresh_noti");
823 g_object_unref(reply);
825 NOTIFICATION_ERR("notification_ipc_request_refresh done [result: %d]", result);
829 int notification_ipc_request_delete_single(notification_type_e type, char *pkgname, int priv_id)
833 GDBusMessage *reply = NULL;
835 GVariant *reply_body;
837 result = _dbus_init();
838 if (result != NOTIFICATION_ERROR_NONE) {
839 NOTIFICATION_ERR("Can't init dbus %d", result);
843 body = g_variant_new("(si)", pkgname, priv_id);
844 result = _send_sync_noti(body, &reply, "del_noti_single");
846 if (result == NOTIFICATION_ERROR_NONE) {
847 reply_body = g_dbus_message_get_body(reply);
848 g_variant_get(reply_body, "(i)", &id);
852 g_object_unref(reply);
854 NOTIFICATION_ERR("notification_ipc_request_delete_single done [result: %d]", result);
858 int notification_ipc_request_delete_multiple(notification_type_e type, char *pkgname)
863 GVariant *reply_body;
864 GDBusMessage *reply = NULL;
866 result = _dbus_init();
867 if (result != NOTIFICATION_ERROR_NONE) {
868 NOTIFICATION_ERR("Can't init dbus %d", result);
872 body = g_variant_new("(si)", pkgname, type);
873 result = _send_sync_noti(body, &reply, "del_noti_multiple");
875 if (result == NOTIFICATION_ERROR_NONE) {
876 reply_body = g_dbus_message_get_body(reply);
877 g_variant_get(reply_body, "(i)", &num_deleted);
878 NOTIFICATION_ERR("num deleted:%d", num_deleted);
882 g_object_unref(reply);
887 int notification_ipc_request_load_noti_by_tag(notification_h noti, const char *pkgname, const char *tag)
890 GDBusMessage *reply = NULL;
892 GVariant *reply_body;
895 result = _dbus_init();
896 if (result != NOTIFICATION_ERROR_NONE) {
897 NOTIFICATION_ERR("Can't init dbus %d", result);
901 body = g_variant_new("(ss)", pkgname, tag);
902 result = _send_sync_noti(body, &reply, "load_noti_by_tag");
904 if (result == NOTIFICATION_ERROR_NONE) {
905 reply_body = g_dbus_message_get_body(reply);
906 g_variant_get(reply_body, "(v)", ¬i_body);
908 notification_ipc_make_noti_from_gvariant(noti, noti_body);
909 g_variant_unref(noti_body);
915 g_object_unref(reply);
917 NOTIFICATION_DBG("notification_ipc_request_load_noti_by_tag done [result: %d]", result);
921 int notification_ipc_request_load_noti_by_priv_id(notification_h noti, const char *pkgname, int priv_id)
924 GDBusMessage *reply = NULL;
926 GVariant *reply_body;
929 result = _dbus_init();
930 if (result != NOTIFICATION_ERROR_NONE) {
931 NOTIFICATION_ERR("Can't init dbus %d", result);
935 body = g_variant_new("(si)", pkgname, priv_id);
936 result = _send_sync_noti(body, &reply, "load_noti_by_priv_id");
938 if (result == NOTIFICATION_ERROR_NONE) {
939 reply_body = g_dbus_message_get_body(reply);
940 g_variant_get(reply_body, "(v)", ¬i_body);
942 notification_ipc_make_noti_from_gvariant(noti, noti_body);
943 g_variant_unref(noti_body);
948 g_object_unref(reply);
950 NOTIFICATION_DBG("notification_ipc_request_load_noti_by_priv_id done [result: %d]", result);
954 int notification_ipc_request_get_count(notification_type_e type,
955 const char *pkgname, int group_id, int priv_id, int *count)
958 GDBusMessage *reply = NULL;
960 GVariant *reply_body;
963 result = _dbus_init();
964 if (result != NOTIFICATION_ERROR_NONE) {
965 NOTIFICATION_ERR("Can't init dbus %d", result);
969 body = g_variant_new("(isii)", type, pkgname, group_id, priv_id);
970 result = _send_sync_noti(body, &reply, "get_noti_count");
972 if (result == NOTIFICATION_ERROR_NONE) {
973 reply_body = g_dbus_message_get_body(reply);
974 g_variant_get(reply_body, "(i)", &re_count);
977 NOTIFICATION_DBG("noti count [%d]", re_count);
981 g_object_unref(reply);
983 NOTIFICATION_DBG("notification_ipc_request_get_count done [result: %d]", result);
987 int notification_ipc_request_load_noti_grouping_list(notification_type_e type, int count,
988 notification_list_h *list)
991 GDBusMessage *reply = NULL;
993 GVariant *reply_body;
999 result = _dbus_init();
1000 if (result != NOTIFICATION_ERROR_NONE) {
1001 NOTIFICATION_ERR("Can't init dbus %d", result);
1005 body = g_variant_new("(ii)", type, count);
1006 result = _send_sync_noti(body, &reply, "load_noti_grouping_list");
1008 if (result == NOTIFICATION_ERROR_NONE) {
1009 reply_body = g_dbus_message_get_body(reply);
1010 g_variant_get(reply_body, "(a(v))", &iter);
1012 while (g_variant_iter_loop(iter, "(v)", &iter_body)) {
1013 noti = notification_create(NOTIFICATION_TYPE_NOTI);
1014 g_variant_get(iter_body, "(v)", ¬i_body);
1015 notification_ipc_make_noti_from_gvariant(noti, noti_body);
1017 *list = notification_list_append(*list, noti);
1019 g_variant_iter_free(iter);
1023 g_object_unref(reply);
1025 NOTIFICATION_DBG("notification_ipc_request_load_noti_grouping_list done [result: %d]", result);
1029 int notification_ipc_request_load_noti_detail_list(const char *pkgname,
1033 notification_list_h *list)
1036 GDBusMessage *reply = NULL;
1038 GVariant *reply_body;
1039 GVariant *iter_body;
1041 notification_h noti;
1042 GVariant *noti_body;
1044 result = _dbus_init();
1045 if (result != NOTIFICATION_ERROR_NONE) {
1046 NOTIFICATION_ERR("Can't init dbus %d", result);
1050 body = g_variant_new("(siii)", pkgname, group_id, priv_id, count);
1051 result = _send_sync_noti(body, &reply, "load_noti_detail_list");
1053 if (result == NOTIFICATION_ERROR_NONE) {
1054 reply_body = g_dbus_message_get_body(reply);
1055 g_variant_get(reply_body, "(a(v))", &iter);
1057 while (g_variant_iter_loop(iter, "(v)", &iter_body)) {
1058 noti = notification_create(NOTIFICATION_TYPE_NOTI);
1059 g_variant_get(iter_body, "(v)", ¬i_body);
1060 notification_ipc_make_noti_from_gvariant(noti, noti_body);
1062 *list = notification_list_append(*list, noti);
1064 g_variant_iter_free(iter);
1068 g_object_unref(reply);
1070 NOTIFICATION_DBG("notification_ipc_request_load_noti_detail_list done [result: %d]", result);
1074 int notification_ipc_request_get_setting_array(
1075 notification_setting_h *setting_array,
1079 GDBusMessage *reply = NULL;
1080 GVariant *reply_body;
1081 GVariant *iter_body;
1084 notification_setting_h result_setting_array;
1085 notification_setting_h temp;
1088 result = _dbus_init();
1089 if (result != NOTIFICATION_ERROR_NONE) {
1090 NOTIFICATION_ERR("Can't init dbus %d", result);
1094 result = _send_sync_noti(NULL, &reply, "get_setting_array");
1096 if (result == NOTIFICATION_ERROR_NONE) {
1097 reply_body = g_dbus_message_get_body(reply);
1098 g_variant_get(reply_body, "(ia(v))", &setting_cnt, &iter);
1100 NOTIFICATION_DBG("get setting arr cnt: %d", setting_cnt);
1101 result_setting_array = (struct notification_setting *)malloc(sizeof(struct notification_setting) * setting_cnt);
1102 if (result_setting_array == NULL) {
1103 NOTIFICATION_ERR("malloc failed");
1104 g_object_unref(reply);
1105 g_variant_iter_free(iter);
1106 return NOTIFICATION_ERROR_OUT_OF_MEMORY;
1110 while (g_variant_iter_loop(iter, "(v)", &iter_body)) {
1111 temp = result_setting_array + setting_idx;
1112 notification_ipc_make_setting_from_gvariant(temp, iter_body);
1116 *count = setting_cnt;
1117 *setting_array = result_setting_array;
1118 g_variant_iter_free(iter);
1122 g_object_unref(reply);
1124 NOTIFICATION_DBG("notification_ipc_request_get_setting_array done [result: %d]", result);
1128 int notification_ipc_request_get_setting_by_package_name(
1129 const char *package_name, notification_setting_h *setting)
1132 GDBusMessage *reply = NULL;
1134 GVariant *reply_body;
1135 GVariant *setting_body;
1136 notification_setting_h result_setting;
1138 result = _dbus_init();
1139 if (result != NOTIFICATION_ERROR_NONE) {
1140 NOTIFICATION_ERR("Can't init dbus %d", result);
1144 body = g_variant_new("(s)", package_name);
1145 result = _send_sync_noti(body, &reply, "get_setting_by_package_name");
1147 if (result == NOTIFICATION_ERROR_NONE) {
1148 reply_body = g_dbus_message_get_body(reply);
1149 g_variant_get(reply_body, "(v)", &setting_body);
1151 result_setting = (struct notification_setting *)malloc(sizeof(struct notification_setting));
1152 if (result_setting == NULL) {
1153 NOTIFICATION_ERR("malloc failed");
1154 g_object_unref(reply);
1155 g_variant_unref(body);
1156 return NOTIFICATION_ERROR_OUT_OF_MEMORY;
1158 notification_ipc_make_setting_from_gvariant(result_setting, setting_body);
1160 *setting = result_setting;
1161 g_variant_unref(setting_body);
1165 g_object_unref(reply);
1167 NOTIFICATION_DBG("notification_ipc_request_get_setting_by_package_name done [result: %d]", result);
1171 int notification_ipc_request_load_system_setting(notification_system_setting_h *setting)
1174 GDBusMessage *reply = NULL;
1175 GVariant *setting_body;
1176 GVariant *reply_body;
1177 notification_system_setting_h result_setting;
1179 result = _dbus_init();
1180 if (result != NOTIFICATION_ERROR_NONE) {
1181 NOTIFICATION_ERR("Can't init dbus %d", result);
1185 result = _send_sync_noti(NULL, &reply, "load_system_setting");
1187 if (result == NOTIFICATION_ERROR_NONE) {
1188 reply_body = g_dbus_message_get_body(reply);
1189 g_variant_get(reply_body, "(v)", &setting_body);
1191 result_setting = (struct notification_system_setting *)malloc(sizeof(struct notification_system_setting));
1192 if (result_setting == NULL) {
1193 NOTIFICATION_ERR("malloc failed");
1194 g_object_unref(reply);
1195 return NOTIFICATION_ERROR_OUT_OF_MEMORY;
1197 notification_ipc_make_system_setting_from_gvariant(result_setting, setting_body);
1199 *setting = result_setting;
1200 g_variant_unref(setting_body);
1204 g_object_unref(reply);
1206 NOTIFICATION_DBG("notification_ipc_request_load_system_setting done [result: %d]", result);
1210 int notification_ipc_update_setting(notification_setting_h setting)
1213 GDBusMessage *reply = NULL;
1216 result = _dbus_init();
1217 if (result != NOTIFICATION_ERROR_NONE) {
1218 NOTIFICATION_ERR("Can't init dbus %d", result);
1222 body = g_variant_new("(siii)",
1223 setting->package_name,
1224 (int)(setting->allow_to_notify),
1225 (int)(setting->do_not_disturb_except),
1226 (int)(setting->visibility_class));
1228 result = _send_sync_noti(body, &reply, "update_noti_setting");
1231 g_object_unref(reply);
1233 NOTIFICATION_DBG("notification_ipc_update_setting done [result: %d]", result);
1237 int notification_ipc_update_system_setting(notification_system_setting_h system_setting)
1240 GDBusMessage *reply = NULL;
1243 result = _dbus_init();
1244 if (result != NOTIFICATION_ERROR_NONE) {
1245 NOTIFICATION_ERR("Can't init dbus %d", result);
1249 body = g_variant_new("(ii)",
1250 (int)(system_setting->do_not_disturb),
1251 (int)(system_setting->visibility_class));
1253 result = _send_sync_noti(body, &reply, "update_noti_sys_setting");
1256 g_object_unref(reply);
1258 NOTIFICATION_DBG("notification_ipc_update_system_setting done [result: %d]", result);
1262 int notification_ipc_noti_setting_property_set(const char *pkgname, const char *property, const char *value)
1265 GDBusMessage *reply = NULL;
1268 result = _dbus_init();
1269 if (result != NOTIFICATION_ERROR_NONE) {
1270 NOTIFICATION_ERR("Can't init dbus %d", result);
1273 body = g_variant_new("(sss)", pkgname, property, value);
1275 result = _send_sync_noti(body, &reply, "set_noti_property");
1278 g_object_unref(reply);
1280 NOTIFICATION_DBG("notification_ipc_noti_setting_property_set done [result: %d]", result);
1284 int notification_ipc_noti_setting_property_get(const char *pkgname, const char *property, char **value)
1287 GDBusMessage *reply = NULL;
1289 GVariant *reply_body = NULL;
1292 result = _dbus_init();
1294 if (result != NOTIFICATION_ERROR_NONE) {
1295 NOTIFICATION_ERR("Can't init dbus %d", result);
1299 body = g_variant_new("(ss)", pkgname, property);
1300 result = _send_sync_noti(body, &reply, "get_noti_property");
1302 if (result == NOTIFICATION_ERROR_NONE) {
1303 reply_body = g_dbus_message_get_body(reply);
1304 g_variant_get(body, "(s)", &ret_val);
1306 if (ret_val != NULL) {
1307 *value = g_strdup(ret_val);
1313 g_object_unref(reply);
1315 NOTIFICATION_DBG("notification_ipc_noti_setting_property_get done [result: %d]", result);
1319 EXPORT_API GVariant *notification_ipc_make_gvariant_from_noti(notification_h noti)
1321 NOTIFICATION_DBG("make gvariant from noti");
1323 int b_encode_len = 0;
1324 bundle_raw *args = NULL;
1325 bundle_raw *group_args = NULL;
1326 bundle_raw *b_image_path = NULL;
1327 bundle_raw *b_execute_option = NULL;
1328 bundle_raw *b_service_responding = NULL;
1329 bundle_raw *b_service_single_launch = NULL;
1330 bundle_raw *b_service_multi_launch = NULL;
1331 bundle_raw *b_event_handler[NOTIFICATION_EVENT_TYPE_MAX] = {NULL, };
1332 bundle_raw *b_text = NULL;
1333 bundle_raw *b_key = NULL;
1334 bundle_raw *b_format_args = NULL;
1335 GVariant *body = NULL;
1336 GVariant *result_body = NULL;
1337 GVariantBuilder builder;
1339 g_variant_builder_init(&builder, G_VARIANT_TYPE("a{iv}"));
1340 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_NOTI_TYPE, g_variant_new_int32(noti->type));
1341 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_LAYOUT, g_variant_new_int32(noti->layout));
1342 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_GROUP_ID, g_variant_new_int32(noti->group_id));
1343 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_INTERNAL_GROUP_ID, g_variant_new_int32(noti->internal_group_id));
1344 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_PRIV_ID, g_variant_new_int32(noti->priv_id));
1345 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_CALLER_PKGNAME, g_variant_new_string((const gchar *)noti->caller_pkgname));
1346 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_DISPLAY_APPLIST, g_variant_new_int32(noti->display_applist));
1349 bundle_encode(noti->args, (bundle_raw **)&args, NULL);
1350 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_ARGS, g_variant_new_string((const gchar *)args));
1353 bundle_free_encoded_rawdata(&args);
1356 if (noti->group_args) {
1357 bundle_encode(noti->group_args, (bundle_raw **)&group_args,
1359 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_GROUP_ARGS, g_variant_new_string((const gchar *)group_args));
1362 bundle_free_encoded_rawdata(&group_args);
1365 if (noti->b_execute_option) {
1366 bundle_encode(noti->b_execute_option,
1367 (bundle_raw **)&b_execute_option, &b_encode_len);
1368 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_EXECUTE_OPTION, g_variant_new_string((const gchar *)b_execute_option));
1370 if (b_execute_option)
1371 bundle_free_encoded_rawdata(&b_execute_option);
1374 if (noti->b_service_responding) {
1375 bundle_encode(noti->b_service_responding,
1376 (bundle_raw **)&b_service_responding, &b_encode_len);
1377 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_SERVICE_RESPONDING, g_variant_new_string((const gchar *)b_service_responding));
1379 if (b_service_responding)
1380 bundle_free_encoded_rawdata(&b_service_responding);
1383 if (noti->b_service_single_launch) {
1384 bundle_encode(noti->b_service_single_launch,
1385 (bundle_raw **)&b_service_single_launch, &b_encode_len);
1386 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_SERVICE_SINGLE_LAUNCH, g_variant_new_string((const gchar *)b_service_single_launch));
1388 if (b_service_single_launch)
1389 bundle_free_encoded_rawdata(&b_service_single_launch);
1392 if (noti->b_service_multi_launch) {
1393 bundle_encode(noti->b_service_multi_launch,
1394 (bundle_raw **)&b_service_multi_launch, &b_encode_len);
1395 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_SERVICE_MULTI_LAUNCH, g_variant_new_string((const gchar *)b_service_multi_launch));
1397 if (b_service_multi_launch)
1398 bundle_free_encoded_rawdata(&b_service_multi_launch);
1401 for (i = 0; i < NOTIFICATION_EVENT_TYPE_MAX; i++) {
1402 if (noti->b_event_handler[i]) {
1403 bundle_encode(noti->b_event_handler[i],
1404 (bundle_raw **)&b_event_handler[i], &b_encode_len);
1405 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_BUTTON1_EVENT + i, g_variant_new_string((const gchar *)b_event_handler[i]));
1407 if (b_event_handler[i])
1408 bundle_free_encoded_rawdata(&b_event_handler[i]);
1412 if (noti->launch_pkgname)
1413 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_LAUNCH_PKGNAME, g_variant_new_string((const gchar *)noti->launch_pkgname));
1415 if (noti->domain != NULL)
1416 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_DOMAIN, g_variant_new_string((const gchar *)noti->domain));
1418 if (noti->dir != NULL)
1419 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_DIR, g_variant_new_string((const gchar *)noti->dir));
1422 bundle_encode(noti->b_text, (bundle_raw **)&b_text, &b_encode_len);
1423 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_TEXT, g_variant_new_string((const gchar *)b_text));
1426 bundle_free_encoded_rawdata(&b_text);
1430 bundle_encode(noti->b_key, (bundle_raw **)&b_key, &b_encode_len);
1431 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_KEY, g_variant_new_string((const gchar *)b_key));
1434 bundle_free_encoded_rawdata(&b_key);
1437 if (noti->b_format_args) {
1438 bundle_encode(noti->b_format_args,
1439 (bundle_raw **)&b_format_args, &b_encode_len);
1440 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_FORMAT_ARGS, g_variant_new_string((const gchar *)b_format_args));
1443 bundle_free_encoded_rawdata(&b_format_args);
1446 if (noti->num_format_args != 0)
1447 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_NUM_FORMAT_ARGS, g_variant_new_int32(noti->num_format_args));
1449 if (noti->b_image_path) {
1450 bundle_encode(noti->b_image_path,
1451 (bundle_raw **)&b_image_path, &b_encode_len);
1452 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_IMAGE_PATH, g_variant_new_string((const gchar *)b_image_path));
1455 bundle_free_encoded_rawdata(&b_image_path);
1458 if (noti->sound_type != NOTIFICATION_SOUND_TYPE_NONE)
1459 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_SOUND_TYPE, g_variant_new_int32(noti->sound_type));
1461 if (noti->sound_path)
1462 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_SOUND_PATH, g_variant_new_string((const gchar *)noti->sound_path));
1464 if (noti->vibration_type != NOTIFICATION_VIBRATION_TYPE_NONE)
1465 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_VIBRATION_TYPE, g_variant_new_int32(noti->vibration_type));
1467 if (noti->vibration_path)
1468 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_VIBRATION_PATH, g_variant_new_string((const gchar *)noti->vibration_path));
1470 if (noti->led_operation != NOTIFICATION_LED_OP_OFF)
1471 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_LED_OPERATION, g_variant_new_int32(noti->led_operation));
1473 if (noti->led_argb != 0)
1474 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_LED_ARGB, g_variant_new_int32(noti->led_argb));
1476 if (noti->led_on_ms != 0)
1477 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_LED_ON_MS, g_variant_new_int32(noti->led_on_ms));
1479 if (noti->led_off_ms != 0)
1480 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_LED_OFF_MS, g_variant_new_int32(noti->led_off_ms));
1482 if (noti->time != 0)
1483 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_TIME, g_variant_new_int32(noti->time));
1485 if (noti->insert_time != 0)
1486 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_INSERT_TIME, g_variant_new_int32(noti->insert_time));
1488 if (noti->flags_for_property != 0)
1489 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_FLAGS_FOR_PROPERTY, g_variant_new_int32(noti->flags_for_property));
1491 if (noti->progress_size != 0.0)
1492 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_PROGRESS_SIZE, g_variant_new_double(noti->progress_size));
1494 if (noti->progress_percentage != 0.0)
1495 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_PROGRESS_PERCENTAGE, g_variant_new_double(noti->progress_percentage));
1497 if (noti->app_icon_path != NULL)
1498 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_APP_ICON_PATH, g_variant_new_string((const gchar *)noti->app_icon_path));
1499 if (noti->app_name != NULL)
1500 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_APP_NAME, g_variant_new_string((const gchar *)noti->app_name));
1501 if (noti->temp_title != NULL)
1502 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_TEMP_TITLE, g_variant_new_string((const gchar *)noti->temp_title));
1503 if (noti->temp_content != NULL)
1504 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_TEMP_CONTENT, g_variant_new_string((const gchar *)noti->temp_content));
1505 if (noti->tag != NULL)
1506 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_TAG, g_variant_new_string((const gchar *)noti->tag));
1508 if (noti->ongoing_flag != 0)
1509 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_ONGOING_FLAG, g_variant_new_int32(noti->ongoing_flag));
1510 if (noti->auto_remove != 0)
1511 g_variant_builder_add(&builder, "{iv}", NOTIFICATION_DATA_TYPE_AUTO_REMOVE, g_variant_new_int32(noti->auto_remove));
1513 result_body = g_variant_builder_end(&builder);
1514 body = g_variant_new("(v)", result_body);
1519 static gboolean _variant_to_int_dict(GHashTable **dict, GVariant *variant) {
1526 *dict = g_hash_table_new_full(g_int_hash, g_int_equal, g_free, (GDestroyNotify)g_variant_unref);
1530 g_variant_iter_init(&iter, variant);
1531 while (g_variant_iter_next(&iter, "{iv}", &key, &value)) {
1532 hash_key = (int *)calloc(sizeof(int), 1);
1533 if (hash_key == NULL) {
1534 g_hash_table_remove_all(*dict);
1538 g_hash_table_insert(*dict, (gpointer)hash_key, value);
1543 static gboolean _variant_dict_lookup(GHashTable *dict,
1545 const gchar *format_string,
1551 value = g_hash_table_lookup(dict, (gpointer)&key);
1553 if (value == NULL || !g_variant_check_format_string(value, format_string, FALSE))
1556 va_start(ap, format_string);
1557 g_variant_get_va(value, format_string, NULL, &ap);
1564 * functions creating notification packet
1566 EXPORT_API int notification_ipc_make_noti_from_gvariant(notification_h noti,
1567 GVariant *variant) {
1569 NOTIFICATION_DBG("make noti from GVariant");
1573 char *caller_pkgname = NULL;
1574 char *launch_pkgname = NULL;
1575 bundle_raw *args = NULL;
1576 bundle_raw *group_args = NULL;
1577 bundle_raw *b_execute_option = NULL;
1578 bundle_raw *b_service_responding = NULL;
1579 bundle_raw *b_service_single_launch = NULL;
1580 bundle_raw *b_service_multi_launch = NULL;
1581 bundle_raw *b_event_handler[NOTIFICATION_EVENT_TYPE_MAX] = { NULL, };
1582 char *domain = NULL;
1584 bundle_raw *b_text = NULL;
1585 bundle_raw *b_key = NULL;
1586 bundle_raw *b_format_args = NULL;
1587 bundle_raw *b_image_path = NULL;
1588 char *sound_path = NULL;
1589 char *vibration_path = NULL;
1590 char *app_icon_path = NULL;
1591 char *app_name = NULL;
1592 char *temp_title = NULL;
1593 char *temp_content = NULL;
1597 NOTIFICATION_ERR("invalid data noti NULL");
1598 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1601 if (variant == NULL) {
1602 NOTIFICATION_ERR("invalid data variant NULL");
1603 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1606 if (!_variant_to_int_dict(&dict, variant))
1607 return NOTIFICATION_ERROR_OUT_OF_MEMORY;
1609 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_NOTI_TYPE, "i", ¬i->type);
1610 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_LAYOUT, "i", ¬i->layout);
1611 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_GROUP_ID, "i", ¬i->group_id);
1612 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_INTERNAL_GROUP_ID, "i", ¬i->internal_group_id);
1613 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_PRIV_ID, "i", ¬i->priv_id);
1614 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_CALLER_PKGNAME, "&s", &caller_pkgname);
1615 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_LAUNCH_PKGNAME, "&s", &launch_pkgname);
1616 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_ARGS, "&s", &args);
1617 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_GROUP_ARGS, "&s", &group_args);
1618 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_EXECUTE_OPTION, "&s", &b_execute_option);
1619 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_SERVICE_RESPONDING, "&s", &b_service_responding);
1620 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_SERVICE_SINGLE_LAUNCH, "&s", &b_service_single_launch);
1621 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_SERVICE_MULTI_LAUNCH, "&s", &b_service_multi_launch);
1622 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_BUTTON1_EVENT, "&s", ¬i->b_event_handler[NOTIFICATION_EVENT_TYPE_CLICK_ON_BUTTON_1]);
1623 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_BUTTON2_EVENT, "&s", ¬i->b_event_handler[NOTIFICATION_EVENT_TYPE_CLICK_ON_BUTTON_2]);
1624 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_BUTTON3_EVENT, "&s", ¬i->b_event_handler[NOTIFICATION_EVENT_TYPE_CLICK_ON_BUTTON_3]);
1625 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_BUTTON4_EVENT, "&s", ¬i->b_event_handler[NOTIFICATION_EVENT_TYPE_CLICK_ON_BUTTON_4]);
1626 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_BUTTON5_EVENT, "&s", ¬i->b_event_handler[NOTIFICATION_EVENT_TYPE_CLICK_ON_BUTTON_5]);
1627 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_BUTTON6_EVENT, "&s", ¬i->b_event_handler[NOTIFICATION_EVENT_TYPE_CLICK_ON_BUTTON_6]);
1628 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_ICON_EVENT, "&s", ¬i->b_event_handler[NOTIFICATION_EVENT_TYPE_CLICK_ON_ICON]);
1629 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_THUMBNAIL_EVENT, "&s", ¬i->b_event_handler[NOTIFICATION_EVENT_TYPE_CLICK_ON_THUMBNAIL]);
1630 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_DOMAIN, "&s", &domain);
1631 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_DIR, "&s", &dir);
1632 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_TEXT, "&s", &b_text);
1633 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_KEY, "&s", &b_key);
1634 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_FORMAT_ARGS, "&s", &b_format_args);
1635 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_NUM_FORMAT_ARGS, "i", ¬i->num_format_args);
1636 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_IMAGE_PATH, "&s", &b_image_path);
1637 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_SOUND_TYPE, "i", ¬i->sound_type);
1638 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_SOUND_PATH, "&s", &sound_path);
1639 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_VIBRATION_TYPE, "i", ¬i->vibration_type);
1640 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_VIBRATION_PATH, "&s", &vibration_path);
1641 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_LED_OPERATION, "i", ¬i->led_operation);
1642 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_LED_ARGB, "i", ¬i->led_argb);
1643 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_LED_ON_MS, "i", ¬i->led_on_ms);
1644 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_LED_OFF_MS, "i", ¬i->led_off_ms);
1645 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_TIME, "i", ¬i->time);
1646 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_INSERT_TIME, "i", ¬i->insert_time);
1647 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_FLAGS_FOR_PROPERTY, "i", ¬i->flags_for_property);
1648 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_DISPLAY_APPLIST, "i", ¬i->display_applist);
1649 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_PROGRESS_SIZE, "d", ¬i->progress_size);
1650 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_PROGRESS_PERCENTAGE, "d", ¬i->progress_percentage);
1651 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_APP_ICON_PATH, "&s", &app_icon_path);
1652 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_APP_NAME, "&s", &app_name);
1653 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_TEMP_TITLE, "&s", &temp_title);
1654 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_TEMP_CONTENT, "&s", &temp_content);
1655 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_TAG, "&s", &tag);
1656 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_ONGOING_FLAG, "i", ¬i->ongoing_flag);
1657 _variant_dict_lookup(dict, NOTIFICATION_DATA_TYPE_AUTO_REMOVE, "i", ¬i->auto_remove);
1659 noti->caller_pkgname = _dup_string(caller_pkgname);
1660 noti->launch_pkgname = _dup_string(launch_pkgname);
1661 noti->args = _create_bundle_from_bundle_raw(args);
1662 noti->group_args = _create_bundle_from_bundle_raw(group_args);
1663 noti->b_execute_option = _create_bundle_from_bundle_raw(b_execute_option);
1664 noti->b_service_responding = _create_bundle_from_bundle_raw(
1665 b_service_responding);
1666 noti->b_service_single_launch = _create_bundle_from_bundle_raw(
1667 b_service_single_launch);
1668 noti->b_service_multi_launch = _create_bundle_from_bundle_raw(
1669 b_service_multi_launch);
1670 for (i = 0; i < NOTIFICATION_EVENT_TYPE_MAX; i++) {
1671 noti->b_event_handler[i] = _create_bundle_from_bundle_raw(
1672 b_event_handler[i]);
1674 noti->domain = _dup_string(domain);
1675 noti->dir = _dup_string(dir);
1676 noti->b_text = _create_bundle_from_bundle_raw(b_text);
1677 noti->b_key = _create_bundle_from_bundle_raw(b_key);
1678 noti->b_format_args = _create_bundle_from_bundle_raw(b_format_args);
1679 noti->b_image_path = _create_bundle_from_bundle_raw(b_image_path);
1680 noti->sound_path = _dup_string(sound_path);
1681 noti->vibration_path = _dup_string(vibration_path);
1682 noti->app_icon_path = _dup_string(app_icon_path);
1683 noti->app_name = _dup_string(app_name);
1684 noti->temp_title = _dup_string(temp_title);
1685 noti->temp_content = _dup_string(temp_content);
1686 noti->tag = _dup_string(tag);
1688 g_hash_table_remove_all(dict);
1690 return NOTIFICATION_ERROR_NONE;
1693 EXPORT_API GVariant *notification_ipc_make_gvariant_from_system_setting(struct notification_system_setting *noti_setting)
1695 GVariant *body = NULL;
1696 body = g_variant_new("(ii)",
1697 noti_setting->do_not_disturb,
1698 noti_setting->visibility_class);
1702 EXPORT_API int notification_ipc_make_system_setting_from_gvariant(struct notification_system_setting *noti_setting,
1706 int visibility_class;
1708 if (noti_setting == NULL) {
1709 NOTIFICATION_ERR("invalid data");
1710 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1712 g_variant_get(variant,
1717 NOTIFICATION_DBG("system setting #### %d, %d",
1718 do_not_disturb, visibility_class);
1720 noti_setting->do_not_disturb = do_not_disturb;
1721 noti_setting->visibility_class = visibility_class;
1723 NOTIFICATION_DBG("system setting2 #### %d, %d",
1724 noti_setting->do_not_disturb, noti_setting->visibility_class);
1726 return NOTIFICATION_ERROR_NONE;
1729 EXPORT_API GVariant *notification_ipc_make_gvariant_from_setting(struct notification_setting *noti_setting)
1731 GVariant *body = NULL;
1733 body = g_variant_new("(siii)",
1734 noti_setting->package_name,
1735 noti_setting->allow_to_notify,
1736 noti_setting->do_not_disturb_except,
1737 noti_setting->visibility_class);
1742 EXPORT_API int notification_ipc_make_setting_from_gvariant(struct notification_setting *noti_setting,
1745 NOTIFICATION_DBG("notification_ipc_make_setting_from_gvariant !!!!");
1747 int allow_to_notify;
1748 int do_not_disturb_except;
1749 int visibility_class;
1751 if (noti_setting == NULL || variant == NULL) {
1752 NOTIFICATION_ERR("invalid data");
1753 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1755 g_variant_get(variant,
1759 &do_not_disturb_except,
1762 NOTIFICATION_DBG("setting from variant %s !!", pkgname);
1764 noti_setting->package_name = _dup_string(pkgname);
1765 noti_setting->allow_to_notify = allow_to_notify;
1766 noti_setting->do_not_disturb_except = do_not_disturb_except;
1767 noti_setting->visibility_class = visibility_class;
1769 NOTIFICATION_DBG("setting from variant %s, %s",
1770 noti_setting->package_name, pkgname);
1772 return NOTIFICATION_ERROR_NONE;
1775 static int _send_service_register()
1777 NOTIFICATION_DBG("service register");
1778 GDBusMessage *reply = NULL;
1781 result = _send_sync_noti(NULL, &reply, "noti_service_register");
1784 g_object_unref(reply);
1786 NOTIFICATION_ERR("_send_service_register done = %s, result = %d", _bus_name, result);
1790 static int _ipc_monitor_register(void)
1792 NOTIFICATION_ERR("register a service\n");
1794 return _send_service_register();
1797 static void _on_name_appeared(GDBusConnection *connection,
1799 const gchar *name_owner,
1802 NOTIFICATION_DBG("name appeared : %s", name);
1803 is_master_started = 1;
1804 _ipc_monitor_register();
1806 /* TODO: dbus activation isn't enough ? */
1807 _do_deffered_task();
1810 static void _on_name_vanished(GDBusConnection *connection,
1814 NOTIFICATION_DBG("name vanished : %s", name);
1815 is_master_started = 0;
1818 int notification_ipc_monitor_init(void)
1823 if (ret != NOTIFICATION_ERROR_NONE) {
1824 NOTIFICATION_ERR("Can't init dbus %d", ret);
1828 ret = _dbus_signal_init();
1829 if (ret != NOTIFICATION_ERROR_NONE) {
1830 NOTIFICATION_ERR("Can't signal_init %d", ret);
1834 ret = _ipc_monitor_register();
1835 if (ret != NOTIFICATION_ERROR_NONE) {
1836 NOTIFICATION_ERR("Can't init ipc_monitor_register %d", ret);
1840 if (provider_monitor_id == 0) {
1841 provider_monitor_id = g_bus_watch_name_on_connection(
1844 G_BUS_NAME_WATCHER_FLAGS_NONE,
1850 if (provider_monitor_id == 0) {
1851 g_dbus_connection_signal_unsubscribe(_gdbus_conn, monitor_id);
1853 NOTIFICATION_ERR("watch on name fail");
1854 return NOTIFICATION_ERROR_IO_ERROR;
1858 return NOTIFICATION_ERROR_NONE;
1861 static int _ipc_monitor_deregister(void)
1863 if (provider_monitor_id) {
1864 g_bus_unwatch_name(provider_monitor_id);
1865 provider_monitor_id = 0;
1869 g_dbus_connection_signal_unsubscribe(_gdbus_conn, monitor_id);
1873 return NOTIFICATION_ERROR_NONE;
1876 int notification_ipc_monitor_fini(void)
1878 return _ipc_monitor_deregister();