From 8563553b10ee0285c234e3b7e0b5899e90d859df Mon Sep 17 00:00:00 2001 From: Hwankyu Jhun Date: Wed, 19 Apr 2017 08:27:15 +0900 Subject: [PATCH] Modify app_context_set_status_cb API Requires: - https://review.tizen.org/gerrit/#/c/125770/ Change-Id: I251c53c5474eb30acaa5013731fc78577a67f1d8 Signed-off-by: Hwankyu Jhun --- include/app_manager_extension.h | 1 + src/app_context.c | 110 ++++++++++++++++++++++++++++++++-------- 2 files changed, 90 insertions(+), 21 deletions(-) diff --git a/include/app_manager_extension.h b/include/app_manager_extension.h index 2abe3e5..98b8fc9 100644 --- a/include/app_manager_extension.h +++ b/include/app_manager_extension.h @@ -98,6 +98,7 @@ int app_manager_set_splash_screen_display(const char *app_id, bool display); * @retval #APP_MANAGER_ERROR_NONE Successful * @retval #APP_MANAGER_ERROR_INVALID_PARAMETER Invalid parameter * @retval #APP_MANAGER_ERROR_IO_ERROR Internal I/O error + * @retval #APP_MANAGER_ERROR_OUT_OF_MEMORY Out of memory * @post It will invoke app_manager_app_context_event_cb() when the application is launched or terminated. * @see app_manager_app_context_status_cb() */ diff --git a/src/app_context.c b/src/app_context.c index 671ab1a..c312ced 100644 --- a/src/app_context.c +++ b/src/app_context.c @@ -66,7 +66,14 @@ typedef struct _retrieval_context_ { const char *instance_id; } retrieval_context_s; -static app_manager_app_context_status_cb _status_cb; +struct status_listen_info { + status_listen_h handle; + char *appid; + app_manager_app_context_status_cb callback; + void *user_data; +}; + +static GList *status_listen_list; static app_state_e app_context_get_app_status(int status) { @@ -625,24 +632,78 @@ void app_context_unset_event_cb(void) app_context_unlock_event_cb_context(); } -static int app_context_status_cb(const char *appid, const char *pkgid, int pid, int status, int is_subapp, void *data) +static struct status_listen_info *__find_status_listen_info(app_manager_app_context_status_cb callback, const char *appid) +{ + struct status_listen_info *info; + GList *iter; + + iter = g_list_first(status_listen_list); + while (iter) { + info = (struct status_listen_info *)iter->data; + if (info && info->callback == callback && !strcmp(info->appid, appid)) + return info; + iter = g_list_next(iter); + } + + return NULL; +} + +static struct status_listen_info *__create_status_listen_info(app_manager_app_context_status_cb callback, const char *appid, void *user_data) { + struct status_listen_info *info; + + info = calloc(1, sizeof(struct status_listen_info)); + if (info == NULL) { + LOGE("Out of memory"); + return NULL; + } + + info->appid = strdup(appid); + if (info->appid == NULL) { + LOGE("Out of memory"); + free(info); + return NULL; + } + + info->callback = callback; + info->user_data = user_data; + + return info; +} + +static void __destroy_status_listen_info(struct status_listen_info *info) +{ + if (info == NULL) + return; + + if (info->appid) + free(info->appid); + free(info); +} + +static int app_context_status_cb(aul_app_info *aul_app_context, int ctx_status, void *data) +{ + struct status_listen_info *info = (struct status_listen_info *)data; app_context_h app_context = NULL; - app_state_e state; app_context_status_e context_status; int ret; - state = app_context_get_app_status(status); - if (state == APP_STATE_TERMINATED) + if (ctx_status == STATUS_TERMINATE) context_status = APP_CONTEXT_STATUS_TERMINATED; else context_status = APP_CONTEXT_STATUS_LAUNCHED; - ret = app_context_create(appid, pid, pkgid, state, is_subapp, NULL, &app_context); + ret = app_context_create(aul_app_context->appid, + aul_app_context->pid, + aul_app_context->pkgid, + app_context_get_app_status(aul_app_context->status), + aul_app_context->is_sub_app, + aul_app_context->instance_id, + &app_context); if (ret != APP_MANAGER_ERROR_NONE) return app_manager_error(ret, __FUNCTION__, NULL); - _status_cb(app_context, context_status, data); + info->callback(app_context, context_status, info->user_data); app_context_destroy(app_context); return APP_MANAGER_ERROR_NONE; @@ -651,26 +712,33 @@ static int app_context_status_cb(const char *appid, const char *pkgid, int pid, int app_context_set_status_cb(app_manager_app_context_status_cb callback, const char *appid, void *user_data) { int ret; + struct status_listen_info *info; if (callback == NULL || appid == NULL) - return app_manager_error(APP_MANAGER_ERROR_INVALID_PARAMETER, __FUNCTION__, NULL); + return APP_MANAGER_ERROR_INVALID_PARAMETER; - _status_cb = callback; + info = __find_status_listen_info(callback, appid); + if (info) { + info->user_data = user_data; + return APP_MANAGER_ERROR_NONE; + } - ret = aul_listen_app_status(appid, app_context_status_cb, user_data); - switch (ret) { - case AUL_R_OK: - ret = APP_MANAGER_ERROR_NONE; - break; - case AUL_R_EINVAL: - ret = APP_MANAGER_ERROR_INVALID_PARAMETER; - break; - default: - ret = APP_MANAGER_ERROR_IO_ERROR; - break; + info = __create_status_listen_info(callback, appid, user_data); + if (info == NULL) + return APP_MANAGER_ERROR_OUT_OF_MEMORY; + + ret = aul_listen_app_status(appid, app_context_status_cb, info, &info->handle); + if (ret != AUL_R_OK) { + __destroy_status_listen_info(info); + if (ret == AUL_R_EINVAL) + return APP_MANAGER_ERROR_INVALID_PARAMETER; + + return APP_MANAGER_ERROR_IO_ERROR; } - return ret; + status_listen_list = g_list_append(status_listen_list, info); + + return APP_MANAGER_ERROR_NONE; } int app_context_get_app_context_by_instance_id(const char *app_id, const char *instance_id, app_context_h *app_context) -- 2.7.4