4 * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved.
6 * Contact: Jayoun Lee <airjany@samsung.com>, Sewook Park <sewook7.park@samsung.com>, Jaeho Lee <jaeho81.lee@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 <tzplatform_config.h>
30 #include "ail_private.h"
31 #include "ail_convert.h"
34 #include "ail_package.h"
38 #define LANGUAGE_LENGTH 2
39 #define DEFAULT_LOCALE "No Locale"
40 #define MAX_QUERY_LEN 4096
41 #define PKG_SD_PATH tzplatform_mkpath(TZ_SYS_STORAGE, "sdcard/app2sd/")
42 #define QUERY_GET_LOCALNAME "select name from localname where package='%s' and locale='%s'"
49 typedef struct _pkgmgr_locale_x {
54 /* get the first locale value*/
55 static int __fallback_locale_cb(void *data, int ncols, char **coltxt, char **colname)
57 pkgmgr_locale_x *info = (pkgmgr_locale_x *)data;
60 info->locale = strdup(coltxt[0]);
67 static int __check_validation_of_query_cb(void *data, int ncols, char **coltxt, char **colname)
74 static int __check_app_locale_from_app_localized_info_by_exact(const char *appid, const char *locale)
76 int result_query = -1;
77 char query[MAX_QUERY_LEN];
79 snprintf(query, MAX_QUERY_LEN, "select exists(select locale from localname where package='%s' and locale='%s')", appid, locale);
80 db_exec_sqlite_query(query, __check_validation_of_query_cb, (void *)&result_query);
85 static int __check_app_locale_from_app_localized_info_by_fallback(const char *appid, const char *locale)
87 int result_query = -1;
88 char wildcard[2] = {'%','\0'};
89 char query[MAX_QUERY_LEN];
90 char lang[3] = {'\0'};
91 strncpy(lang, locale, LANGUAGE_LENGTH);
93 snprintf(query, MAX_QUERY_LEN, "select exists(select locale from localname where package='%s' and locale like '%s%s')", appid, lang, wildcard);
94 db_exec_sqlite_query(query, __check_validation_of_query_cb, (void *)&result_query);
99 static char* __get_app_locale_from_app_localized_info_by_fallback(const char *appid, const char *locale)
101 char wildcard[2] = {'%','\0'};
102 char lang[3] = {'\0'};
103 char query[MAX_QUERY_LEN];
104 char *locale_new = NULL;
105 pkgmgr_locale_x *info = NULL;
107 info = (pkgmgr_locale_x *)malloc(sizeof(pkgmgr_locale_x));
109 _E("Out of Memory!!!\n");
112 memset(info, NULL, sizeof(*info));
114 strncpy(lang, locale, 2);
115 snprintf(query, MAX_QUERY_LEN, "select locale from localname where package='%s' and locale like '%s%s'", appid, lang, wildcard);
116 db_exec_sqlite_query(query, __fallback_locale_cb, (void *)info);
117 locale_new = info->locale;
123 static char* __convert_syslocale_to_manifest_locale(char *syslocale)
125 char *locale = malloc(6);
127 _E("Malloc Failed\n");
131 snprintf(locale, 6, "%c%c_%c%c", syslocale[0], syslocale[1], toupper(syslocale[3]), toupper(syslocale[4]));
135 static char* __get_app_locale_by_fallback(const char *appid, const char *syslocale)
141 char *locale_new = NULL;
142 int check_result = 0;
144 locale = __convert_syslocale_to_manifest_locale(syslocale);
146 /*check exact matching */
147 check_result = __check_app_locale_from_app_localized_info_by_exact(appid, locale);
150 if (check_result == 1) {
151 _D("%s find exact locale(%s)\n", appid, locale);
155 /* fallback matching */
156 check_result = __check_app_locale_from_app_localized_info_by_fallback(appid, locale);
157 if(check_result == 1) {
158 locale_new = __get_app_locale_from_app_localized_info_by_fallback(appid, locale);
159 _D("%s found (%s) language-locale in DB by fallback!\n", appid, locale_new);
161 if (locale_new == NULL)
162 locale_new = strdup(DEFAULT_LOCALE);
168 _D("%s DEFAULT_LOCALE)\n", appid);
169 return strdup(DEFAULT_LOCALE);
172 static ail_error_e __retrieve_all_column(ail_appinfo_h ai)
178 retv_if(!ai, AIL_ERROR_INVALID_PARAMETER);
179 retv_if(!ai->stmt, AIL_ERROR_INVALID_PARAMETER);
181 ai->values = calloc(NUM_OF_PROP, sizeof(char *));
182 retv_if(!ai->values, AIL_ERROR_OUT_OF_MEMORY);
184 for (i = 0; i < NUM_OF_PROP; i++) {
185 err = db_column_str(ai->stmt, i, &col);
186 if (AIL_ERROR_OK != err)
190 ai->values[i] = NULL;
192 ai->values[i] = strdup(col);
193 if (!ai->values[i]) {
194 err = AIL_ERROR_OUT_OF_MEMORY;
201 for (j = 0; j < i; ++j) {
212 int _appinfo_check_installed_storage(ail_appinfo_h ai)
215 ail_prop_str_e prop = -1;
217 char *installed_storage = NULL;
218 char buf[AIL_SQL_QUERY_MAX_LEN] = {'\0'};
220 retv_if(!ai, AIL_ERROR_OK);
223 prop = _ail_convert_to_prop_str(AIL_PROP_X_SLP_INSTALLEDSTORAGE_STR);
224 index = sql_get_app_info_idx(prop);
225 if (db_column_str(ai->stmt, index, &installed_storage) < 0){
229 prop = _ail_convert_to_prop_str(AIL_PROP_X_SLP_PKGID_STR);
230 index = sql_get_app_info_idx(prop);
231 if (db_column_str(ai->stmt, index, &pkgid) < 0){
235 prop = _ail_convert_to_prop_str(AIL_PROP_X_SLP_INSTALLEDSTORAGE_STR);
236 installed_storage = ai->values[prop];
238 prop = _ail_convert_to_prop_str(AIL_PROP_X_SLP_PKGID_STR);
239 pkgid = ai->values[prop];
242 if (strcmp(installed_storage, "installed_external") == 0) {
243 snprintf(buf, AIL_SQL_QUERY_MAX_LEN - 1, "%s%s", PKG_SD_PATH, pkgid);
244 if (access(buf, R_OK) != 0) {
245 _E("can not access [%s]", buf);
246 return AIL_ERROR_OK;//tmep, it will be fixed to :: return AIL_ERROR_FAIL;
253 void appinfo_set_stmt(ail_appinfo_h ai, sqlite3_stmt *stmt)
258 ail_appinfo_h appinfo_create(void)
261 ai = calloc(1, sizeof(struct ail_appinfo));
262 retv_if (NULL == ai, NULL);
268 void appinfo_destroy(ail_appinfo_h ai)
274 EXPORT_API ail_error_e ail_package_destroy_appinfo(ail_appinfo_h ai)
276 return ail_destroy_appinfo(ai);
279 EXPORT_API ail_error_e ail_destroy_appinfo(ail_appinfo_h ai)
283 retv_if(!ai, AIL_ERROR_INVALID_PARAMETER);
284 retv_if(!ai->values, AIL_ERROR_INVALID_PARAMETER);
286 for (i = 0; i < NUM_OF_PROP; i++) {
299 EXPORT_API ail_error_e ail_package_get_appinfo(const char *package, ail_appinfo_h *ai)
301 return ail_get_appinfo(package, ai);
304 EXPORT_API ail_error_e ail_package_get_usr_appinfo(const char *package, uid_t uid, ail_appinfo_h *ai)
306 return ail_get_usr_appinfo(package, uid, ai);
309 EXPORT_API ail_error_e ail_get_appinfo(const char *appid, ail_appinfo_h *ai)
312 char query[AIL_SQL_QUERY_MAX_LEN];
313 sqlite3_stmt *stmt = NULL;
314 char w[AIL_SQL_QUERY_MAX_LEN];
317 retv_if(!appid, AIL_ERROR_INVALID_PARAMETER);
318 retv_if(!ai, AIL_ERROR_INVALID_PARAMETER);
320 *ai = appinfo_create();
321 retv_if(!*ai, AIL_ERROR_OUT_OF_MEMORY);
323 filter = sql_get_filter(E_AIL_PROP_X_SLP_APPID_STR);
324 if (filter == NULL) {
325 appinfo_destroy(*ai);
326 return AIL_ERROR_FAIL;
329 snprintf(w, sizeof(w), filter, appid);
330 snprintf(query, sizeof(query), "SELECT %s FROM %s WHERE %s",
331 SQL_FLD_APP_INFO, SQL_TBL_APP_INFO, w);
334 ret = db_open(DB_OPEN_RO, GLOBAL_USER);
339 ret = db_prepare_globalro(query, &stmt);
351 ret = _appinfo_check_installed_storage(*ai);
353 db_finalize((*ai)->stmt);
357 ret = __retrieve_all_column(*ai);
359 db_finalize((*ai)->stmt);
363 ret = db_finalize((*ai)->stmt);
372 appinfo_destroy(*ai);
377 EXPORT_API ail_error_e ail_get_usr_appinfo(const char *appid, uid_t uid, ail_appinfo_h *ai)
380 char query[AIL_SQL_QUERY_MAX_LEN];
381 sqlite3_stmt *stmt = NULL;
382 char w[AIL_SQL_QUERY_MAX_LEN];
385 retv_if(!appid, AIL_ERROR_INVALID_PARAMETER);
386 retv_if(!ai, AIL_ERROR_INVALID_PARAMETER);
388 *ai = appinfo_create();
389 retv_if(!*ai, AIL_ERROR_OUT_OF_MEMORY);
391 filter = sql_get_filter(E_AIL_PROP_X_SLP_APPID_STR);
392 if (filter == NULL) {
393 appinfo_destroy(*ai);
394 return AIL_ERROR_FAIL;
397 snprintf(w, sizeof(w), filter, appid);
398 snprintf(query, sizeof(query), "SELECT %s FROM %s WHERE %s",
399 SQL_FLD_APP_INFO, SQL_TBL_APP_INFO, w);
402 ret = db_open(DB_OPEN_RO, uid);
407 ret = db_prepare(query, &stmt);
419 ret = _appinfo_check_installed_storage(*ai);
421 db_finalize((*ai)->stmt);
425 ret = __retrieve_all_column(*ai);
427 db_finalize((*ai)->stmt);
431 ret = db_finalize((*ai)->stmt);
440 appinfo_destroy(*ai);
445 EXPORT_API ail_error_e ail_appinfo_get_bool(const ail_appinfo_h ai, const char *property, bool *value)
447 ail_prop_bool_e prop;
450 retv_if(!ai, AIL_ERROR_INVALID_PARAMETER);
451 retv_if(!property, AIL_ERROR_INVALID_PARAMETER);
452 retv_if(!value, AIL_ERROR_INVALID_PARAMETER);
454 prop = _ail_convert_to_prop_bool(property);
456 if (prop < E_AIL_PROP_BOOL_MIN || prop > E_AIL_PROP_BOOL_MAX)
457 return AIL_ERROR_INVALID_PARAMETER;
461 index = sql_get_app_info_idx(prop);
462 if (db_column_bool(ai->stmt, index, value) < 0)
463 return AIL_ERROR_DB_FAILED;
465 val = atoi(ai->values[prop]);
466 *value = (val == 0? false : true);
471 EXPORT_API ail_error_e ail_appinfo_get_int(const ail_appinfo_h ai, const char *property, int *value)
475 retv_if(!ai, AIL_ERROR_INVALID_PARAMETER);
476 retv_if(!property, AIL_ERROR_INVALID_PARAMETER);
477 retv_if(!value, AIL_ERROR_INVALID_PARAMETER);
479 prop = _ail_convert_to_prop_int(property);
481 if (prop < E_AIL_PROP_INT_MIN || prop > E_AIL_PROP_INT_MAX)
482 return AIL_ERROR_INVALID_PARAMETER;
486 index = sql_get_app_info_idx(prop);
487 if (db_column_int(ai->stmt, index, value) < 0)
488 return AIL_ERROR_DB_FAILED;
490 *value = atoi(ai->values[prop]);
495 char *appinfo_get_localname(const char *package, char *locale, uid_t uid)
497 db_open(DB_OPEN_RO, uid);
503 snprintf(query, sizeof(query), QUERY_GET_LOCALNAME, package, locale);
505 if (uid != GLOBAL_USER)
506 retv_if (db_prepare(query, &stmt) < 0, NULL);
508 retv_if (db_prepare_globalro(query, &stmt) < 0, NULL);
511 if (db_step(stmt) < 0)
513 if (db_column_str(stmt, 0, &str) < 0)
516 localname = strdup(str);
529 EXPORT_API ail_error_e ail_appinfo_get_str(const ail_appinfo_h ai, const char *property, char **str)
535 char *locale, *localname;
539 retv_if(!ai, AIL_ERROR_INVALID_PARAMETER);
540 retv_if(!property, AIL_ERROR_INVALID_PARAMETER);
541 retv_if(!str, AIL_ERROR_INVALID_PARAMETER);
543 prop = _ail_convert_to_prop_str(property);
545 if (prop < E_AIL_PROP_STR_MIN || prop > E_AIL_PROP_STR_MAX)
546 return AIL_ERROR_INVALID_PARAMETER;
550 if (E_AIL_PROP_NAME_STR == prop) {
552 if (db_column_str(ai->stmt, E_AIL_PROP_X_SLP_PACKAGETYPE_STR, &pkg_type) < 0)
553 return AIL_ERROR_DB_FAILED;
554 if(pkg_type && (strcasecmp(pkg_type, "tpk") ==0))
556 locale = sql_get_locale();
557 retv_if (NULL == locale, AIL_ERROR_FAIL);
559 if (db_column_str(ai->stmt, E_AIL_PROP_PACKAGE_STR, &pkg) < 0){
561 return AIL_ERROR_DB_FAILED;
565 return AIL_ERROR_DB_FAILED;
568 locale_new = __get_app_locale_by_fallback(pkg, locale);
569 localname = (char *)appinfo_get_localname(pkg, locale_new, GLOBAL_USER);
573 if (db_column_str(ai->stmt, SQL_LOCALNAME_IDX, &localname) < 0)
574 return AIL_ERROR_DB_FAILED;
577 pkg_type = ai->values[E_AIL_PROP_X_SLP_PACKAGETYPE_STR];
578 pkg = ai->values[E_AIL_PROP_PACKAGE_STR];
579 retv_if (NULL == pkg, AIL_ERROR_FAIL);
581 locale = sql_get_locale();
582 retv_if (NULL == locale, AIL_ERROR_FAIL);
584 if(pkg_type && (strcasecmp(pkg_type, "tpk") ==0))
586 locale_new = __get_app_locale_by_fallback(pkg, locale);
587 localname = (char *)appinfo_get_localname(pkg, locale_new, GLOBAL_USER);
591 localname = (char *)appinfo_get_localname(pkg, locale, GLOBAL_USER);
599 if (ai->values[prop])
600 free(ai->values[prop]);
601 ai->values[prop] = localname;
610 index = sql_get_app_info_idx(prop);
611 if (db_column_str(ai->stmt, index, &value) < 0){
612 return AIL_ERROR_DB_FAILED;
616 *str = ai->values[prop];
620 EXPORT_API ail_error_e ail_appinfo_get_usr_str(const ail_appinfo_h ai, const char *property, uid_t uid, char **str)
626 char *locale, *localname;
630 retv_if(!ai, AIL_ERROR_INVALID_PARAMETER);
631 retv_if(!property, AIL_ERROR_INVALID_PARAMETER);
632 retv_if(!str, AIL_ERROR_INVALID_PARAMETER);
634 prop = _ail_convert_to_prop_str(property);
636 if (prop < E_AIL_PROP_STR_MIN || prop > E_AIL_PROP_STR_MAX)
637 return AIL_ERROR_INVALID_PARAMETER;
641 if (E_AIL_PROP_NAME_STR == prop) {
643 if (db_column_str(ai->stmt, E_AIL_PROP_X_SLP_PACKAGETYPE_STR, &pkg_type) < 0)
644 return AIL_ERROR_DB_FAILED;
645 if(pkg_type && (strcasecmp(pkg_type, "tpk") ==0))
647 locale = sql_get_locale();
648 retv_if (NULL == locale, AIL_ERROR_FAIL);
650 if (db_column_str(ai->stmt, E_AIL_PROP_PACKAGE_STR, &pkg) < 0){
652 return AIL_ERROR_DB_FAILED;
656 return AIL_ERROR_DB_FAILED;
659 locale_new = __get_app_locale_by_fallback(pkg, locale);
660 localname = (char *)appinfo_get_localname(pkg, locale_new, uid);
664 if (db_column_str(ai->stmt, SQL_LOCALNAME_IDX, &localname) < 0)
665 return AIL_ERROR_DB_FAILED;
668 pkg_type = ai->values[E_AIL_PROP_X_SLP_PACKAGETYPE_STR];
669 pkg = ai->values[E_AIL_PROP_PACKAGE_STR];
670 retv_if (NULL == pkg, AIL_ERROR_FAIL);
672 locale = sql_get_locale();
673 retv_if (NULL == locale, AIL_ERROR_FAIL);
675 if(pkg_type && (strcasecmp(pkg_type, "tpk") ==0))
677 locale_new = __get_app_locale_by_fallback(pkg, locale);
678 localname = (char *)appinfo_get_localname(pkg, locale_new, uid);
682 localname = (char *)appinfo_get_localname(pkg, locale, uid);
690 if (ai->values[prop])
691 free(ai->values[prop]);
692 ai->values[prop] = localname;
701 index = sql_get_app_info_idx(prop);
702 if (db_column_str(ai->stmt, index, &value) < 0){
703 return AIL_ERROR_DB_FAILED;
707 *str = ai->values[prop];
713 EXPORT_API ail_error_e ail_close_appinfo_db(void)