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.
33 #include "ail_private.h"
36 #define GLOBAL_USER 0 //#define tzplatform_getenv(TZ_GLOBAL) //TODO
38 #define QUERY_ATTACH "attach database '%s' as Global"
39 #define QUERY_CREATE_VIEW_APP "CREATE temp VIEW app_info as select distinct * from (select * from main.app_info m union select * from Global.app_info g)"
41 #define QUERY_CREATE_VIEW_LOCAL "CREATE temp VIEW localname as select distinct * from (select * from main.localname m union select * from Global.localname g)"
43 #define retv_with_dbmsg_if(expr, val) do { \
45 _E("db_info.dbUserro: %s", sqlite3_errmsg(db_info.dbUserro)); \
46 _E("db_info.dbGlobalro: %s", sqlite3_errmsg(db_info.dbGlobalro)); \
47 _E("db_info.dbUserrw: %s", sqlite3_errmsg(db_info.dbUserrw)); \
48 _E("db_info.dbGlobalrw: %s", sqlite3_errmsg(db_info.dbGlobalrw)); \
49 _E("db_info.dbUserro errcode: %d", sqlite3_extended_errcode(db_info.dbUserro)); \
50 _E("db_info.dbGlobalro errcode: %d", sqlite3_extended_errcode(db_info.dbGlobalro)); \
51 _E("db_info.dbUserrw errcode: %d", sqlite3_extended_errcode(db_info.dbUserrw)); \
52 _E("db_info.dbGlobalrw errcode: %d", sqlite3_extended_errcode(db_info.dbGlobalrw)); \
57 static __thread struct {
68 static __thread sqlite3 *dbInit = NULL;
70 static int ail_db_change_perm(const char *db_file)
73 char journal_file[BUFSIZE];
76 struct group *grpinfo = NULL;
77 const char *name = "users";
79 files[0] = (char *)db_file;
80 files[1] = journal_file;
83 retv_if(!db_file, AIL_ERROR_FAIL);
84 if(getuid()) //At this time we should be root to apply this
87 snprintf(journal_file, sizeof(journal_file), "%s%s", db_file, "-journal");
89 for (i = 0; files[i]; i++) {
90 grpinfo = getgrnam(name);
92 _E("getgrnam(users) returns NULL !");
94 // Compare git_t type and not group name
95 ret = chown(files[i], OWNER_ROOT, grpinfo->gr_gid);
97 strerror_r(errno, buf, sizeof(buf));
98 _E("FAIL : chown %s %d.%d, because %s", db_file, OWNER_ROOT, grpinfo->gr_gid, buf);
99 return AIL_ERROR_FAIL;
102 ret = chmod(files[i], S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH);
104 strerror_r(errno, buf, sizeof(buf));
105 _E("FAIL : chmod %s 0664, because %s", db_file, buf);
106 return AIL_ERROR_FAIL;
113 char* ail_get_icon_path(uid_t uid)
115 char *result_psswd = NULL;
116 if(uid == GLOBAL_USER)
118 result_psswd = tzplatform_getenv(TZ_SYS_RW_ICONS);
122 const char *name = "users";
123 struct passwd *userinfo = NULL;
124 struct group *grpinfo = NULL;
126 userinfo = getpwuid(uid);
127 if(userinfo == NULL) {
128 _E("getpwuid(%d) returns NULL !", uid);
132 grpinfo = getgrnam(name);
133 if(grpinfo == NULL) {
134 _E("getgrnam(users) returns NULL !");
137 // Compare git_t type and not group name
138 if (grpinfo->gr_gid != userinfo->pw_gid) {
139 _E("UID [%d] does not belong to 'users' group!", uid);
142 result_psswd = tzplatform_getenv(TZ_USER_ICONS);
147 static char* ail_get_app_DB(uid_t uid)
149 char *result_psswd = NULL;
150 struct group *grpinfo = NULL;
152 if(uid == GLOBAL_USER)
154 result_psswd = strdup(APP_INFO_DB_FILE);
155 grpinfo = getgrnam("root");
156 if(grpinfo == NULL) {
157 _E("getgrnam(users) returns NULL !");
163 struct passwd *userinfo = getpwuid(uid);
164 if(userinfo == NULL) {
165 _E("getpwuid(%d) returns NULL !", uid);
168 grpinfo = getgrnam("users");
169 if(grpinfo == NULL) {
170 _E("getgrnam(users) returns NULL !");
173 // Compare git_t type and not group name
174 if (grpinfo->gr_gid != userinfo->pw_gid) {
175 _E("UID [%d] does not belong to 'users' group!", uid);
178 asprintf(&result_psswd, "%s/.applications/dbspace/.app_info.db", userinfo->pw_dir);
181 dir = strrchr(result_psswd, '/');
185 //Control if db exist create otherwise
186 if(access(dir + 1, F_OK)) {
188 mkdir(dir + 1, S_IRWXU | S_IRGRP | S_IXGRP | S_IXOTH);
189 ret = chown(dir + 1, uid, grpinfo->gr_gid);
192 strerror_r(errno, buf, sizeof(buf));
193 _E("FAIL : chown %s %d.%d, because %s", dir + 1, uid, grpinfo->gr_gid, buf);
199 static ail_error_e db_do_prepare(sqlite3 *db, const char *query, sqlite3_stmt **stmt)
203 retv_if(!query, AIL_ERROR_INVALID_PARAMETER);
204 retv_if(!stmt, AIL_ERROR_INVALID_PARAMETER);
205 retv_if(!db, AIL_ERROR_DB_FAILED);
207 ret = sqlite3_prepare_v2(db, query, strlen(query), stmt, NULL);
208 if (ret != SQLITE_OK) {
209 _E("%s\n", sqlite3_errmsg(db));
210 return AIL_ERROR_DB_FAILED;
215 ail_error_e db_open(db_open_mode mode, uid_t uid)
220 const char *tbls[3] = {
221 "CREATE TABLE app_info "
222 "(package TEXT PRIMARY KEY, "
223 "exec TEXT DEFAULT 'No Exec', "
224 "name TEXT DEFAULT 'No Name', "
225 "type TEXT DEFAULT 'Application', "
226 "icon TEXT DEFAULT 'No Icon', "
230 "x_slp_service TEXT, "
231 "x_slp_packagetype TEXT, "
232 "x_slp_packagecategories TEXT, "
233 "x_slp_packageid TEXT, "
236 "x_slp_exe_path TEXT, "
239 "x_slp_domain TEXT, "
240 "x_slp_submodemainid TEXT, "
241 "x_slp_installedstorage TEXT, "
242 "x_slp_baselayoutwidth INTEGER DEFAULT 0, "
243 "x_slp_installedtime INTEGER DEFAULT 0, "
244 "nodisplay INTEGER DEFAULT 0, "
245 "x_slp_taskmanage INTEGER DEFAULT 1, "
246 "x_slp_multiple INTEGER DEFAULT 0, "
247 "x_slp_removable INTEGER DEFAULT 1, "
248 "x_slp_ishorizontalscale INTEGER DEFAULT 0, "
249 "x_slp_enabled INTEGER DEFAULT 1, "
250 "x_slp_submode INTEGER DEFAULT 0, "
251 "desktop TEXT UNIQUE NOT NULL);",
252 "CREATE TABLE localname (package TEXT NOT NULL, "
253 "locale TEXT NOT NULL, "
254 "name TEXT NOT NULL, "
255 "x_slp_pkgid TEXT NOT NULL, PRIMARY KEY (package, locale));",
260 if (access(ail_get_app_DB(uid), F_OK)) {
261 if (AIL_ERROR_OK == db_util_open_with_options(ail_get_app_DB(uid), &dbInit, SQLITE_OPEN_READWRITE | SQLITE_OPEN_CREATE, NULL))
263 for (i = 0; tbls[i] != NULL; i++) {
264 ret = do_db_exec(tbls[i], dbInit);
265 retv_if(ret != AIL_ERROR_OK, AIL_ERROR_DB_FAILED);
269 _E("Failed to create table %s\n",ail_get_app_DB(uid));
273 if(AIL_ERROR_OK != ail_db_change_perm(ail_get_app_DB(uid))) {
274 _E("Failed to change permission\n");
276 ret = sqlite3_close(dbInit);
277 retv_with_dbmsg_if(ret != SQLITE_OK, AIL_ERROR_DB_FAILED);
280 if(mode & DB_OPEN_RO) {
281 if (!db_info.dbUserro) {
282 db_util_open_with_options(ail_get_app_DB(uid), &db_info.dbUserro, SQLITE_OPEN_READONLY, NULL);
283 char query_attach[AIL_SQL_QUERY_MAX_LEN];
284 char query_view_app[AIL_SQL_QUERY_MAX_LEN];
285 char query_view_local[AIL_SQL_QUERY_MAX_LEN];
286 snprintf(query_attach, AIL_SQL_QUERY_MAX_LEN, QUERY_ATTACH, ail_get_app_DB(GLOBAL_USER));
287 _E("info : execute query_attach : %s", query_attach );
288 if (db_exec_usr_ro(query_attach) < 0) {
289 return AIL_ERROR_DB_FAILED;
291 snprintf(query_view_app, AIL_SQL_QUERY_MAX_LEN, QUERY_CREATE_VIEW_APP);
292 _E("info : execute query_attach : %s", query_view_app );
293 if (db_exec_usr_ro(query_view_app) < 0) {
294 return AIL_ERROR_DB_FAILED;
297 snprintf(query_view_local, AIL_SQL_QUERY_MAX_LEN, QUERY_CREATE_VIEW_LOCAL);
298 _E("info : execute query_attach : %s", query_view_local );
299 if (db_exec_usr_ro(query_view_local) < 0) {
300 return AIL_ERROR_DB_FAILED;
303 if (!db_info.dbGlobalro) {
304 ret = db_util_open_with_options(ail_get_app_DB(GLOBAL_USER), &db_info.dbGlobalro, SQLITE_OPEN_READONLY, NULL);
305 retv_with_dbmsg_if(ret != SQLITE_OK, AIL_ERROR_DB_FAILED);
309 if(mode & DB_OPEN_RW) {
311 if(uid != GLOBAL_USER) {//TOCHANGETO is_admin
312 if(!db_info.dbUserrw){
313 ret = db_util_open(ail_get_app_DB(uid), &db_info.dbUserrw, 0);
316 if(!db_info.dbGlobalrw){
317 ret = db_util_open(ail_get_app_DB(GLOBAL_USER), &db_info.dbGlobalrw, 0);
320 retv_with_dbmsg_if(ret != SQLITE_OK, AIL_ERROR_DB_FAILED);
329 ail_error_e db_prepare(const char *query, sqlite3_stmt **stmt)
331 return db_do_prepare(db_info.dbUserro, query, stmt);
334 ail_error_e db_prepare_globalro(const char *query, sqlite3_stmt **stmt)
336 return db_do_prepare(db_info.dbGlobalro, query, stmt);
339 ail_error_e db_prepare_rw(const char *query, sqlite3_stmt **stmt)
341 return db_do_prepare(db_info.dbUserrw, query, stmt);
345 ail_error_e db_prepare_globalrw(const char *query, sqlite3_stmt **stmt)
347 return db_do_prepare(db_info.dbGlobalrw, query, stmt);
351 ail_error_e db_bind_bool(sqlite3_stmt *stmt, int idx, bool value)
355 retv_if(!stmt, AIL_ERROR_INVALID_PARAMETER);
357 ret = sqlite3_bind_int(stmt, idx, (int) value);
358 retv_with_dbmsg_if(ret != SQLITE_OK, AIL_ERROR_DB_FAILED);
365 ail_error_e db_bind_int(sqlite3_stmt *stmt, int idx, int value)
369 retv_if(!stmt, AIL_ERROR_INVALID_PARAMETER);
371 ret = sqlite3_bind_int(stmt, idx, value);
372 retv_with_dbmsg_if(ret != SQLITE_OK, AIL_ERROR_DB_FAILED);
377 ail_error_e db_bind_text(sqlite3_stmt *stmt, int idx, char* value)
381 retv_if(!stmt, AIL_ERROR_INVALID_PARAMETER);
383 ret = sqlite3_bind_text(stmt, idx, value, strlen(value), 0);
384 retv_with_dbmsg_if(ret != SQLITE_OK, AIL_ERROR_DB_FAILED);
390 ail_error_e db_step(sqlite3_stmt *stmt)
394 retv_if(!stmt, AIL_ERROR_INVALID_PARAMETER);
396 ret = sqlite3_step(stmt);
399 return AIL_ERROR_NO_DATA;
404 retv_with_dbmsg_if(1, AIL_ERROR_DB_FAILED);
409 ail_error_e db_column_bool(sqlite3_stmt *stmt, int index, bool *value)
413 retv_if(!stmt, AIL_ERROR_INVALID_PARAMETER);
414 retv_if(!value, AIL_ERROR_INVALID_PARAMETER);
416 out_val = sqlite3_column_int(stmt, index);
417 *value = (out_val == 1)? true:false;
424 ail_error_e db_column_int(sqlite3_stmt *stmt, int index, int *value)
426 retv_if(!stmt, AIL_ERROR_INVALID_PARAMETER);
427 retv_if(!value, AIL_ERROR_INVALID_PARAMETER);
429 *value = sqlite3_column_int(stmt, index);
436 ail_error_e db_column_str(sqlite3_stmt *stmt, int index, char **str)
438 retv_if(!stmt, AIL_ERROR_INVALID_PARAMETER);
439 retv_if(!str, AIL_ERROR_INVALID_PARAMETER);
441 *str = (char *)sqlite3_column_text(stmt, index);
448 ail_error_e db_reset(sqlite3_stmt *stmt)
452 retv_if(!stmt, AIL_ERROR_INVALID_PARAMETER);
454 sqlite3_clear_bindings(stmt);
456 ret = sqlite3_reset(stmt);
457 retv_with_dbmsg_if(ret != SQLITE_OK, AIL_ERROR_DB_FAILED);
464 ail_error_e db_finalize(sqlite3_stmt *stmt)
468 retv_if(!stmt, AIL_ERROR_INVALID_PARAMETER);
470 ret = sqlite3_finalize(stmt);
471 retv_with_dbmsg_if(ret != SQLITE_OK, AIL_ERROR_DB_FAILED);
478 ail_error_e do_db_exec(const char *query, sqlite3 * fileSQL)
483 retv_if(!query, AIL_ERROR_INVALID_PARAMETER);
484 retv_if(!fileSQL, AIL_ERROR_DB_FAILED);
486 ret = sqlite3_exec(fileSQL, query, NULL, NULL, &errmsg);
487 if (ret != SQLITE_OK) {
488 _E("Cannot execute this query - %s. because %s",
489 query, errmsg? errmsg:"uncatched error");
490 sqlite3_free(errmsg);
491 return AIL_ERROR_DB_FAILED;
499 ail_error_e db_exec_usr_rw(const char *query)
501 return do_db_exec(query, db_info.dbUserrw);
505 ail_error_e db_exec_usr_ro(const char *query)
507 return do_db_exec(query, db_info.dbUserro);
510 ail_error_e db_exec_glo_ro(const char *query)
512 return do_db_exec(query, db_info.dbGlobalro);
515 ail_error_e db_exec_glo_rw(const char *query)
517 return do_db_exec(query, db_info.dbGlobalrw);
521 ail_error_e db_close(void)
525 if(db_info.dbUserro) {
526 ret = sqlite3_close(db_info.dbUserro);
527 retv_with_dbmsg_if(ret != SQLITE_OK, AIL_ERROR_DB_FAILED);
529 db_info.dbUserro = NULL;
531 if(db_info.dbGlobalrw) {
532 ret = sqlite3_close(db_info.dbGlobalrw);
533 retv_with_dbmsg_if(ret != SQLITE_OK, AIL_ERROR_DB_FAILED);
535 db_info.dbGlobalrw = NULL;
537 if(db_info.dbUserrw) {
538 ret = sqlite3_close(db_info.dbUserrw);
539 retv_with_dbmsg_if(ret != SQLITE_OK, AIL_ERROR_DB_FAILED);
541 db_info.dbUserrw = NULL;
547 EXPORT_API ail_error_e ail_db_close(void)
552 int db_exec_sqlite_query(char *query, sqlite_query_callback callback, void *data)
554 char *error_message = NULL;
555 if(db_info.dbUserro) {
557 sqlite3_exec(db_info.dbUserro, query, callback, data, &error_message)) {
558 _E("Don't execute query = %s error message = %s\n", query,
560 sqlite3_free(error_message);
564 if(db_info.dbUserro) {
566 sqlite3_exec(db_info.dbUserro, query, callback, data, &error_message)) {
567 _E("Don't execute query = %s error message = %s\n", query,
569 sqlite3_free(error_message);
573 sqlite3_free(error_message);