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.
31 #include <com-core_packet.h>
33 #include <notification_ipc.h>
34 #include <notification_db.h>
35 #include <notification_type.h>
36 #include <notification_internal.h>
37 #include <notification_debug.h>
39 #define NOTIFICATION_IPC_TIMEOUT 0.0
44 int server_cl_fd_ref_cnt;
46 const char *socket_file;
48 int (*request_cb)(const char *appid, const char *name, int type, const char *content, const char *icon, pid_t pid, double period, int allow_duplicate, void *data);
52 int is_started_cb_set_svc;
56 .server_cl_fd_ref_cnt = 0,
58 .socket_file = NOTIFICATION_ADDR,
60 .is_started_cb_set_svc = 0,
63 typedef struct _task_list task_list;
68 void (*task_cb) (void *data);
72 typedef struct _result_cb_item {
73 void (*result_cb)(int priv_id, int result, void *data);
77 static task_list *g_task_list;
79 static Eina_Bool _do_deffered_task(void *data);
82 * The concept of having to deffer a task till the "master" was
83 * started is now defunct since we use systemd to auto activate
84 * the service, with clients blissfully unaware of the state
85 * of the service at the time they attempt to use the socket.
87 * To enable backwards compatability we now setup an idle handler
88 * to cleanup all the deffered task. This keeps the call behavior
89 * as non-blocking and is true to the original spirit (i.e. run
90 * the task when the service is available)
94 notification_ipc_add_deffered_task(
95 void (*deffered_task_cb)(void *data),
98 task_list *list = NULL;
99 task_list *list_new = NULL;
102 (task_list *) malloc(sizeof(task_list));
104 if (list_new == NULL) {
105 return NOTIFICATION_ERROR_NO_MEMORY;
108 list_new->next = NULL;
109 list_new->prev = NULL;
111 list_new->task_cb = deffered_task_cb;
112 list_new->data = user_data;
114 if (g_task_list == NULL) {
115 g_task_list = list_new;
119 while (list->next != NULL) {
123 list->next = list_new;
124 list_new->prev = list;
127 ecore_idler_add(_do_deffered_task, NULL);
129 return NOTIFICATION_ERROR_NONE;
133 notification_ipc_del_deffered_task(
134 void (*deffered_task_cb)(void *data))
136 task_list *list_del = NULL;
137 task_list *list_prev = NULL;
138 task_list *list_next = NULL;
140 list_del = g_task_list;
142 if (list_del == NULL) {
143 return NOTIFICATION_ERROR_INVALID_DATA;
146 while (list_del->prev != NULL) {
147 list_del = list_del->prev;
151 if (list_del->task_cb == deffered_task_cb) {
152 list_prev = list_del->prev;
153 list_next = list_del->next;
155 if (list_prev == NULL) {
156 g_task_list = list_next;
158 list_prev->next = list_next;
161 if (list_next == NULL) {
162 if (list_prev != NULL) {
163 list_prev->next = NULL;
166 list_next->prev = list_prev;
171 if (g_task_list == NULL) {
172 ecore_idler_del(_do_deffered_task);
175 return NOTIFICATION_ERROR_NONE;
177 list_del = list_del->next;
178 } while (list_del != NULL);
180 return NOTIFICATION_ERROR_INVALID_DATA;
183 static Eina_Bool _do_deffered_task(void *data) {
184 task_list *list_do = NULL;
185 task_list *list_temp = NULL;
189 list_do = g_task_list;
192 while (list_do->prev != NULL) {
193 list_do = list_do->prev;
196 while (list_do != NULL) {
197 if (list_do->task_cb != NULL) {
198 list_do->task_cb(list_do->data);
199 NOTIFICATION_DBG("called:%p", list_do->task_cb);
201 list_temp = list_do->next;
207 return ECORE_CALLBACK_CANCEL;
211 * functions to create operation list
213 notification_op *notification_ipc_create_op(notification_op_type_e type, int num_op, int *list_priv_id, int num_priv_id, notification_h *noti_list)
216 notification_op *op_list = NULL;
222 op_list = (notification_op *)malloc(sizeof(notification_op) * num_op);
223 memset(op_list, 0x0, sizeof(notification_op) * num_op);
225 for (i = 0; i < num_op; i++) {
226 (op_list + i)->type = type;
227 if (list_priv_id != NULL) {
228 (op_list + i)->priv_id = *(list_priv_id + i);
230 if (noti_list != NULL) {
231 (op_list + i)->noti = *(noti_list + i);
239 * utility functions creating notification packet
241 static inline char *_dup_string(const char *string)
245 if (string == NULL) {
248 if (string[0] == '\0') {
252 ret = strdup(string);
254 NOTIFICATION_ERR("Error: %s\n", strerror(errno));
259 static inline bundle *_create_bundle_from_string(unsigned char *string)
261 if (string == NULL) {
264 if (string[0] == '\0') {
268 return bundle_decode(string, strlen((char *)string));
272 * functions creating notification packet
274 EXPORT_API notification_error_e notification_ipc_make_noti_from_packet(notification_h noti, const struct packet *packet)
280 int internal_group_id;
282 char *caller_pkgname = NULL;
283 char *launch_pkgname = NULL;
284 unsigned char *args = NULL;
285 unsigned char *group_args = NULL;
286 unsigned char *b_execute_option = NULL;
287 unsigned char *b_service_responding = NULL;
288 unsigned char *b_service_single_launch = NULL;
289 unsigned char *b_service_multi_launch = NULL;
292 unsigned char *b_text = NULL;
293 unsigned char *b_key = NULL;
294 unsigned char *b_format_args = NULL;
296 unsigned char *b_image_path = NULL;
298 char *sound_path = NULL;
300 char *vibration_path = NULL;
307 int flags_for_property;
309 double progress_size;
310 double progress_percentage;
311 char *app_icon_path = NULL;
312 char *app_name = NULL;
313 char *temp_title = NULL;
314 char *temp_content = NULL;
317 NOTIFICATION_ERR("invalid data");
318 return NOTIFICATION_ERROR_INVALID_DATA;
321 ret = packet_get(packet,
322 "iiiiisssssssssssssisisisiiiiiiiiddssss",
333 &b_service_responding,
334 &b_service_single_launch,
335 &b_service_multi_launch,
356 &progress_percentage,
363 NOTIFICATION_ERR("failed to create a noti from packet");
364 return NOTIFICATION_ERROR_INVALID_DATA;
368 * This is already allocated from the notification_create function.
369 * Before reallocate string to here.
370 * We have to release old one first.
372 free(noti->caller_pkgname);
373 noti->caller_pkgname = _dup_string(caller_pkgname);
374 noti->launch_pkgname = _dup_string(launch_pkgname);
375 noti->args = _create_bundle_from_string(args);
376 noti->group_args = _create_bundle_from_string(group_args);
377 noti->b_execute_option = _create_bundle_from_string(b_execute_option);
378 noti->b_service_responding = _create_bundle_from_string(b_service_responding);
379 noti->b_service_single_launch = _create_bundle_from_string(b_service_single_launch);
380 noti->b_service_multi_launch = _create_bundle_from_string(b_service_multi_launch);
381 noti->domain = _dup_string(domain);
382 noti->dir = _dup_string(dir);
383 noti->b_text = _create_bundle_from_string(b_text);
384 noti->b_key = _create_bundle_from_string(b_key);
385 noti->b_format_args = _create_bundle_from_string(b_format_args);
386 noti->b_image_path = _create_bundle_from_string(b_image_path);
387 noti->sound_path = _dup_string(sound_path);
388 noti->vibration_path = _dup_string(vibration_path);
389 noti->app_icon_path = _dup_string(app_icon_path);
390 noti->app_name = _dup_string(app_name);
391 noti->temp_title = _dup_string(temp_title);
392 noti->temp_content = _dup_string(temp_content);
395 noti->layout = layout;
396 noti->group_id = group_id;
397 noti->internal_group_id = internal_group_id;
398 noti->priv_id = priv_id;
399 noti->num_format_args = num_format_args;
400 noti->sound_type = sound_type;
401 noti->vibration_type = vibration_type;
402 noti->led_operation = led_operation;
403 noti->led_argb = led_argb;
404 noti->led_on_ms = led_on_ms;
405 noti->led_off_ms = led_off_ms;
407 noti->insert_time = insert_time;
408 noti->flags_for_property = flags_for_property;
409 noti->display_applist = display_applist;
410 noti->progress_size = progress_size;
411 noti->progress_percentage = progress_percentage;
413 return NOTIFICATION_ERROR_NONE;
416 EXPORT_API struct packet *notification_ipc_make_packet_from_noti(notification_h noti, const char *command, int packet_type)
418 struct packet *result = NULL;
420 char *group_args = NULL;
421 char *b_image_path = NULL;
422 char *b_execute_option = NULL;
423 char *b_service_responding = NULL;
424 char *b_service_single_launch = NULL;
425 char *b_service_multi_launch = NULL;
428 char *b_format_args = NULL;
429 int flag_simmode = 0;
430 struct packet *(*func_to_create_packet)(const char *command, const char *fmt, ...);
431 const char *title_key = NULL;
432 char buf_key[32] = { 0, };
434 /* Decode bundle to insert DB */
436 bundle_encode(noti->args, (bundle_raw **) & args, NULL);
438 if (noti->group_args) {
439 bundle_encode(noti->group_args, (bundle_raw **) & group_args,
443 if (noti->b_execute_option) {
444 bundle_encode(noti->b_execute_option,
445 (bundle_raw **) & b_execute_option, NULL);
447 if (noti->b_service_responding) {
448 bundle_encode(noti->b_service_responding,
449 (bundle_raw **) & b_service_responding, NULL);
451 if (noti->b_service_single_launch) {
452 bundle_encode(noti->b_service_single_launch,
453 (bundle_raw **) & b_service_single_launch, NULL);
455 if (noti->b_service_multi_launch) {
456 bundle_encode(noti->b_service_multi_launch,
457 (bundle_raw **) & b_service_multi_launch, NULL);
461 bundle_encode(noti->b_text, (bundle_raw **) & b_text, NULL);
464 bundle_encode(noti->b_key, (bundle_raw **) & b_key, NULL);
466 if (noti->b_format_args) {
467 bundle_encode(noti->b_format_args,
468 (bundle_raw **) & b_format_args, NULL);
471 if (noti->b_image_path) {
472 bundle_encode(noti->b_image_path,
473 (bundle_raw **) & b_image_path, NULL);
476 /* Check only simmode property is enable */
477 if (noti->flags_for_property & NOTIFICATION_PROP_DISPLAY_ONLY_SIMMODE) {
481 if (noti->b_key != NULL) {
482 snprintf(buf_key, sizeof(buf_key), "%d",
483 NOTIFICATION_TEXT_TYPE_TITLE);
485 title_key = bundle_get_val(noti->b_key, buf_key);
488 if (title_key == NULL && noti->b_text != NULL) {
489 snprintf(buf_key, sizeof(buf_key), "%d",
490 NOTIFICATION_TEXT_TYPE_TITLE);
492 title_key = bundle_get_val(noti->b_text, buf_key);
495 if (title_key == NULL) {
496 title_key = noti->caller_pkgname;
499 if (packet_type == 1)
500 func_to_create_packet = packet_create;
501 else if (packet_type == 2)
502 func_to_create_packet = packet_create_noack;
507 result = func_to_create_packet(command,
508 "iiiiisssssssssssssisisisiiiiiiiiddssss",
512 noti->internal_group_id,
514 NOTIFICATION_CHECK_STR(noti->caller_pkgname),
515 NOTIFICATION_CHECK_STR(noti->launch_pkgname),
516 NOTIFICATION_CHECK_STR(args),
517 NOTIFICATION_CHECK_STR(group_args),
518 NOTIFICATION_CHECK_STR(b_execute_option),
519 NOTIFICATION_CHECK_STR(b_service_responding),
520 NOTIFICATION_CHECK_STR(b_service_single_launch),
521 NOTIFICATION_CHECK_STR(b_service_multi_launch),
522 NOTIFICATION_CHECK_STR(noti->domain),
523 NOTIFICATION_CHECK_STR(noti->dir),
524 NOTIFICATION_CHECK_STR(b_text),
525 NOTIFICATION_CHECK_STR(b_key),
526 NOTIFICATION_CHECK_STR(b_format_args),
527 noti->num_format_args,
528 NOTIFICATION_CHECK_STR(b_image_path),
530 NOTIFICATION_CHECK_STR(noti->sound_path),
531 noti->vibration_type,
532 NOTIFICATION_CHECK_STR(noti->vibration_path),
539 noti->flags_for_property,
540 noti->display_applist,
542 noti->progress_percentage,
543 NOTIFICATION_CHECK_STR(noti->app_icon_path),
544 NOTIFICATION_CHECK_STR(noti->app_name),
545 NOTIFICATION_CHECK_STR(noti->temp_title),
546 NOTIFICATION_CHECK_STR(noti->temp_content));
549 /* Free decoded data */
557 if (b_execute_option) {
558 free(b_execute_option);
560 if (b_service_responding) {
561 free(b_service_responding);
563 if (b_service_single_launch) {
564 free(b_service_single_launch);
566 if (b_service_multi_launch) {
567 free(b_service_multi_launch);
588 * functions to handler services
590 static struct packet *_handler_insert(pid_t pid, int handle, const struct packet *packet)
592 notification_h noti = NULL;
595 NOTIFICATION_ERR("a packet is null");
598 noti = notification_create(NOTIFICATION_TYPE_NOTI);
600 NOTIFICATION_ERR("failed to create a notification");
603 notification_ipc_make_noti_from_packet(noti, packet);
605 if (noti->flags_for_property
606 & NOTIFICATION_PROP_DISABLE_UPDATE_ON_INSERT) {
607 /* Disable changed cb */
609 /* Enable changed cb */
610 notification_op *noti_op = notification_ipc_create_op(NOTIFICATION_OP_INSERT, 1, &(noti->priv_id), 1, ¬i);
611 if (noti_op != NULL) {
612 notification_call_changed_cb(noti_op, 1);
616 notification_free(noti);
621 static struct packet *_handler_update(pid_t pid, int handle, const struct packet *packet)
623 notification_h noti = NULL;
626 NOTIFICATION_ERR("a packet is null");
630 noti = notification_create(NOTIFICATION_TYPE_NOTI);
632 NOTIFICATION_ERR("failed to create a notification");
636 notification_ipc_make_noti_from_packet(noti, packet);
638 notification_op *noti_op = notification_ipc_create_op(NOTIFICATION_OP_UPDATE, 1, &(noti->priv_id), 1, ¬i);
639 if (noti_op != NULL) {
640 notification_call_changed_cb(noti_op, 1);
644 notification_free(noti);
649 static struct packet *_handler_refresh(pid_t pid, int handle, const struct packet *packet)
652 NOTIFICATION_ERR("a packet is null");
655 notification_op *noti_op = notification_ipc_create_op(NOTIFICATION_OP_REFRESH, 1, NULL, 0, NULL);
656 if (noti_op != NULL) {
657 notification_call_changed_cb(noti_op, 1);
664 static struct packet *_handler_delete_single(pid_t pid, int handle, const struct packet *packet)
667 int priv_id = NOTIFICATION_PRIV_ID_NONE;
670 NOTIFICATION_ERR("a packet is null");
673 if (packet_get(packet, "ii", &num_deleted, &priv_id) == 2) {
674 notification_op *noti_op = notification_ipc_create_op(NOTIFICATION_OP_DELETE, 1, &priv_id, 1, NULL);
675 if (noti_op != NULL) {
676 notification_call_changed_cb(noti_op, 1);
684 static struct packet *_handler_delete_multiple(pid_t pid, int handle, const struct packet *packet)
690 NOTIFICATION_ERR("delete_noti_multiple");
693 NOTIFICATION_ERR("a packet is null");
696 ret = packet_get(packet, "iiiiiiiiiii", &num_deleted,
708 NOTIFICATION_ERR("packet data count:%d", ret);
709 NOTIFICATION_ERR("packet data num deleted:%d", num_deleted);
712 for (i = 0 ; i < 10 ; i++) {
713 NOTIFICATION_ERR("packet data[%d]:%d",i, buf[i]);
717 notification_op *noti_op = notification_ipc_create_op(
718 NOTIFICATION_OP_DELETE, num_deleted, buf, num_deleted, NULL);
719 if (noti_op != NULL) {
720 notification_call_changed_cb(noti_op, num_deleted);
728 static int _handler_service_register(pid_t pid, int handle, const struct packet *packet, void *data)
733 NOTIFICATION_ERR("Packet is not valid\n");
734 ret = NOTIFICATION_ERROR_INVALID_DATA;
735 } else if (packet_get(packet, "i", &ret) != 1) {
736 NOTIFICATION_ERR("Packet is not valid\n");
737 ret = NOTIFICATION_ERROR_INVALID_DATA;
740 notification_op *noti_op = notification_ipc_create_op(NOTIFICATION_OP_SERVICE_READY, 1, NULL, 1, NULL);
741 if (noti_op != NULL) {
742 notification_call_changed_cb(noti_op, 1);
750 notification_error_e notification_ipc_monitor_init(void)
753 struct packet *packet;
754 static struct method service_table[] = {
757 .handler = _handler_insert,
760 .cmd = "update_noti",
761 .handler = _handler_update,
764 .cmd = "refresh_noti",
765 .handler = _handler_refresh,
768 .cmd = "del_noti_single",
769 .handler = _handler_delete_single,
772 .cmd = "del_noti_multiple",
773 .handler = _handler_delete_multiple,
781 if (s_info.initialized == 1) {
782 return NOTIFICATION_ERROR_NONE;
784 s_info.initialized = 1;
787 NOTIFICATION_ERR("register a service\n");
789 com_core_packet_use_thread(1);
790 s_info.server_fd = com_core_packet_client_init(s_info.socket_file, 0, service_table);
791 if (s_info.server_fd < 0) {
792 NOTIFICATION_ERR("Failed to make a connection to the master\n");
793 return NOTIFICATION_ERROR_IO;
796 packet = packet_create("service_register", "");
798 NOTIFICATION_ERR("Failed to build a packet\n");
799 com_core_packet_client_fini(s_info.server_fd);
800 return NOTIFICATION_ERROR_IO;
803 ret = com_core_packet_async_send(s_info.server_fd, packet, 1.0, _handler_service_register, NULL);
804 NOTIFICATION_DBG("Service register sent: %d\n", ret);
805 packet_destroy(packet);
807 com_core_packet_client_fini(s_info.server_fd);
808 s_info.server_fd = NOTIFICATION_ERROR_INVALID_DATA;
809 ret = NOTIFICATION_ERROR_IO;
811 ret = NOTIFICATION_ERROR_NONE;
814 NOTIFICATION_DBG("Server FD: %d\n", s_info.server_fd);
818 notification_error_e notification_ipc_monitor_fini(void)
820 if (s_info.initialized == 0) {
821 return NOTIFICATION_ERROR_NONE;
824 com_core_packet_client_fini(s_info.server_fd);
825 s_info.server_fd = NOTIFICATION_ERROR_INVALID_DATA;
827 s_info.initialized = 0;
829 return NOTIFICATION_ERROR_NONE;
833 * functions to request the service
835 notification_error_e notification_ipc_request_insert(notification_h noti, int *priv_id)
838 int id = NOTIFICATION_PRIV_ID_NONE;
839 struct packet *packet;
840 struct packet *result;
842 /* Initialize private ID */
843 noti->priv_id = NOTIFICATION_PRIV_ID_NONE;
844 noti->group_id = NOTIFICATION_GROUP_ID_NONE;
845 noti->internal_group_id = NOTIFICATION_GROUP_ID_NONE;
847 packet = notification_ipc_make_packet_from_noti(noti, "add_noti", 1);
848 result = com_core_packet_oneshot_send(NOTIFICATION_ADDR,
850 NOTIFICATION_IPC_TIMEOUT);
851 packet_destroy(packet);
853 if (result != NULL) {
854 if (packet_get(result, "ii", &status, &id) != 2) {
855 NOTIFICATION_ERR("Failed to get a result packet");
856 packet_unref(result);
857 return NOTIFICATION_ERROR_IO;
860 if (status != NOTIFICATION_ERROR_NONE) {
861 packet_unref(result);
864 packet_unref(result);
866 return NOTIFICATION_ERROR_SERVICE_NOT_READY;
869 if (priv_id != NULL) {
873 return NOTIFICATION_ERROR_NONE;
876 notification_error_e notification_ipc_request_delete_single(notification_type_e type, char *pkgname, int priv_id)
879 int id = NOTIFICATION_PRIV_ID_NONE;
880 struct packet *packet;
881 struct packet *result;
883 packet = packet_create("del_noti_single", "si", pkgname, priv_id);
884 result = com_core_packet_oneshot_send(NOTIFICATION_ADDR,
886 NOTIFICATION_IPC_TIMEOUT);
887 packet_destroy(packet);
889 if (result != NULL) {
890 if (packet_get(result, "ii", &status, &id) != 2) {
891 NOTIFICATION_ERR("Failed to get a result packet");
892 packet_unref(result);
893 return NOTIFICATION_ERROR_IO;
895 packet_unref(result);
897 return NOTIFICATION_ERROR_SERVICE_NOT_READY;
903 notification_error_e notification_ipc_request_delete_multiple(notification_type_e type, char *pkgname)
907 struct packet *packet;
908 struct packet *result;
910 packet = packet_create("del_noti_multiple", "si", pkgname, type);
911 result = com_core_packet_oneshot_send(NOTIFICATION_ADDR,
913 NOTIFICATION_IPC_TIMEOUT);
914 packet_destroy(packet);
916 if (result != NULL) {
917 if (packet_get(result, "ii", &status, &num_deleted) != 2) {
918 NOTIFICATION_ERR("Failed to get a result packet");
919 packet_unref(result);
920 return NOTIFICATION_ERROR_IO;
922 NOTIFICATION_ERR("num deleted:%d", num_deleted);
923 packet_unref(result);
925 return NOTIFICATION_ERROR_SERVICE_NOT_READY;
931 notification_error_e notification_ipc_request_update(notification_h noti)
934 int id = NOTIFICATION_PRIV_ID_NONE;
935 struct packet *packet;
936 struct packet *result;
938 packet = notification_ipc_make_packet_from_noti(noti, "update_noti", 1);
939 result = com_core_packet_oneshot_send(NOTIFICATION_ADDR,
941 NOTIFICATION_IPC_TIMEOUT);
942 packet_destroy(packet);
944 if (result != NULL) {
945 if (packet_get(result, "ii", &status, &id) != 2) {
946 NOTIFICATION_ERR("Failed to get a result packet");
947 packet_unref(result);
948 return NOTIFICATION_ERROR_IO;
950 packet_unref(result);
952 return NOTIFICATION_ERROR_SERVICE_NOT_READY;
958 static int _notification_ipc_update_cb(pid_t pid, int handle, const struct packet *packet, void *data)
961 int id = NOTIFICATION_PRIV_ID_NONE;
962 result_cb_item *cb_item = (result_cb_item *)data;
964 if (cb_item == NULL) {
965 NOTIFICATION_ERR("Failed to get a callback item");
966 return NOTIFICATION_ERROR_INVALID_DATA;
968 s_info.server_cl_fd_ref_cnt = (s_info.server_cl_fd_ref_cnt <= 1) ? 0 : s_info.server_cl_fd_ref_cnt - 1;
969 if (s_info.server_cl_fd_ref_cnt <= 0) {
970 NOTIFICATION_DBG("REFCNT: %d (fd: %d)", s_info.server_cl_fd_ref_cnt, s_info.server_cl_fd);
971 int fd_temp = s_info.server_cl_fd;
972 s_info.server_cl_fd = -1;
973 com_core_packet_client_fini(fd_temp);
974 NOTIFICATION_DBG("FD(%d) finalized", fd_temp);
977 if (packet != NULL) {
978 if (packet_get(packet, "ii", &status, &id) != 2) {
979 NOTIFICATION_ERR("Failed to get a result packet");
980 status = NOTIFICATION_ERROR_IO;
984 if (cb_item->result_cb != NULL) {
985 cb_item->result_cb(id, status, cb_item->data);
992 notification_error_e notification_ipc_request_update_async(notification_h noti,
993 void (*result_cb)(int priv_id, int result, void *data), void *user_data)
995 int ret = NOTIFICATION_ERROR_NONE;
997 struct packet *packet = NULL;
998 result_cb_item *cb_item = NULL;
1000 packet = notification_ipc_make_packet_from_noti(noti, "update_noti", 1);
1001 if (packet == NULL) {
1002 ret = NOTIFICATION_ERROR_INVALID_DATA;
1006 cb_item = calloc(1, sizeof(result_cb_item));
1007 if (cb_item == NULL) {
1008 ret = NOTIFICATION_ERROR_NO_MEMORY;
1012 if (s_info.server_cl_fd < 0) {
1013 com_core_packet_use_thread(1);
1014 s_info.server_cl_fd = com_core_packet_client_init(s_info.socket_file, 0, NULL);
1015 if (s_info.server_cl_fd < 0) {
1016 NOTIFICATION_DBG("Failed to init client: %d", s_info.server_cl_fd);
1017 ret = NOTIFICATION_ERROR_SERVICE_NOT_READY;
1020 s_info.server_cl_fd_ref_cnt = 1;
1022 s_info.server_cl_fd_ref_cnt++;
1025 cb_item->result_cb = result_cb;
1026 cb_item->data = user_data;
1028 NOTIFICATION_INFO("Connection count:%d, fd:%d", s_info.server_cl_fd_ref_cnt, s_info.server_cl_fd);
1030 ret_con = com_core_packet_async_send(s_info.server_cl_fd, packet, 0.0f,
1031 _notification_ipc_update_cb, cb_item);
1033 NOTIFICATION_ERR("Failed to request update, %d\n", ret_con);
1034 s_info.server_cl_fd_ref_cnt = (s_info.server_cl_fd_ref_cnt <= 1) ? 0 : s_info.server_cl_fd_ref_cnt - 1;
1035 if (s_info.server_cl_fd_ref_cnt <= 0) {
1036 int fd_temp = s_info.server_cl_fd;
1037 s_info.server_cl_fd = -1;
1038 com_core_packet_client_fini(fd_temp);
1039 NOTIFICATION_INFO("FD(%d) finalized", fd_temp);
1041 ret = NOTIFICATION_ERROR_IO;
1044 ret = NOTIFICATION_ERROR_NONE;
1049 if (cb_item) free(cb_item);
1050 NOTIFICATION_ERR("Err: %d\n", ret);
1053 if (packet) packet_destroy(packet);
1058 notification_error_e notification_ipc_request_refresh(void)
1061 struct packet *packet;
1062 struct packet *result;
1064 packet = packet_create("refresh_noti", "i", NOTIFICATION_OP_REFRESH);
1065 result = com_core_packet_oneshot_send(NOTIFICATION_ADDR,
1067 NOTIFICATION_IPC_TIMEOUT);
1068 packet_destroy(packet);
1070 if (result != NULL) {
1071 if (packet_get(result, "i", &status) != 1) {
1072 NOTIFICATION_ERR("Failed to get a result packet");
1073 packet_unref(result);
1074 return NOTIFICATION_ERROR_IO;
1076 packet_unref(result);
1078 return NOTIFICATION_ERROR_SERVICE_NOT_READY;
1084 notification_error_e notification_ipc_noti_setting_property_set(const char *pkgname, const char *property, const char *value)
1088 struct packet *packet;
1089 struct packet *result;
1091 packet = packet_create("set_noti_property", "sss", pkgname, property, value);
1092 result = com_core_packet_oneshot_send(NOTIFICATION_ADDR,
1094 NOTIFICATION_IPC_TIMEOUT);
1095 packet_destroy(packet);
1097 if (result != NULL) {
1098 if (packet_get(result, "ii", &status, &ret) != 2) {
1099 NOTIFICATION_ERR("Failed to get a result packet");
1100 packet_unref(result);
1101 return NOTIFICATION_ERROR_IO;
1103 packet_unref(result);
1105 return NOTIFICATION_ERROR_SERVICE_NOT_READY;
1111 notification_error_e notification_ipc_noti_setting_property_get(const char *pkgname, const char *property, char **value)
1115 struct packet *packet;
1116 struct packet *result;
1118 packet = packet_create("get_noti_property", "ss", pkgname, property);
1119 result = com_core_packet_oneshot_send(NOTIFICATION_ADDR,
1121 NOTIFICATION_IPC_TIMEOUT);
1122 packet_destroy(packet);
1124 if (result != NULL) {
1125 if (packet_get(result, "is", &status, &ret) != 2) {
1126 NOTIFICATION_ERR("Failed to get a result packet");
1127 packet_unref(result);
1128 return NOTIFICATION_ERROR_IO;
1130 if (status == NOTIFICATION_ERROR_NONE && ret != NULL) {
1131 *value = strdup(ret);
1133 packet_unref(result);
1135 return NOTIFICATION_ERROR_SERVICE_NOT_READY;