2 * Copyright (c) 2000 - 2016 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.
23 #include <dbus/dbus.h>
24 #include <dbus/dbus-glib-lowlevel.h>
28 #include <app_control_internal.h>
32 #include <vconf-keys.h>
35 #include <notification.h>
36 #include <notification_list.h>
37 #include <notification_debug.h>
38 #include <notification_private.h>
39 #include <notification_noti.h>
40 #include <notification_ongoing.h>
41 #include <notification_group.h>
42 #include <notification_ipc.h>
43 #include <notification_internal.h>
45 typedef struct _notification_cb_info notification_cb_info_s;
46 typedef struct _notification_event_cb_info notification_event_cb_info_s;
48 typedef enum __notification_cb_type {
49 NOTIFICATION_CB_NORMAL = 1,
50 NOTIFICATION_CB_DETAILED,
51 } _notification_cb_type_e;
53 struct _notification_cb_info {
54 _notification_cb_type_e cb_type;
55 void (*changed_cb) (void *data, notification_type_e type);
56 void (*detailed_changed_cb) (void *data, notification_type_e type, notification_op *op_list, int num_op);
60 struct _notification_event_cb_info {
66 static GHashTable *_noti_cb_hash = NULL;
67 static GList *__noti_event_cb_list = NULL;
70 static void __free_changed_cb_info(gpointer data)
72 notification_cb_info_s *noti_cb_info = (notification_cb_info_s *)data;
78 void notification_call_changed_cb_for_uid(notification_op *op_list, int op_num, uid_t uid)
80 notification_type_e type = 0;
81 GList *noti_cb_list = NULL;
82 notification_cb_info_s *noti_cb_info = NULL;
84 if (_noti_cb_hash == NULL)
87 noti_cb_list = (GList *)g_hash_table_lookup(_noti_cb_hash, GUINT_TO_POINTER(uid));
89 if (noti_cb_list == NULL)
92 if (op_list == NULL) {
93 NOTIFICATION_ERR("invalid data");
97 noti_cb_list = g_list_first(noti_cb_list);
98 notification_get_type(op_list->noti, &type);
100 for (; noti_cb_list != NULL; noti_cb_list = noti_cb_list->next) {
101 noti_cb_info = noti_cb_list->data;
103 if (noti_cb_info->cb_type == NOTIFICATION_CB_NORMAL && noti_cb_info->changed_cb) {
104 noti_cb_info->changed_cb(noti_cb_info->data, type);
106 if (noti_cb_info->cb_type == NOTIFICATION_CB_DETAILED && noti_cb_info->detailed_changed_cb) {
107 noti_cb_info->detailed_changed_cb(noti_cb_info->data,
108 type, op_list, op_num);
113 static gint __priv_id_compare(gconstpointer a, gconstpointer b)
115 const notification_event_cb_info_s *info = NULL;
120 info = (notification_event_cb_info_s *)a;
122 if (info->priv_id == GPOINTER_TO_UINT(b))
128 void notification_call_event_handler_cb(notification_h noti, int event_type)
133 notification_event_cb_info_s *info;
135 if (__noti_event_cb_list == NULL)
138 ret = notification_get_id(noti, NULL, &priv_id);
139 if (ret != NOTIFICATION_ERROR_NONE)
142 __noti_event_cb_list = g_list_first(__noti_event_cb_list);
143 find_list = g_list_find_custom(__noti_event_cb_list, GUINT_TO_POINTER(priv_id),
144 (GCompareFunc)__priv_id_compare);
145 if (find_list == NULL)
148 info = g_list_nth_data(find_list, 0);
149 info->cb(noti, event_type, info->userdata);
152 void notification_delete_event_handler_cb(int priv_id)
155 notification_event_cb_info_s *info = NULL;
157 if (__noti_event_cb_list == NULL)
160 __noti_event_cb_list = g_list_first(__noti_event_cb_list);
161 delete_list = g_list_find_custom(__noti_event_cb_list, GUINT_TO_POINTER(priv_id),
162 (GCompareFunc)__priv_id_compare);
164 if (delete_list == NULL)
167 info = g_list_nth_data(delete_list, 0);
168 __noti_event_cb_list = g_list_remove(g_list_first(__noti_event_cb_list), info);
173 if (__noti_event_cb_list == NULL)
174 notification_ipc_event_monitor_fini();
177 EXPORT_API int notification_add_deferred_task(
178 void (*deferred_task_cb)(void *data), void *user_data)
180 if (deferred_task_cb == NULL)
181 return NOTIFICATION_ERROR_INVALID_PARAMETER;
183 return notification_ipc_add_deffered_task(deferred_task_cb, user_data);
186 EXPORT_API int notification_del_deferred_task(
187 void (*deferred_task_cb)(void *data))
189 if (deferred_task_cb == NULL)
190 return NOTIFICATION_ERROR_INVALID_PARAMETER;
192 return notification_ipc_del_deffered_task(deferred_task_cb);
195 EXPORT_API int notification_resister_changed_cb_for_uid(
196 void (*changed_cb)(void *data, notification_type_e type),
197 void *user_data, uid_t uid)
199 GList *noti_cb_list = NULL;
200 notification_cb_info_s *noti_cb_info_new = NULL;
202 if (changed_cb == NULL)
203 return NOTIFICATION_ERROR_INVALID_PARAMETER;
205 if (notification_ipc_monitor_init(uid) != NOTIFICATION_ERROR_NONE)
206 return NOTIFICATION_ERROR_IO_ERROR;
208 if (_noti_cb_hash == NULL)
209 _noti_cb_hash = g_hash_table_new(g_direct_hash, g_direct_equal);
211 noti_cb_info_new = (notification_cb_info_s *)malloc(sizeof(notification_cb_info_s));
212 if (noti_cb_info_new == NULL) {
213 NOTIFICATION_ERR("malloc failed");
214 return NOTIFICATION_ERROR_OUT_OF_MEMORY;
217 noti_cb_info_new->cb_type = NOTIFICATION_CB_NORMAL;
218 noti_cb_info_new->changed_cb = changed_cb;
219 noti_cb_info_new->detailed_changed_cb = NULL;
220 noti_cb_info_new->data = user_data;
222 noti_cb_list = g_hash_table_lookup(_noti_cb_hash, GUINT_TO_POINTER(uid));
224 if (noti_cb_list == NULL) {
225 noti_cb_list = g_list_append(noti_cb_list, noti_cb_info_new);
226 g_hash_table_insert(_noti_cb_hash, GUINT_TO_POINTER(uid), noti_cb_list);
228 noti_cb_list = g_list_append(noti_cb_list, noti_cb_info_new);
231 return NOTIFICATION_ERROR_NONE;
234 EXPORT_API int notification_resister_changed_cb(
235 void (*changed_cb)(void *data, notification_type_e type),
238 return notification_resister_changed_cb_for_uid(changed_cb, user_data, getuid());
241 static gint _noti_changed_compare(gconstpointer a, gconstpointer b)
243 const struct _notification_cb_info *info = NULL;
247 info = (notification_cb_info_s *)a;
249 if (info->changed_cb == b)
255 EXPORT_API int notification_unresister_changed_cb_for_uid(
256 void (*changed_cb)(void *data, notification_type_e type), uid_t uid)
258 notification_cb_info_s *noti_cb_info = NULL;
259 GList *noti_cb_list = NULL;
260 GList *delete_cb_list = NULL;
262 if (changed_cb == NULL)
263 return NOTIFICATION_ERROR_INVALID_PARAMETER;
265 if (_noti_cb_hash == NULL)
266 return NOTIFICATION_ERROR_INVALID_PARAMETER;
268 noti_cb_list = (GList *)g_hash_table_lookup(_noti_cb_hash, GUINT_TO_POINTER(uid));
270 if (noti_cb_list == NULL)
271 return NOTIFICATION_ERROR_INVALID_PARAMETER;
273 noti_cb_list = g_list_first(noti_cb_list);
274 delete_cb_list = g_list_find_custom(noti_cb_list, (gconstpointer)changed_cb,
275 _noti_changed_compare);
277 if (delete_cb_list) {
278 noti_cb_info = g_list_nth_data(delete_cb_list, 0);
279 noti_cb_list = g_list_delete_link(noti_cb_list, delete_cb_list);
280 __free_changed_cb_info(noti_cb_info);
282 if (noti_cb_list == NULL) {
283 g_hash_table_steal(_noti_cb_hash, GUINT_TO_POINTER(uid));
285 noti_cb_list = g_list_first(noti_cb_list);
286 g_hash_table_replace(_noti_cb_hash, GUINT_TO_POINTER(uid), noti_cb_list);
290 return NOTIFICATION_ERROR_INVALID_PARAMETER;
293 if (g_hash_table_size(_noti_cb_hash) == 0)
294 notification_ipc_monitor_fini();
296 return NOTIFICATION_ERROR_NONE;
299 EXPORT_API int notification_unresister_changed_cb(
300 void (*changed_cb)(void *data, notification_type_e type))
302 return notification_unresister_changed_cb_for_uid(changed_cb, getuid());
305 EXPORT_API int notification_update_progress(notification_h noti,
309 char *caller_pkgname = NULL;
310 int input_priv_id = 0;
312 double input_progress = 0.0;
314 if (priv_id <= NOTIFICATION_PRIV_ID_NONE) {
316 return NOTIFICATION_ERROR_INVALID_PARAMETER;
318 input_priv_id = noti->priv_id;
321 input_priv_id = priv_id;
325 caller_pkgname = notification_get_pkgname_by_pid();
327 caller_pkgname = strdup(noti->caller_pkgname);
330 input_progress = 0.0;
331 else if (progress > 1.0)
332 input_progress = 1.0;
334 input_progress = progress;
336 ret = notification_ongoing_update_progress(caller_pkgname, input_priv_id,
340 free(caller_pkgname);
345 EXPORT_API int notification_update_size(notification_h noti,
349 char *caller_pkgname = NULL;
350 int input_priv_id = 0;
352 double input_size = 0.0;
354 if (priv_id <= NOTIFICATION_PRIV_ID_NONE) {
356 return NOTIFICATION_ERROR_INVALID_PARAMETER;
358 input_priv_id = noti->priv_id;
360 input_priv_id = priv_id;
364 caller_pkgname = notification_get_pkgname_by_pid();
366 caller_pkgname = strdup(noti->caller_pkgname);
373 ret = notification_ongoing_update_size(caller_pkgname, input_priv_id,
377 free(caller_pkgname);
382 EXPORT_API int notification_update_content(notification_h noti,
386 char *caller_pkgname = NULL;
387 int input_priv_id = 0;
390 if (priv_id <= NOTIFICATION_PRIV_ID_NONE) {
392 return NOTIFICATION_ERROR_INVALID_PARAMETER;
394 input_priv_id = noti->priv_id;
397 input_priv_id = priv_id;
401 caller_pkgname = notification_get_pkgname_by_pid();
403 caller_pkgname = strdup(noti->caller_pkgname);
405 ret = notification_ongoing_update_content(caller_pkgname, input_priv_id,
409 free(caller_pkgname);
414 /* notification_set_icon will be removed */
415 /* LCOV_EXCL_START */
416 EXPORT_API int notification_set_icon(notification_h noti,
417 const char *icon_path)
419 return notification_set_image(noti, NOTIFICATION_IMAGE_TYPE_ICON, icon_path);
423 /* notification_get_icon will be removed */
424 /* LCOV_EXCL_START */
425 EXPORT_API int notification_get_icon(notification_h noti,
428 int ret_err = NOTIFICATION_ERROR_NONE;
429 char *ret_image_path = NULL;
431 ret_err = notification_get_image(noti, NOTIFICATION_IMAGE_TYPE_ICON,
434 if (ret_err == NOTIFICATION_ERROR_NONE && icon_path != NULL)
435 *icon_path = ret_image_path;
441 EXPORT_API int notification_translate_localized_text(notification_h noti)
443 int noti_err = NOTIFICATION_ERROR_NONE;
444 char *ret_text = NULL;
446 char *bundle_val = NULL;
449 notification_text_type_e type = NOTIFICATION_TEXT_TYPE_TITLE;
451 for (; type < NOTIFICATION_TEXT_TYPE_MAX; type++) {
452 noti_err = notification_get_text(noti, type, &ret_text);
453 if (noti_err == NOTIFICATION_ERROR_NONE && ret_text) {
454 if (noti->b_text == NULL) {
455 noti->b_text = bundle_create();
456 if (noti->b_text == NULL)
457 return NOTIFICATION_ERROR_OUT_OF_MEMORY;
462 new_text = strdup(ret_text);
464 snprintf(buf_key, sizeof(buf_key), "%d", type);
465 bundle_get_str(b, buf_key, &bundle_val);
466 if (bundle_val != NULL)
467 bundle_del(b, buf_key);
469 bundle_add_str(b, buf_key, new_text);
473 noti->num_format_args = 0;
481 /* LCOV_EXCL_START */
482 EXPORT_API int notification_set_title(notification_h noti,
484 const char *loc_title)
486 return notification_set_text(noti, NOTIFICATION_TEXT_TYPE_TITLE,
488 NOTIFICATION_VARIABLE_TYPE_NONE);;
492 /* LCOV_EXCL_START */
493 EXPORT_API int notification_get_title(notification_h noti,
497 int noti_err = NOTIFICATION_ERROR_NONE;
498 char *ret_text = NULL;
500 noti_err = notification_get_text(noti, NOTIFICATION_TEXT_TYPE_TITLE,
506 if (loc_title != NULL)
513 /* LCOV_EXCL_START */
514 EXPORT_API int notification_set_content(notification_h noti,
516 const char *loc_content)
518 return notification_set_text(noti, NOTIFICATION_TEXT_TYPE_CONTENT,
519 content, loc_content,
520 NOTIFICATION_VARIABLE_TYPE_NONE);
524 /* LCOV_EXCL_START */
525 EXPORT_API int notification_get_content(notification_h noti,
529 int noti_err = NOTIFICATION_ERROR_NONE;
530 char *ret_text = NULL;
532 noti_err = notification_get_text(noti, NOTIFICATION_TEXT_TYPE_CONTENT,
538 if (loc_content != NULL)
545 /* LCOV_EXCL_START */
546 EXPORT_API int notification_set_application(notification_h noti,
549 if (noti == NULL || pkgname == NULL)
550 return NOTIFICATION_ERROR_INVALID_PARAMETER;
552 if (noti->launch_pkgname)
553 free(noti->launch_pkgname);
555 noti->launch_pkgname = strdup(pkgname);
557 return NOTIFICATION_ERROR_NONE;
561 /* LCOV_EXCL_START */
562 EXPORT_API int notification_get_application(notification_h noti,
565 if (noti == NULL || pkgname == NULL)
566 return NOTIFICATION_ERROR_INVALID_PARAMETER;
568 if (noti->launch_pkgname)
569 *pkgname = noti->launch_pkgname;
571 *pkgname = noti->caller_pkgname;
573 return NOTIFICATION_ERROR_NONE;
577 /* LCOV_EXCL_START */
578 EXPORT_API int notification_set_args(notification_h noti, bundle *args,
581 if (noti == NULL || args == NULL)
582 return NOTIFICATION_ERROR_INVALID_PARAMETER;
585 bundle_free(noti->args);
587 noti->args = bundle_dup(args);
589 if (noti->group_args) {
590 bundle_free(noti->group_args);
591 noti->group_args = NULL;
594 if (group_args != NULL)
595 noti->group_args = bundle_dup(group_args);
597 return NOTIFICATION_ERROR_NONE;
601 /* LCOV_EXCL_START */
602 EXPORT_API int notification_get_args(notification_h noti,
606 if (noti == NULL || args == NULL)
607 return NOTIFICATION_ERROR_INVALID_PARAMETER;
614 if (group_args != NULL && noti->group_args)
615 *group_args = noti->group_args;
617 return NOTIFICATION_ERROR_NONE;
621 /* LCOV_EXCL_START */
622 int notification_get_grouping_list_for_uid(notification_type_e type, int count,
623 notification_list_h *list, uid_t uid)
625 notification_list_h get_list = NULL;
629 return NOTIFICATION_ERROR_INVALID_PARAMETER;
631 ret = notification_noti_get_grouping_list(type, count, &get_list, uid);
632 if (ret != NOTIFICATION_ERROR_NONE)
637 return NOTIFICATION_ERROR_NONE;
640 EXPORT_API int notification_get_grouping_list(notification_type_e type, int count,
641 notification_list_h *list)
643 return notification_get_grouping_list_for_uid(type, count, list, getuid());
647 /* LCOV_EXCL_START */
648 EXPORT_API int notification_delete_group_by_group_id(const char *pkgname,
649 notification_type_e type,
653 char *caller_pkgname = NULL;
656 caller_pkgname = notification_get_pkgname_by_pid();
658 caller_pkgname = strdup(pkgname);
660 ret = notification_ipc_request_delete_multiple(type, caller_pkgname, getuid());
663 free(caller_pkgname);
669 /* LCOV_EXCL_START */
670 int notification_delete_group_by_priv_id_for_uid(const char *pkgname,
671 notification_type_e type,
672 int priv_id, uid_t uid)
675 char *caller_pkgname = NULL;
678 caller_pkgname = notification_get_pkgname_by_pid();
680 caller_pkgname = strdup(pkgname);
682 ret = notification_ipc_request_delete_single(type, caller_pkgname, priv_id, uid);
685 free(caller_pkgname);
691 /* LCOV_EXCL_START */
692 EXPORT_API int notification_delete_group_by_priv_id(const char *pkgname,
693 notification_type_e type,
696 return notification_delete_group_by_priv_id_for_uid(pkgname, type, priv_id, getuid());
699 int notification_get_count_for_uid(notification_type_e type,
702 int priv_id, int *count,
706 char *caller_pkgname = NULL;
709 return NOTIFICATION_ERROR_INVALID_PARAMETER;
712 caller_pkgname = notification_get_pkgname_by_pid();
714 caller_pkgname = strdup(pkgname);
716 ret = notification_ipc_request_get_count(
725 free(caller_pkgname);
731 /* LCOV_EXCL_START */
732 EXPORT_API int notification_get_count(notification_type_e type,
735 int priv_id, int *count)
737 return notification_get_count_for_uid(type, pkgname, group_id, priv_id, count, getuid());
740 int notification_clear_for_uid(notification_type_e type, uid_t uid)
742 if (type <= NOTIFICATION_TYPE_NONE || type >= NOTIFICATION_TYPE_MAX)
743 return NOTIFICATION_ERROR_INVALID_PARAMETER;
745 return notification_ipc_request_delete_multiple(type, NULL, uid);
749 /* LCOV_EXCL_START */
750 EXPORT_API int notification_clear(notification_type_e type)
752 return notification_clear_for_uid(type, getuid());
755 EXPORT_API int notification_op_get_data(notification_op *noti_op, notification_op_data_type_e type,
758 if (noti_op == NULL || data == NULL)
759 return NOTIFICATION_ERROR_INVALID_PARAMETER;
762 case NOTIFICATION_OP_DATA_TYPE:
763 *((int *)data) = noti_op->type;
765 case NOTIFICATION_OP_DATA_PRIV_ID:
766 *((int *)data) = noti_op->priv_id;
768 case NOTIFICATION_OP_DATA_NOTI:
769 *((notification_h *)data) = noti_op->noti;
771 case NOTIFICATION_OP_DATA_EXTRA_INFO_1:
772 *((int *)data) = noti_op->extra_info_1;
774 case NOTIFICATION_OP_DATA_EXTRA_INFO_2:
775 *((int *)data) = noti_op->extra_info_2;
778 return NOTIFICATION_ERROR_INVALID_PARAMETER;
782 return NOTIFICATION_ERROR_NONE;
786 /* LCOV_EXCL_START */
787 EXPORT_API int notification_set_pkgname(notification_h noti,
790 if (noti == NULL || pkgname == NULL)
791 return NOTIFICATION_ERROR_INVALID_PARAMETER;
793 /* Remove previous caller pkgname */
794 if (noti->caller_pkgname) {
795 free(noti->caller_pkgname);
796 noti->caller_pkgname = NULL;
799 noti->caller_pkgname = strdup(pkgname);
801 return NOTIFICATION_ERROR_NONE;
805 /* LCOV_EXCL_START */
806 int notification_delete_all_by_type_for_uid(const char *pkgname,
807 notification_type_e type, uid_t uid)
810 char *caller_pkgname = NULL;
812 if (type <= NOTIFICATION_TYPE_NONE || type >= NOTIFICATION_TYPE_MAX)
813 return NOTIFICATION_ERROR_INVALID_PARAMETER;
816 caller_pkgname = notification_get_pkgname_by_pid();
818 caller_pkgname = strdup(pkgname);
820 ret = notification_ipc_request_delete_multiple(type, caller_pkgname, uid);
823 free(caller_pkgname);
829 /* LCOV_EXCL_START */
830 EXPORT_API int notification_delete_all_by_type(const char *pkgname,
831 notification_type_e type)
833 return notification_delete_all_by_type_for_uid(pkgname, type, getuid());
836 int notification_delete_by_priv_id_for_uid(const char *pkgname,
837 notification_type_e type,
842 char *caller_pkgname = NULL;
844 if (priv_id <= NOTIFICATION_PRIV_ID_NONE)
845 return NOTIFICATION_ERROR_INVALID_PARAMETER;
848 caller_pkgname = notification_get_pkgname_by_pid();
850 caller_pkgname = strdup(pkgname);
852 ret = notification_ipc_request_delete_single(type, caller_pkgname, priv_id, uid);
855 free(caller_pkgname);
861 /* LCOV_EXCL_START */
862 EXPORT_API int notification_delete_by_priv_id(const char *pkgname,
863 notification_type_e type,
866 return notification_delete_by_priv_id_for_uid(pkgname, type, priv_id, getuid());
869 EXPORT_API int notification_set_execute_option(notification_h noti,
870 notification_execute_type_e type,
873 bundle *service_handle)
875 char buf_key[32] = { 0, };
876 char *ret_val = NULL;
880 return NOTIFICATION_ERROR_INVALID_PARAMETER;
882 if (type <= NOTIFICATION_EXECUTE_TYPE_NONE
883 || type >= NOTIFICATION_EXECUTE_TYPE_MAX)
884 return NOTIFICATION_ERROR_INVALID_PARAMETER;
886 if (noti->b_execute_option == NULL)
887 noti->b_execute_option = bundle_create();
889 b = noti->b_execute_option;
892 snprintf(buf_key, sizeof(buf_key), "text%d", type);
894 bundle_get_str(b, buf_key, &ret_val);
896 bundle_del(b, buf_key);
898 bundle_add_str(b, buf_key, text);
902 snprintf(buf_key, sizeof(buf_key), "key%d", type);
904 bundle_get_str(b, buf_key, &ret_val);
906 bundle_del(b, buf_key);
908 bundle_add_str(b, buf_key, key);
912 case NOTIFICATION_EXECUTE_TYPE_RESPONDING:
913 if (noti->b_service_responding != NULL) {
914 bundle_free(noti->b_service_responding);
915 noti->b_service_responding = NULL;
918 if (service_handle != NULL)
919 noti->b_service_responding = bundle_dup(service_handle);
922 case NOTIFICATION_EXECUTE_TYPE_SINGLE_LAUNCH:
923 if (noti->b_service_single_launch != NULL) {
924 bundle_free(noti->b_service_single_launch);
925 noti->b_service_single_launch = NULL;
928 if (service_handle != NULL)
929 noti->b_service_single_launch =
930 bundle_dup(service_handle);
933 case NOTIFICATION_EXECUTE_TYPE_MULTI_LAUNCH:
934 if (noti->b_service_multi_launch != NULL) {
935 bundle_free(noti->b_service_multi_launch);
936 noti->b_service_multi_launch = NULL;
939 if (service_handle != NULL)
940 noti->b_service_multi_launch =
941 bundle_dup(service_handle);
946 return NOTIFICATION_ERROR_NONE;
950 /* LCOV_EXCL_START */
951 EXPORT_API int notification_get_id(notification_h noti,
952 int *group_id, int *priv_id)
955 return NOTIFICATION_ERROR_INVALID_PARAMETER;
958 if (noti->group_id < NOTIFICATION_GROUP_ID_NONE)
959 *group_id = NOTIFICATION_GROUP_ID_NONE;
961 *group_id = noti->group_id;
965 *priv_id = noti->priv_id;
967 return NOTIFICATION_ERROR_NONE;
971 /* LCOV_EXCL_START */
972 notification_h notification_load_for_uid(char *pkgname,
973 int priv_id, uid_t uid)
976 notification_h noti = NULL;
978 noti = (notification_h)calloc(1, sizeof(struct _notification));
980 NOTIFICATION_ERR("NO MEMORY : noti == NULL");
984 ret = notification_ipc_request_load_noti_by_priv_id(noti, pkgname, priv_id, uid);
985 if (ret != NOTIFICATION_ERROR_NONE) {
986 notification_free(noti);
994 /* LCOV_EXCL_START */
995 EXPORT_API notification_h notification_load(char *pkgname,
998 return notification_load_for_uid(pkgname, priv_id, getuid());
1000 /* LCOV_EXCL_STOP */
1002 /* LCOV_EXCL_START */
1003 EXPORT_API notification_h notification_new(notification_type_e type,
1004 int group_id, int priv_id)
1006 return notification_create(type);
1009 static void _notification_get_text_domain(notification_h noti)
1012 /* LCOV_EXCL_STOP */
1014 /* LCOV_EXCL_START */
1015 EXPORT_API int notification_get_execute_option(notification_h noti,
1016 notification_execute_type_e type,
1018 bundle **service_handle)
1020 char buf_key[32] = { 0, };
1021 char *ret_val = NULL;
1022 char *get_str = NULL;
1026 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1028 if (type <= NOTIFICATION_EXECUTE_TYPE_NONE
1029 || type >= NOTIFICATION_EXECUTE_TYPE_MAX)
1030 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1034 case NOTIFICATION_EXECUTE_TYPE_RESPONDING:
1035 b = noti->b_service_responding;
1037 case NOTIFICATION_EXECUTE_TYPE_SINGLE_LAUNCH:
1038 b = noti->b_service_single_launch;
1040 case NOTIFICATION_EXECUTE_TYPE_MULTI_LAUNCH:
1041 b = noti->b_service_multi_launch;
1049 if (noti->domain == NULL || noti->dir == NULL)
1050 _notification_get_text_domain(noti);
1052 snprintf(buf_key, sizeof(buf_key), "key%d", type);
1054 bundle_get_str(b, buf_key, &ret_val);
1055 if (ret_val != NULL && noti->domain != NULL
1056 && noti->dir != NULL) {
1057 bindtextdomain(noti->domain, noti->dir);
1059 get_str = dgettext(noti->domain, ret_val);
1062 } else if (ret_val != NULL) {
1063 get_str = dgettext("sys_string", ret_val);
1067 snprintf(buf_key, sizeof(buf_key), "text%d",
1070 bundle_get_str(b, buf_key, &ret_val);
1077 if (service_handle != NULL)
1078 *service_handle = b;
1080 return NOTIFICATION_ERROR_NONE;
1082 /* LCOV_EXCL_STOP */
1084 EXPORT_API int notification_insert_for_uid(notification_h noti,
1085 int *priv_id, uid_t uid)
1091 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1093 if (noti->type <= NOTIFICATION_TYPE_NONE
1094 || noti->type >= NOTIFICATION_TYPE_MAX)
1095 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1098 noti->insert_time = time(NULL);
1100 ret = notification_ipc_request_insert(noti, &id);
1101 if (ret != NOTIFICATION_ERROR_NONE)
1105 NOTIFICATION_DBG("from master:%d", id);
1107 /* If priv_id is valid data, set priv_id */
1108 if (priv_id != NULL)
1109 *priv_id = noti->priv_id;
1111 return NOTIFICATION_ERROR_NONE;
1114 EXPORT_API int notification_insert(notification_h noti,
1117 return notification_insert_for_uid(noti, priv_id, getuid());
1120 EXPORT_API int notification_update_async_for_uid(notification_h noti,
1121 void (*result_cb)(int priv_id, int result, void *data), void *user_data, uid_t uid)
1124 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1127 /* Update insert time ? */
1128 noti->insert_time = time(NULL);
1130 return notification_ipc_request_update_async(noti, result_cb, user_data);
1133 EXPORT_API int notification_update_async(notification_h noti,
1134 void (*result_cb)(int priv_id, int result, void *data), void *user_data)
1136 return notification_update_async_for_uid(noti, result_cb, user_data, getuid());
1139 EXPORT_API int notification_register_detailed_changed_cb_for_uid(
1140 void (*detailed_changed_cb)(void *data, notification_type_e type, notification_op *op_list, int num_op),
1141 void *user_data, uid_t uid)
1143 GList *noti_cb_list = NULL;
1144 notification_cb_info_s *noti_cb_info_new = NULL;
1146 if (detailed_changed_cb == NULL)
1147 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1149 if (notification_ipc_monitor_init(uid) != NOTIFICATION_ERROR_NONE)
1150 return NOTIFICATION_ERROR_IO_ERROR;
1152 if (_noti_cb_hash == NULL)
1153 _noti_cb_hash = g_hash_table_new(g_direct_hash, g_direct_equal);
1155 noti_cb_info_new = (notification_cb_info_s *)malloc(sizeof(notification_cb_info_s));
1156 if (noti_cb_info_new == NULL) {
1157 NOTIFICATION_ERR("malloc failed");
1158 return NOTIFICATION_ERROR_OUT_OF_MEMORY;
1161 noti_cb_info_new->cb_type = NOTIFICATION_CB_DETAILED;
1162 noti_cb_info_new->changed_cb = NULL;
1163 noti_cb_info_new->detailed_changed_cb = detailed_changed_cb;
1164 noti_cb_info_new->data = user_data;
1166 noti_cb_list = g_hash_table_lookup(_noti_cb_hash, GUINT_TO_POINTER(uid));
1168 if (noti_cb_list == NULL) {
1169 noti_cb_list = g_list_append(noti_cb_list, noti_cb_info_new);
1170 g_hash_table_insert(_noti_cb_hash, GUINT_TO_POINTER(uid), noti_cb_list);
1172 noti_cb_list = g_list_append(noti_cb_list, noti_cb_info_new);
1175 return NOTIFICATION_ERROR_NONE;
1178 EXPORT_API int notification_register_detailed_changed_cb(
1179 void (*detailed_changed_cb)(void *data, notification_type_e type, notification_op *op_list, int num_op),
1182 return notification_register_detailed_changed_cb_for_uid(detailed_changed_cb, user_data, getuid());
1185 static gint _noti_detailed_changed_compare(gconstpointer a, gconstpointer b)
1187 const struct _notification_cb_info *info = NULL;
1191 info = (notification_cb_info_s *)a;
1193 if (info->detailed_changed_cb == b)
1199 EXPORT_API int notification_unregister_detailed_changed_cb_for_uid(
1200 void (*detailed_changed_cb)(void *data, notification_type_e type, notification_op *op_list, int num_op),
1201 void *user_data, uid_t uid)
1203 notification_cb_info_s *noti_cb_info = NULL;
1204 GList *noti_cb_list = NULL;
1205 GList *delete_cb_list = NULL;
1207 if (detailed_changed_cb == NULL)
1208 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1210 if (_noti_cb_hash == NULL)
1211 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1213 noti_cb_list = (GList *)g_hash_table_lookup(_noti_cb_hash, GUINT_TO_POINTER(uid));
1215 if (noti_cb_list == NULL)
1216 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1218 noti_cb_list = g_list_first(noti_cb_list);
1219 delete_cb_list = g_list_find_custom(noti_cb_list, (gconstpointer)detailed_changed_cb,
1220 _noti_detailed_changed_compare);
1222 if (delete_cb_list) {
1223 noti_cb_info = (notification_cb_info_s *)g_list_nth_data(delete_cb_list, 0);
1224 noti_cb_list = g_list_delete_link(noti_cb_list, delete_cb_list);
1225 __free_changed_cb_info(noti_cb_info);
1226 if (noti_cb_list == NULL) {
1227 g_hash_table_steal(_noti_cb_hash, GUINT_TO_POINTER(uid));
1229 noti_cb_list = g_list_first(noti_cb_list);
1230 g_hash_table_replace(_noti_cb_hash, GUINT_TO_POINTER(uid), noti_cb_list);
1234 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1237 if (g_hash_table_size(_noti_cb_hash) == 0)
1238 notification_ipc_monitor_fini();
1240 return NOTIFICATION_ERROR_NONE;
1244 EXPORT_API int notification_unregister_detailed_changed_cb(
1245 void (*detailed_changed_cb)(void *data, notification_type_e type, notification_op *op_list, int num_op),
1248 return notification_unregister_detailed_changed_cb_for_uid(detailed_changed_cb, user_data, getuid());
1251 /* LCOV_EXCL_START */
1252 EXPORT_API int notification_is_service_ready(void)
1254 return notification_ipc_is_master_ready();
1256 /* LCOV_EXCL_STOP */
1258 EXPORT_API int notification_set_uid(notification_h noti,
1262 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1265 return NOTIFICATION_ERROR_NONE;
1268 EXPORT_API int notification_get_uid(notification_h noti,
1271 if (noti == NULL || uid == NULL)
1272 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1275 return NOTIFICATION_ERROR_NONE;
1278 EXPORT_API int notification_post_for_uid(notification_h noti, uid_t uid)
1284 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1286 if (noti->type <= NOTIFICATION_TYPE_NONE
1287 || noti->type >= NOTIFICATION_TYPE_MAX)
1288 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1290 /* Save insert time */
1291 noti->insert_time = time(NULL);
1294 ret = notification_ipc_request_insert(noti, &id);
1295 if (ret != NOTIFICATION_ERROR_NONE)
1299 NOTIFICATION_DBG("from master:%d", id);
1301 return NOTIFICATION_ERROR_NONE;
1304 EXPORT_API int notification_update_for_uid(notification_h noti, uid_t uid)
1307 notification_ipc_request_refresh(uid);
1308 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1312 /* Update insert time ? */
1313 noti->insert_time = time(NULL);
1315 return notification_ipc_request_update(noti);
1318 EXPORT_API int notification_delete_for_uid(notification_h noti, uid_t uid)
1322 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1324 return notification_ipc_request_delete_single(NOTIFICATION_TYPE_NONE,
1325 noti->caller_pkgname, noti->priv_id, uid);
1328 EXPORT_API int notification_delete_all_for_uid(notification_type_e type, uid_t uid)
1331 char *caller_pkgname = NULL;
1333 if (type <= NOTIFICATION_TYPE_NONE || type >= NOTIFICATION_TYPE_MAX)
1334 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1336 caller_pkgname = notification_get_pkgname_by_pid();
1338 ret = notification_ipc_request_delete_multiple(type, caller_pkgname, uid);
1341 free(caller_pkgname);
1346 EXPORT_API notification_h notification_load_by_tag_for_uid(const char *tag, uid_t uid)
1349 notification_h noti = NULL;
1350 char *caller_pkgname = NULL;
1353 NOTIFICATION_ERR("Invalid parameter");
1354 set_last_result(NOTIFICATION_ERROR_INVALID_PARAMETER);
1358 caller_pkgname = notification_get_pkgname_by_pid();
1359 if (!caller_pkgname) {
1360 /* LCOV_EXCL_START */
1361 NOTIFICATION_ERR("Failed to get a package name");
1362 set_last_result(NOTIFICATION_ERROR_OUT_OF_MEMORY);
1364 /* LCOV_EXCL_STOP */
1367 noti = (notification_h)calloc(1, sizeof(struct _notification));
1369 /* LCOV_EXCL_START */
1370 NOTIFICATION_ERR("Failed to alloc a new notification");
1371 set_last_result(NOTIFICATION_ERROR_OUT_OF_MEMORY);
1372 free(caller_pkgname);
1375 /* LCOV_EXCL_STOP */
1378 ret = notification_ipc_request_load_noti_by_tag(noti, caller_pkgname, (char *)tag, uid);
1379 free(caller_pkgname);
1381 set_last_result(ret);
1382 if (ret != NOTIFICATION_ERROR_NONE) {
1383 notification_free(noti);
1390 EXPORT_API notification_h notification_create_from_package_template(const char *pkgname, const char *template_name)
1393 notification_h noti = NULL;
1395 if (pkgname == NULL || template_name == NULL) {
1396 NOTIFICATION_ERR("Invalid parameter");
1397 set_last_result(NOTIFICATION_ERROR_INVALID_PARAMETER);
1401 noti = (notification_h)calloc(1, sizeof(struct _notification));
1403 NOTIFICATION_ERR("Failed to alloc a new notification");
1404 set_last_result(NOTIFICATION_ERROR_OUT_OF_MEMORY);
1408 ret = notification_ipc_request_create_from_package_template(noti, pkgname, template_name);
1410 set_last_result(ret);
1411 if (ret != NOTIFICATION_ERROR_NONE) {
1412 notification_free(noti);
1419 EXPORT_API int notification_set_default_button(notification_h noti, notification_button_index_e index)
1422 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1424 if (index < 0 || index > NOTIFICATION_BUTTON_6)
1425 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1427 noti->default_button_index = index;
1429 return NOTIFICATION_ERROR_NONE;
1432 EXPORT_API int notification_get_default_button(notification_h noti, notification_button_index_e *index)
1434 if (noti == NULL || index == NULL)
1435 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1437 *index = noti->default_button_index;
1439 return NOTIFICATION_ERROR_NONE;
1442 EXPORT_API int notification_get_ongoing_value_type(notification_h noti, notification_ongoing_value_type_e *type)
1444 if (noti == NULL || type == NULL)
1445 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1447 *type = noti->ongoing_value_type;
1449 return NOTIFICATION_ERROR_NONE;
1452 EXPORT_API int notification_set_ongoing_value_type(notification_h noti, notification_ongoing_value_type_e type)
1455 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1457 if (type < NOTIFICATION_ONGOING_VALUE_TYPE_PERCENT || type > NOTIFICATION_ONGOING_VALUE_TYPE_TIME)
1458 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1460 noti->ongoing_value_type = type;
1462 return NOTIFICATION_ERROR_NONE;
1465 EXPORT_API int notification_get_ongoing_time(notification_h noti, int *current, int *duration)
1467 if (noti == NULL || current == NULL || duration == NULL)
1468 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1470 *current = noti->ongoing_current;
1471 *duration = noti->ongoing_duration;
1473 return NOTIFICATION_ERROR_NONE;
1476 EXPORT_API int notification_set_ongoing_time(notification_h noti, int current, int duration)
1479 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1481 if (current < 0 || duration < 0 || current > duration)
1482 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1484 noti->ongoing_current = current;
1485 noti->ongoing_duration = duration;
1487 return NOTIFICATION_ERROR_NONE;
1490 EXPORT_API int notification_get_hide_timeout(notification_h noti, int *timeout)
1492 if (noti == NULL || timeout == NULL)
1493 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1495 *timeout = noti->timeout;
1497 return NOTIFICATION_ERROR_NONE;
1500 EXPORT_API int notification_set_hide_timeout(notification_h noti, int timeout)
1502 if (noti == NULL || timeout < 0)
1503 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1505 noti->timeout = timeout;
1507 return NOTIFICATION_ERROR_NONE;
1510 EXPORT_API int notification_get_text_input_max_length(notification_h noti, int *text_input_max_length)
1512 if (noti == NULL || text_input_max_length == NULL)
1513 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1515 *text_input_max_length = noti->text_input_max_length;
1517 return NOTIFICATION_ERROR_NONE;
1520 EXPORT_API int notification_post_with_event_cb_for_uid(notification_h noti, event_handler_cb cb,
1521 void *userdata, uid_t uid)
1525 notification_event_cb_info_s *info = NULL;
1528 if (noti == NULL || cb == NULL)
1529 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1531 if (noti->type <= NOTIFICATION_TYPE_NONE || noti->type >= NOTIFICATION_TYPE_MAX)
1532 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1534 noti->insert_time = time(NULL);
1535 noti->event_flag = true;
1538 ret = notification_ipc_request_insert(noti, &priv_id);
1539 if (ret != NOTIFICATION_ERROR_NONE)
1542 noti->priv_id = priv_id;
1544 __noti_event_cb_list = g_list_first(__noti_event_cb_list);
1545 find_list = g_list_find_custom(__noti_event_cb_list, GUINT_TO_POINTER(priv_id),
1546 (GCompareFunc)__priv_id_compare);
1549 info = g_list_nth_data(find_list, 0);
1551 info->userdata = userdata;
1553 info = (notification_event_cb_info_s *)malloc(sizeof(notification_cb_info_s));
1555 NOTIFICATION_ERR("malloc failed");
1556 return NOTIFICATION_ERROR_OUT_OF_MEMORY;
1558 info->priv_id = priv_id;
1560 info->userdata = userdata;
1561 __noti_event_cb_list = g_list_append(__noti_event_cb_list, info);
1567 EXPORT_API int notification_post_with_event_cb(notification_h noti, event_handler_cb cb, void *userdata)
1569 return notification_post_with_event_cb_for_uid(noti, cb, userdata, getuid());
1572 EXPORT_API int notification_send_event(notification_h noti, int event_type)
1578 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1580 if (!((event_type >= NOTIFICATION_EVENT_TYPE_CLICK_ON_BUTTON_1
1581 && event_type < NOTIFICATION_EVENT_TYPE_MAX)
1582 || (event_type >= NOTIFICATION_EVENT_TYPE_HIDDEN_BY_USER
1583 && event_type <= NOTIFICATION_EVENT_TYPE_HIDDEN_BY_TIMEOUT)))
1584 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1586 ret = notification_get_event_flag(noti, &event_flag);
1587 if (ret != NOTIFICATION_ERROR_NONE || event_flag == false)
1588 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1590 ret = notification_ipc_send_event(noti, event_type);
1595 EXPORT_API int notification_get_event_flag(notification_h noti, bool *flag)
1597 if (noti == NULL || flag == NULL)
1598 return NOTIFICATION_ERROR_INVALID_PARAMETER;
1600 *flag = noti->event_flag;
1602 return NOTIFICATION_ERROR_NONE;