diff options
author | Hwankyu Jhun <h.jhun@samsung.com> | 2016-11-22 14:21:46 +0900 |
---|---|---|
committer | Hwankyu Jhun <h.jhun@samsung.com> | 2016-11-22 16:13:32 +0900 |
commit | 7902997f62d96e984368918db0e59338c341f5e2 (patch) | |
tree | 4bed12ae467843c7c81db3d4a116df777a510844 | |
parent | 6ff9c218950e0f19f6562c398a5aabe73297099b (diff) | |
download | aul-1-7902997f62d96e984368918db0e59338c341f5e2.tar.gz aul-1-7902997f62d96e984368918db0e59338c341f5e2.tar.bz2 aul-1-7902997f62d96e984368918db0e59338c341f5e2.zip |
Support allowed appid feature
- Add parser plugin to register allowed appid metadata
- Add new APIs to retrive all allowed information
Change-Id: I4ac8a21138615d12c844905e7e03d9fe5fa8c998
Signed-off-by: Hwankyu Jhun <h.jhun@samsung.com>
-rwxr-xr-x | data/appsvc_db.sql | 7 | ||||
-rwxr-xr-x | include/aul_svc.h | 34 | ||||
-rwxr-xr-x | include/aul_svc_db.h | 6 | ||||
-rw-r--r-- | parser/metadata_plugin_parser_db.c | 90 | ||||
-rw-r--r-- | parser/metadata_plugin_parser_db.h | 3 | ||||
-rw-r--r-- | parser/metadata_plugin_parser_handler.c | 42 | ||||
-rwxr-xr-x | scripts/101.appsvc_upgrade.sh | 7 | ||||
-rwxr-xr-x | src/service.c | 64 | ||||
-rwxr-xr-x | src/service_db.c | 195 |
9 files changed, 446 insertions, 2 deletions
diff --git a/data/appsvc_db.sql b/data/appsvc_db.sql index 23e80ae1..fc297b93 100755 --- a/data/appsvc_db.sql +++ b/data/appsvc_db.sql @@ -31,3 +31,10 @@ CREATE TRIGGER IF NOT EXISTS update_alias_info_for_uid DELETE FROM alias_info_for_uid WHERE is_enabled='true'; END; + +CREATE TABLE IF NOT EXISTS allowed_info ( + appid TEXT NOT NULL, + allowed_appid TEXT NOT NULL, + PRIMARY KEY (appid, allowed_appid) +); + diff --git a/include/aul_svc.h b/include/aul_svc.h index 325b9e22..440cc126 100755 --- a/include/aul_svc.h +++ b/include/aul_svc.h @@ -1208,6 +1208,7 @@ int aul_svc_get_appid_by_alias_appid_for_uid(const char *alias_appid, * This API retrieves all alias information based on the given appid. * * @param[in] callback The callback function to be invoked + * @param[in] appid An application ID * @param[in] user_data The user data to be passed to the callback function * * @return 0 if success, negative value(<0) if fail @@ -1219,6 +1220,39 @@ int aul_svc_foreach_alias_info_by_appid_for_uid(int (*callback)( const char *alias_appid, const char *appid, void *data), const char *appid, uid_t uid, void *user_data); +/** + * @par Description: + * This API retrieves all allowed information. + * + * @param[in] callback The callback function to be invoked + * @param[in] user_data The user data to be passed to the callback function + * + * @return 0 if success, negative value(<0) if fail + */ +int aul_svc_foreach_allowed_info(int (*callback)(const char *appid, + const char *allowed_appid, void *data), + void *user_data); +int aul_svc_foreach_allowed_info_for_uid(int (*callback)(const char *appid, + const char *allowed_appid, void *data), + uid_t uid, void *user_data); + +/** + * @par Description: + * This API retrieves all allowed information based on the given appid. + * + * @param[in] callback The callback function to be invoked + * @param[in] appid An application ID + * @param[in] user_data The user data to be passed to the callback function + * + * @return 0 if success, negative value(<0) if fail + */ +int aul_svc_foreach_allowed_info_by_appid(int (*callback)( + const char *appid, const char *allowed_appid, void *data), + const char *appid, void *user_data); +int aul_svc_foreach_allowed_info_by_appid_for_uid(int (*callback)( + const char *appid, const char *allowed_appid, void *data), + const char *appid, uid_t uid, void *user_data); + #ifdef __cplusplus } #endif diff --git a/include/aul_svc_db.h b/include/aul_svc_db.h index 6dcd800f..28731728 100755 --- a/include/aul_svc_db.h +++ b/include/aul_svc_db.h @@ -63,6 +63,12 @@ int _svc_db_disable_alias_info(const char *appid, uid_t uid); int _svc_db_foreach_alias_info_by_appid(int (*callback)( const char *alias_appid, const char *appid, void *data), const char *appid, uid_t uid, void *user_data); +int _svc_db_foreach_allowed_info(int (*callback)(const char *appid, + const char *allowed_appid, void *data), + uid_t uid, void *user_data); +int _svc_db_foreach_allowed_info_by_appid(int (*callback)(const char *appid, + const char *allowed_appid, void *data), + const char *appid, uid_t uid, void *user_data); #ifdef __cplusplus } diff --git a/parser/metadata_plugin_parser_db.c b/parser/metadata_plugin_parser_db.c index 2fcd998d..8a03e118 100644 --- a/parser/metadata_plugin_parser_db.c +++ b/parser/metadata_plugin_parser_db.c @@ -198,3 +198,93 @@ end: return result; } + +int metadata_parser_db_insert_allowed_info(const char *appid, + const char *allowed_appid) +{ + int ret; + int result = 0; + sqlite3_stmt *stmt = NULL; + const char *query = + "INSERT OR REPLACE INTO allowed_info(appid, allowed_appid) " \ + "values(?,?);"; + + if (allowed_appid == NULL || appid == NULL) { + LOGE("Invalid parameters"); + return -1; + } + + ret = sqlite3_prepare_v2(appsvc_db, query, strlen(query), &stmt, NULL); + if (ret != SQLITE_OK) { + LOGE("sqlite3_prepare_v2() error: %d(%s)", + ret, sqlite3_errmsg(appsvc_db)); + return -1; + } + + ret = sqlite3_bind_text(stmt, 1, appid, -1, SQLITE_TRANSIENT); + if (ret != SQLITE_OK) { + LOGE("sqlite3_bind_text() error: %d(%s)", + ret, sqlite3_errmsg(appsvc_db)); + result = -1; + goto end; + } + + ret = sqlite3_bind_text(stmt, 2, allowed_appid, -1, SQLITE_TRANSIENT); + if (ret != SQLITE_OK) { + LOGE("sqlite3_bind_text() error: %d(%s)", + ret, sqlite3_errmsg(appsvc_db)); + result = -1; + goto end; + } + + ret = sqlite3_step(stmt); + if (ret != SQLITE_DONE) { + LOGE("sqlite3_step() error: %d(%s)", + ret, sqlite3_errmsg(appsvc_db)); + result = -1; + } + +end: + sqlite3_finalize(stmt); + + return result; +} + +int metadata_parser_db_delete_allowed_info(const char *appid) +{ + int ret; + int result = 0; + sqlite3_stmt *stmt = NULL; + const char *query = "DELETE FROM allowed_info WHERE appid = ?;"; + + if (appid == NULL) { + LOGE("Invalid parameter"); + return -1; + } + + ret = sqlite3_prepare_v2(appsvc_db, query, strlen(query), &stmt, NULL); + if (ret != SQLITE_OK) { + LOGE("sqlite3_prepare_v2() error: %d(%s)", + ret, sqlite3_errmsg(appsvc_db)); + return -1; + } + + ret = sqlite3_bind_text(stmt, 1, appid, -1, SQLITE_TRANSIENT); + if (ret != SQLITE_OK) { + LOGE("sqlite3_bind_text() error: %d(%s)", + ret, sqlite3_errmsg(appsvc_db)); + result = -1; + goto end; + } + + ret = sqlite3_step(stmt); + if (ret != SQLITE_DONE) { + LOGW("sqlite3_step() error: %d(%s)", + ret, sqlite3_errmsg(appsvc_db)); + } + +end: + sqlite3_finalize(stmt); + + return result; +} diff --git a/parser/metadata_plugin_parser_db.h b/parser/metadata_plugin_parser_db.h index b133abb8..c190bdca 100644 --- a/parser/metadata_plugin_parser_db.h +++ b/parser/metadata_plugin_parser_db.h @@ -20,6 +20,9 @@ int metadata_parser_db_insert_alias_info(const char *alias_appid, const char *appid); int metadata_parser_db_delete_alias_info(const char *appid); +int metadata_parser_db_insert_allowed_info(const char *appid, + const char *allowed_appid); +int metadata_parser_db_delete_allowed_info(const char *appid); int metadata_parser_db_init(void); void metadata_parser_db_fini(void); diff --git a/parser/metadata_plugin_parser_handler.c b/parser/metadata_plugin_parser_handler.c index e3281b8d..85839036 100644 --- a/parser/metadata_plugin_parser_handler.c +++ b/parser/metadata_plugin_parser_handler.c @@ -43,6 +43,7 @@ typedef struct metadater_parser_dispatcher_s { enum metadata_key { KEY_NONE, KEY_ALIAS_APPID, + KEY_ALLOWED_APPID, KEY_MAX, }; @@ -55,6 +56,10 @@ struct key_map map[] = { { KEY_ALIAS_APPID, "http://tizen.org/metadata/aliasappid" + }, + { + KEY_ALLOWED_APPID, + "http://tizen.org/metadata/allowedappid" } }; @@ -148,11 +153,48 @@ static int __uninstall_alias_info(const char *appid) return 0; } +static int __install_allowed_info(const char *appid, + const char *key, const char *value) +{ + int ret; + + if (appid == NULL || key == NULL || value == NULL) { + LOGE("Invalid parameter"); + return -1; + } + + ret = metadata_parser_db_insert_allowed_info(appid, value); + if (ret < 0) + return -1; + + return 0; +} + +static int __uninstall_allowed_info(const char *appid) +{ + int ret; + + if (appid == NULL) { + LOGE("Invalid parameter"); + return -1; + } + + ret = metadata_parser_db_delete_allowed_info(appid); + if (ret < 0) + return -1; + + return 0; +} + static metadata_parser_dispatcher dispatch_table[KEY_MAX] = { [KEY_ALIAS_APPID] = { .install = __install_alias_info, .uninstall = __uninstall_alias_info, }, + [KEY_ALLOWED_APPID] = { + .install = __install_allowed_info, + .uninstall = __uninstall_allowed_info, + } }; int metadata_parser_handler_install(const char *appid, diff --git a/scripts/101.appsvc_upgrade.sh b/scripts/101.appsvc_upgrade.sh index 9ac91246..29596d7e 100755 --- a/scripts/101.appsvc_upgrade.sh +++ b/scripts/101.appsvc_upgrade.sh @@ -37,6 +37,13 @@ CREATE TRIGGER IF NOT EXISTS update_alias_info_for_uid DELETE FROM alias_info_for_uid WHERE is_enabled='true'; END; + +CREATE TABLE IF NOT EXISTS allowed_info ( + appid TEXT NOT NULL, + allowed_appid TEXT NOT NULL, + PRIMARY KEY (appid, allowed_appid) +); + EOF # Copy DB diff --git a/src/service.c b/src/service.c index 965ac6ce..31f538df 100755 --- a/src/service.c +++ b/src/service.c @@ -1583,3 +1583,67 @@ API int aul_svc_foreach_alias_info_by_appid_for_uid(int (*callback)( return AUL_SVC_RET_OK; } + +API int aul_svc_foreach_allowed_info(int (*callback)(const char *appid, + const char *allowed_appid, void *data), void *user_data) +{ + return aul_svc_foreach_allowed_info_for_uid(callback, + getuid(), user_data); +} + +API int aul_svc_foreach_allowed_info_for_uid(int (*callback)(const char *appid, + const char *allowed_appid, void *data), + uid_t uid, void *user_data) +{ + int ret; + + if (callback == NULL) { + _E("Invalid parameter"); + return AUL_SVC_RET_EINVAL; + } + + ret = _svc_db_check_perm(uid, true); + if (ret < 0) { + _E("Permission error: %d", ret); + return AUL_SVC_RET_EILLACC; + } + + ret = _svc_db_foreach_allowed_info(callback, uid, user_data); + if (ret < 0) + return AUL_SVC_RET_ERROR; + + return AUL_SVC_RET_OK; +} + +API int aul_svc_foreach_allowed_info_by_appid(int (*callback)( + const char *appid, const char *allowed_appid, void *data), + const char *appid, void *user_data) +{ + return aul_svc_foreach_allowed_info_by_appid_for_uid(callback, + appid, getuid(), user_data); +} + +API int aul_svc_foreach_allowed_info_by_appid_for_uid(int (*callback)( + const char *appid, const char *allowed_appid, void *data), + const char *appid, uid_t uid, void *user_data) +{ + int ret; + + if (callback == NULL || appid == NULL) { + _E("Invalid parameter"); + return AUL_SVC_RET_EINVAL; + } + + ret = _svc_db_check_perm(uid, true); + if (ret < 0) { + _E("Permission error: %d", ret); + return AUL_SVC_RET_EILLACC; + } + + ret = _svc_db_foreach_allowed_info_by_appid(callback, appid, + uid, user_data); + if (ret < 0) + return AUL_SVC_RET_ERROR; + + return AUL_SVC_RET_OK; +} diff --git a/src/service_db.c b/src/service_db.c index 54d69332..b6ce24c1 100755 --- a/src/service_db.c +++ b/src/service_db.c @@ -55,8 +55,14 @@ struct alias_info_s { char *appid; }; -static sqlite3 *svc_db = NULL; -static sqlite3 *app_info_db = NULL; +struct allowed_info_s { + uid_t uid; + char *appid; + char *allowed_appid; +}; + +static sqlite3 *svc_db; +static sqlite3 *app_info_db; static int __attach_create_view_appinfo_db(sqlite3 *handle, uid_t uid) { @@ -1366,3 +1372,188 @@ int _svc_db_foreach_alias_info_by_appid(int (*callback)( return 0; } + +static int __get_allowed_info_list(const char *appid, uid_t uid, + uid_t db_uid, GHashTable *tbl) +{ + int ret; + sqlite3_stmt *stmt = NULL; + const char *query; + const char *id; + const char *allowed_id; + struct allowed_info_s *info; + GList *list; + GList *iter; + + if (__init(db_uid, true) < 0) + return -1; + + if (appid) { + query = "SELECT appid, allowed_appid FROM allowed_info WHERE " \ + "appid = ?;"; + } else { + query = "SELECT appid, allowed_appid FROM allowed_info;"; + } + + ret = sqlite3_prepare_v2(svc_db, query, strlen(query), &stmt, NULL); + if (ret != SQLITE_OK) { + _E("sqlite3_prepare_v2() error - %s(%d)", + sqlite3_errmsg(svc_db), ret); + __fini(); + return -1; + } + + if (appid) { + ret = sqlite3_bind_text(stmt, 1, appid, -1, SQLITE_TRANSIENT); + if (ret != SQLITE_OK) { + _E("sqlite3_bind_text() error - %s(%d)", + sqlite3_errmsg(svc_db), ret); + sqlite3_finalize(stmt); + __fini(); + return -1; + } + } + + while (sqlite3_step(stmt) == SQLITE_ROW) { + id = (const char *)sqlite3_column_text(stmt, 0); + if (id == NULL) { + _E("Failed to get appid"); + break; + } + + allowed_id = (const char *)sqlite3_column_text(stmt, 1); + if (allowed_id == NULL) { + _E("Failed to get allowed appid"); + break; + } + + list = g_hash_table_lookup(tbl, id); + if (list) { + iter = g_list_first(list); + if (iter) { + info = (struct allowed_info_s *)iter->data; + if (info && info->uid != db_uid) + continue; + } + } + + info = malloc(sizeof(struct allowed_info_s)); + if (info == NULL) { + _E("out of memory"); + break; + } + + info->uid = db_uid; + info->appid = strdup(id); + if (info->appid == NULL) { + _E("out of memory"); + free(info); + break; + } + + info->allowed_appid = strdup(allowed_id); + if (info->allowed_appid == NULL) { + _E("out of memory"); + free(info->appid); + free(info); + break; + } + + if (list) { + list = g_list_append(list, info); + } else { + list = g_list_append(list, info); + g_hash_table_insert(tbl, info->appid, list); + } + } + + sqlite3_finalize(stmt); + __fini(); + + return 0; +} + +static void __destroy_allowed_info(gpointer data) +{ + struct allowed_info_s *info = (struct allowed_info_s *)data; + + if (info == NULL) + return; + + if (info->allowed_appid) + free(info->allowed_appid); + if (info->appid) + free(info->appid); + free(info); +} + +static void __destroy_allowed_info_list(gpointer data) +{ + GList *list = (GList *)data; + + if (list == NULL) + return; + + g_list_free_full(list, __destroy_allowed_info); +} + +int _svc_db_foreach_allowed_info_by_appid(int (*callback)(const char *appid, + const char *allowed_appid, void *data), + const char *appid, uid_t uid, void *user_data) +{ + int ret; + GHashTable *tbl; + GHashTableIter hash_iter; + gpointer value = NULL; + struct allowed_info_s *info; + bool invoked = false; + GList *list; + GList *iter; + + tbl = g_hash_table_new_full(g_str_hash, g_str_equal, NULL, + __destroy_allowed_info_list); + if (tbl == NULL) { + _E("out of memory"); + return -1; + } + + ret = __get_allowed_info_list(appid, uid, uid, tbl); + if (ret == 0 && uid != GLOBAL_USER) + ret = __get_allowed_info_list(appid, uid, GLOBAL_USER, tbl); + + if (ret != 0) { + _E("Failed to get allowed info table"); + g_hash_table_destroy(tbl); + return -1; + } + + g_hash_table_iter_init(&hash_iter, tbl); + while (g_hash_table_iter_next(&hash_iter, NULL, &value)) { + list = (GList *)value; + if (list) { + iter = g_list_first(list); + while (iter) { + info = (struct allowed_info_s *)iter->data; + if (info) + callback(info->appid, info->allowed_appid, user_data); + iter = g_list_next(iter); + } + } + invoked = true; + value = NULL; + } + g_hash_table_destroy(tbl); + + if (!invoked) + _W("allowed info is empty"); + + return 0; +} + +int _svc_db_foreach_allowed_info(int (*callback)(const char *appid, + const char *allowed_appid, void *data), + uid_t uid, void *user_data) +{ + return _svc_db_foreach_allowed_info_by_appid(callback, NULL, + uid, user_data); +} |