Merge pull request #2 from jusung07-son/master
[platform/core/appfw/pkgmgr-info.git] / src / pkgmgrinfo_certinfo.c
1 #include <stdio.h>
2 #include <stdlib.h>
3 #include <string.h>
4 #include <stdbool.h>
5 #include <unistd.h>
6 #include <sys/types.h>
7
8 #include <sqlite3.h>
9 #include <glib.h>
10
11 #include "pkgmgr-info.h"
12 #include "pkgmgrinfo_debug.h"
13 #include "pkgmgrinfo_private.h"
14 #include "pkgmgr_parser.h"
15
16 typedef struct _pkgmgr_certinfo_x {
17         int for_all_users;
18         char *pkgid;
19         char *cert_value;
20         char *cert_info[MAX_CERT_TYPE]; /*certificate info*/
21         int cert_id[MAX_CERT_TYPE];             /*certificate ID in index table*/
22 } pkgmgr_certinfo_x;
23
24 API int pkgmgrinfo_pkginfo_create_certinfo(pkgmgrinfo_certinfo_h *handle)
25 {
26         retvm_if(handle == NULL, PMINFO_R_EINVAL, "Argument supplied to hold return value is NULL\n");
27         pkgmgr_certinfo_x *certinfo = NULL;
28         certinfo = calloc(1, sizeof(pkgmgr_certinfo_x));
29         *handle = NULL;
30         retvm_if(certinfo == NULL, PMINFO_R_ERROR, "Malloc Failed\n");
31         *handle = (void *)certinfo;
32         return PMINFO_R_OK;
33 }
34
35 static int _pkginfo_compare_certinfo(sqlite3 *db, const char *l_pkgid,
36                 const char *r_pkgid,
37                 pkgmgrinfo_cert_compare_result_type_e *result)
38 {
39         static const char query[] =
40                 "SELECT COALESCE(author_signer_cert, -1) FROM package_cert_info "
41                 "WHERE package=?";
42         int ret;
43         sqlite3_stmt *stmt;
44         const char *pkgid[2];
45         int certid[2] = {-1, -1};
46         int i;
47
48         pkgid[0] = l_pkgid;
49         pkgid[1] = r_pkgid;
50
51         ret = sqlite3_prepare_v2(db, query, strlen(query), &stmt, NULL);
52         if (ret != SQLITE_OK) {
53                 _LOGE("prepare error: %s", sqlite3_errmsg(db));
54                 return PMINFO_R_ERROR;
55         }
56
57         for (i = 0; i < 2; i++) {
58                 ret = sqlite3_bind_text(stmt, 1, pkgid[i], -1, SQLITE_STATIC);
59                 if (ret != SQLITE_OK) {
60                         _LOGE("bind error: %s", sqlite3_errmsg(db));
61                         sqlite3_finalize(stmt);
62                         return PMINFO_R_ERROR;
63                 }
64
65                 ret = sqlite3_step(stmt);
66                 if (ret == SQLITE_ROW) {
67                         _save_column_int(stmt, 0, &certid[i]);
68                 } else if (ret != SQLITE_DONE) {
69                         _LOGE("step error: %s", sqlite3_errmsg(db));
70                         sqlite3_finalize(stmt);
71                         return PMINFO_R_ERROR;
72                 }
73
74                 sqlite3_reset(stmt);
75                 sqlite3_clear_bindings(stmt);
76         }
77
78         if (certid[0] == -1 && certid[1] == -1)
79                 *result = PMINFO_CERT_COMPARE_BOTH_NO_CERT;
80         else if (certid[0] == -1)
81                 *result = PMINFO_CERT_COMPARE_LHS_NO_CERT;
82         else if (certid[1] == -1)
83                 *result = PMINFO_CERT_COMPARE_RHS_NO_CERT;
84         else if (certid[0] == certid[1])
85                 *result = PMINFO_CERT_COMPARE_MATCH;
86         else
87                 *result = PMINFO_CERT_COMPARE_MISMATCH;
88
89         sqlite3_finalize(stmt);
90         return PMINFO_R_OK;
91 }
92
93 API int pkgmgrinfo_pkginfo_compare_usr_pkg_cert_info(const char *lhs_package_id,
94                 const char *rhs_package_id, uid_t uid,
95                 pkgmgrinfo_cert_compare_result_type_e *compare_result)
96 {
97         int ret;
98         sqlite3 *db;
99         char *dbpath;
100
101         if (lhs_package_id == NULL || rhs_package_id == NULL ||
102                         compare_result == NULL) {
103                 _LOGE("invalid parameter");
104                 return PMINFO_R_EINVAL;
105         }
106
107         /* open unified global cert db */
108         dbpath = getUserPkgCertDBPath();
109         if (dbpath == NULL)
110                 return PMINFO_R_ERROR;
111
112         ret = __open_db(dbpath, &db, SQLITE_OPEN_READONLY);
113         if (ret != SQLITE_OK) {
114                 _LOGE("failed to open db: %d", ret);
115                 free(dbpath);
116                 return PMINFO_R_ERROR;
117         }
118         free(dbpath);
119
120         if (_pkginfo_compare_certinfo(db, lhs_package_id, rhs_package_id,
121                                 compare_result)) {
122                 _LOGE("failed to compare certinfo");
123                 sqlite3_close_v2(db);
124                 return PMINFO_R_ERROR;
125         }
126
127         sqlite3_close_v2(db);
128
129         return PMINFO_R_OK;
130 }
131
132 API int pkgmgrinfo_pkginfo_compare_pkg_cert_info(const char *lhs_package_id, const char *rhs_package_id, pkgmgrinfo_cert_compare_result_type_e *compare_result)
133 {
134         return pkgmgrinfo_pkginfo_compare_usr_pkg_cert_info(lhs_package_id, rhs_package_id, _getuid(), compare_result);
135 }
136
137 static int _pkginfo_get_pkgid_from_appid(uid_t uid, const char *appid,
138                 char **pkgid)
139 {
140         static const char query[] =
141                 "SELECT package FROM package_app_info WHERE app_id=?";
142         int ret;
143         sqlite3 *db;
144         char *dbpath;
145         sqlite3_stmt *stmt;
146
147         dbpath = getUserPkgParserDBPathUID(uid);
148         if (dbpath == NULL)
149                 return PMINFO_R_ERROR;
150
151         ret = __open_db(dbpath, &db, SQLITE_OPEN_READONLY);
152         if (ret != SQLITE_OK) {
153                 _LOGE("failed to open db: %d", ret);
154                 free(dbpath);
155                 return PMINFO_R_ERROR;
156         }
157         free(dbpath);
158
159         ret = sqlite3_prepare_v2(db, query, strlen(query), &stmt, NULL);
160         if (ret != SQLITE_OK) {
161                 _LOGE("prepare error: %s", sqlite3_errmsg(db));
162                 sqlite3_close_v2(db);
163                 return PMINFO_R_ERROR;
164         }
165
166         ret = sqlite3_bind_text(stmt, 1, appid, -1, SQLITE_STATIC);
167         if (ret != SQLITE_OK) {
168                 _LOGE("bind error: %s", sqlite3_errmsg(db));
169                 sqlite3_finalize(stmt);
170                 sqlite3_close_v2(db);
171                 return PMINFO_R_ERROR;
172         }
173
174         ret = sqlite3_step(stmt);
175         if (ret == SQLITE_ROW) {
176                 _save_column_str(stmt, 0, pkgid);
177                 ret = PMINFO_R_OK;
178         } else if (ret == SQLITE_DONE) {
179                 _LOGI("cannot find pkgid of app %s for uid %d", appid, (int)uid);
180                 ret = PMINFO_R_ENOENT;
181         } else {
182                 _LOGE("step error: %s", sqlite3_errmsg(db));
183                 ret = PMINFO_R_ERROR;
184         }
185
186         sqlite3_finalize(stmt);
187         sqlite3_close_v2(db);
188
189         return ret;
190 }
191
192 API int pkgmgrinfo_pkginfo_compare_usr_app_cert_info(const char *lhs_app_id,
193                 const char *rhs_app_id, uid_t uid,
194                 pkgmgrinfo_cert_compare_result_type_e *compare_result)
195 {
196         int ret;
197         char *l_pkgid = NULL;
198         char *r_pkgid = NULL;
199
200         if (lhs_app_id == NULL || rhs_app_id == NULL ||
201                         compare_result == NULL) {
202                 _LOGE("invalid parameter");
203                 return PMINFO_R_EINVAL;
204         }
205
206         ret = _pkginfo_get_pkgid_from_appid(uid, lhs_app_id, &l_pkgid);
207         if (ret == PMINFO_R_ENOENT && uid != GLOBAL_USER)
208                 ret = _pkginfo_get_pkgid_from_appid(GLOBAL_USER, lhs_app_id,
209                                 &l_pkgid);
210
211         if (ret != PMINFO_R_OK)
212                 return ret;
213
214         ret = _pkginfo_get_pkgid_from_appid(uid, rhs_app_id, &r_pkgid);
215         if (ret == PMINFO_R_ENOENT && uid != GLOBAL_USER)
216                 ret = _pkginfo_get_pkgid_from_appid(GLOBAL_USER, rhs_app_id,
217                                 &r_pkgid);
218
219         if (ret != PMINFO_R_OK) {
220                 free(l_pkgid);
221                 return ret;
222         }
223
224         ret = pkgmgrinfo_pkginfo_compare_usr_pkg_cert_info(l_pkgid, r_pkgid,
225                         uid, compare_result);
226
227         free(l_pkgid);
228         free(r_pkgid);
229
230         return ret;
231 }
232
233 API int pkgmgrinfo_pkginfo_compare_app_cert_info(const char *lhs_app_id,
234                 const char *rhs_app_id,
235                 pkgmgrinfo_cert_compare_result_type_e *compare_result)
236 {
237         return pkgmgrinfo_pkginfo_compare_usr_app_cert_info(lhs_app_id,
238                         rhs_app_id, _getuid(), compare_result);
239 }
240
241 static int _pkginfo_get_cert(sqlite3 *db, int cert_id[],
242                 char *cert_info[])
243 {
244         static const char query[] =
245                 "SELECT cert_info FROM package_cert_index_info WHERE cert_id=?";
246         int ret;
247         sqlite3_stmt *stmt;
248         int i;
249
250         ret = sqlite3_prepare_v2(db, query, strlen(query), &stmt, NULL);
251         if (ret != SQLITE_OK) {
252                 _LOGE("prepare failed: %s", sqlite3_errmsg(db));
253                 return PMINFO_R_ERROR;
254         }
255
256         for (i = 0; i < MAX_CERT_TYPE; i++) {
257                 ret = sqlite3_bind_int(stmt, 1, cert_id[i]);
258                 if (ret != SQLITE_OK) {
259                         sqlite3_finalize(stmt);
260                         _LOGE("bind failed: %s", sqlite3_errmsg(db));
261                         return PMINFO_R_ERROR;
262                 }
263
264                 ret = sqlite3_step(stmt);
265                 if (ret == SQLITE_DONE) {
266                         sqlite3_reset(stmt);
267                         sqlite3_clear_bindings(stmt);
268                         continue;
269                 } else if (ret != SQLITE_ROW) {
270                         _LOGE("step failed: %s", sqlite3_errmsg(db));
271                         sqlite3_finalize(stmt);
272                         return PMINFO_R_ERROR;
273                 }
274
275                 _save_column_str(stmt, 0, &cert_info[i]);
276                 sqlite3_reset(stmt);
277                 sqlite3_clear_bindings(stmt);
278         }
279
280         sqlite3_finalize(stmt);
281
282         return PMINFO_R_OK;
283 }
284
285 static int _pkginfo_get_certid(sqlite3 *db, const char *pkgid, int cert_id[])
286 {
287         static const char query[] =
288                 "SELECT author_root_cert, author_im_cert, author_signer_cert, "
289                 "dist_root_cert, dist_im_cert, dist_signer_cert, "
290                 "dist2_root_cert, dist2_im_cert, dist2_signer_cert "
291                 "FROM package_cert_info WHERE package=?";
292         int ret;
293         sqlite3_stmt *stmt;
294         int idx;
295
296         ret = sqlite3_prepare_v2(db, query, strlen(query), &stmt, NULL);
297         if (ret != SQLITE_OK) {
298                 _LOGE("prepare failed: %s", sqlite3_errmsg(db));
299                 return PMINFO_R_ERROR;
300         }
301
302         ret = sqlite3_bind_text(stmt, 1, pkgid, -1, SQLITE_STATIC);
303         if (ret != SQLITE_OK) {
304                 _LOGE("bind failed: %s", sqlite3_errmsg(db));
305                 sqlite3_finalize(stmt);
306                 return PMINFO_R_ERROR;
307         }
308
309         ret = sqlite3_step(stmt);
310         if (ret == SQLITE_DONE) {
311                 sqlite3_finalize(stmt);
312                 return PMINFO_R_ENOENT;
313         } else if (ret != SQLITE_ROW) {
314                 _LOGE("step failed: %s", sqlite3_errmsg(db));
315                 sqlite3_finalize(stmt);
316                 return PMINFO_R_ERROR;
317         }
318
319         idx = 0;
320         _save_column_int(stmt, idx++, &cert_id[PMINFO_AUTHOR_ROOT_CERT]);
321         _save_column_int(stmt, idx++,
322                         &cert_id[PMINFO_AUTHOR_INTERMEDIATE_CERT]);
323         _save_column_int(stmt, idx++, &cert_id[PMINFO_AUTHOR_SIGNER_CERT]);
324         _save_column_int(stmt, idx++, &cert_id[PMINFO_DISTRIBUTOR_ROOT_CERT]);
325         _save_column_int(stmt, idx++,
326                         &cert_id[PMINFO_DISTRIBUTOR_INTERMEDIATE_CERT]);
327         _save_column_int(stmt, idx++, &cert_id[PMINFO_DISTRIBUTOR_SIGNER_CERT]);
328         _save_column_int(stmt, idx++, &cert_id[PMINFO_DISTRIBUTOR2_ROOT_CERT]);
329         _save_column_int(stmt, idx++,
330                         &cert_id[PMINFO_DISTRIBUTOR2_INTERMEDIATE_CERT]);
331         _save_column_int(stmt, idx++,
332                         &cert_id[PMINFO_DISTRIBUTOR2_SIGNER_CERT]);
333
334         sqlite3_finalize(stmt);
335
336         return PMINFO_R_OK;
337 }
338
339 static int _pkginfo_get_certinfo(const char *pkgid, pkgmgr_certinfo_x *info)
340 {
341         int ret;
342         sqlite3 *db;
343         char *dbpath;
344
345         /* open unified global cert db */
346         dbpath = getUserPkgCertDBPath();
347         if (dbpath == NULL)
348                 return PMINFO_R_ERROR;
349
350         ret = __open_db(dbpath, &db, SQLITE_OPEN_READONLY);
351         if (ret != SQLITE_OK) {
352                 _LOGE("failed to open db: %d", ret);
353                 free(dbpath);
354                 return PMINFO_R_ERROR;
355         }
356         free(dbpath);
357
358         ret = _pkginfo_get_certid(db, pkgid, info->cert_id);
359         if (ret != PMINFO_R_OK) {
360                 sqlite3_close_v2(db);
361                 return ret;
362         }
363
364         ret = _pkginfo_get_cert(db, info->cert_id, info->cert_info);
365         if (ret != PMINFO_R_OK) {
366                 sqlite3_close_v2(db);
367                 return ret;
368         }
369
370         sqlite3_close_v2(db);
371
372         return PMINFO_R_OK;
373 }
374
375 API int pkgmgrinfo_pkginfo_load_certinfo(const char *pkgid, pkgmgrinfo_certinfo_h handle, uid_t uid)
376 {
377         int ret;
378         pkgmgr_certinfo_x *info = (pkgmgr_certinfo_x *)handle;
379
380         if (pkgid == NULL || handle == NULL) {
381                 _LOGE("invalid parameter");
382                 return PMINFO_R_EINVAL;
383         }
384
385         ret = _pkginfo_get_certinfo(pkgid, info);
386         if (ret != PMINFO_R_OK)
387                 _LOGE("failed to get certinfo of %s ", pkgid);
388
389         return ret;
390 }
391
392 API int pkgmgrinfo_pkginfo_get_cert_value(pkgmgrinfo_certinfo_h handle, pkgmgrinfo_cert_type cert_type, const char **cert_value)
393 {
394         retvm_if(handle == NULL, PMINFO_R_EINVAL, "Argument supplied is NULL\n");
395         retvm_if(cert_value == NULL, PMINFO_R_EINVAL, "Argument supplied is NULL\n");
396         retvm_if(cert_type < PMINFO_AUTHOR_ROOT_CERT, PMINFO_R_EINVAL, "Invalid certificate type\n");
397         retvm_if(cert_type > PMINFO_DISTRIBUTOR2_SIGNER_CERT, PMINFO_R_EINVAL, "Invalid certificate type\n");
398         pkgmgr_certinfo_x *certinfo = NULL;
399         certinfo = (pkgmgr_certinfo_x *)handle;
400         if ((certinfo->cert_info)[cert_type])
401                 *cert_value = (certinfo->cert_info)[cert_type];
402         else
403                 *cert_value = NULL;
404         return PMINFO_R_OK;
405 }
406
407 API int pkgmgrinfo_pkginfo_destroy_certinfo(pkgmgrinfo_certinfo_h handle)
408 {
409         retvm_if(handle == NULL, PMINFO_R_EINVAL, "Argument supplied is NULL\n");
410         int i = 0;
411         pkgmgr_certinfo_x *certinfo = NULL;
412         certinfo = (pkgmgr_certinfo_x *)handle;
413         if (certinfo->pkgid) {
414                 free(certinfo->pkgid);
415                 certinfo->pkgid = NULL;
416         }
417         for (i = 0; i < MAX_CERT_TYPE; i++) {
418                 if ((certinfo->cert_info)[i]) {
419                         free((certinfo->cert_info)[i]);
420                         (certinfo->cert_info)[i] = NULL;
421                 }
422         }
423         free(certinfo);
424         certinfo = NULL;
425         return PMINFO_R_OK;
426 }
427
428 API int pkgmgrinfo_create_certinfo_set_handle(pkgmgrinfo_instcertinfo_h *handle)
429 {
430         retvm_if(handle == NULL, PMINFO_R_EINVAL, "Argument supplied to hold return value is NULL\n");
431         pkgmgr_certinfo_x *certinfo = NULL;
432         *handle = NULL;
433         certinfo = calloc(1, sizeof(pkgmgr_certinfo_x));
434         retvm_if(certinfo == NULL, PMINFO_R_ERROR, "Malloc Failed\n");
435         *handle = (void *)certinfo;
436         return PMINFO_R_OK;
437 }
438
439 API int pkgmgrinfo_set_cert_value(pkgmgrinfo_instcertinfo_h handle, pkgmgrinfo_instcert_type cert_type, char *cert_value)
440 {
441         retvm_if(handle == NULL, PMINFO_R_EINVAL, "Argument supplied is NULL\n");
442         retvm_if(cert_value == NULL, PMINFO_R_EINVAL, "Argument supplied is NULL\n");
443         retvm_if(cert_type < PMINFO_SET_AUTHOR_ROOT_CERT, PMINFO_R_EINVAL, "Invalid certificate type\n");
444         retvm_if(cert_type > PMINFO_SET_DISTRIBUTOR2_SIGNER_CERT, PMINFO_R_EINVAL, "Invalid certificate type\n");
445         pkgmgr_certinfo_x *certinfo = NULL;
446         certinfo = (pkgmgr_certinfo_x *)handle;
447         if (certinfo->cert_info[cert_type])
448                 free(certinfo->cert_info[cert_type]);
449         (certinfo->cert_info)[cert_type] = strdup(cert_value);
450         return PMINFO_R_OK;
451 }
452
453 static int _pkginfo_save_cert_info(sqlite3 *db, const char *pkgid,
454                 char *cert_info[])
455 {
456         static const char query_insert[] =
457                 "INSERT INTO package_cert_info (package, package_count,"
458                 " author_root_cert, author_im_cert, author_signer_cert,"
459                 " dist_root_cert, dist_im_cert, dist_signer_cert,"
460                 " dist2_root_cert, dist2_im_cert, dist2_signer_cert) "
461                 "VALUES(?, 1,"
462                 " (SELECT cert_id FROM package_cert_index_info"
463                 "  WHERE cert_info=?),"
464                 " (SELECT cert_id FROM package_cert_index_info"
465                 "  WHERE cert_info=?),"
466                 " (SELECT cert_id FROM package_cert_index_info"
467                 "  WHERE cert_info=?),"
468                 " (SELECT cert_id FROM package_cert_index_info"
469                 "  WHERE cert_info=?),"
470                 " (SELECT cert_id FROM package_cert_index_info"
471                 "  WHERE cert_info=?),"
472                 " (SELECT cert_id FROM package_cert_index_info"
473                 "  WHERE cert_info=?),"
474                 " (SELECT cert_id FROM package_cert_index_info"
475                 "  WHERE cert_info=?),"
476                 " (SELECT cert_id FROM package_cert_index_info"
477                 "  WHERE cert_info=?),"
478                 " (SELECT cert_id FROM package_cert_index_info"
479                 "  WHERE cert_info=?))";
480         static const char query_update[] =
481                 "UPDATE package_cert_info "
482                 "SET package_count = package_count + 1 "
483                 "WHERE package=?";
484         int ret;
485         sqlite3_stmt *stmt;
486         int i;
487         int idx;
488
489         ret = sqlite3_prepare_v2(db, query_insert, strlen(query_insert),
490                         &stmt, NULL);
491         if (ret != SQLITE_OK) {
492                 _LOGE("prepare error: %s", sqlite3_errmsg(db));
493                 return PMINFO_R_ERROR;
494         }
495
496         idx = 1;
497         ret = sqlite3_bind_text(stmt, idx++, pkgid, -1, SQLITE_STATIC);
498         if (ret != SQLITE_OK) {
499                 _LOGE("bind failed: %s", sqlite3_errmsg(db));
500                 sqlite3_finalize(stmt);
501                 return PMINFO_R_ERROR;
502         }
503
504         for (i = 0; i < MAX_CERT_TYPE; i++) {
505                 if (sqlite3_bind_text(stmt, idx++, cert_info[i], -1,
506                                 SQLITE_STATIC)) {
507                         _LOGE("bind error: %s", sqlite3_errmsg(db));
508                         sqlite3_finalize(stmt);
509                         return PMINFO_R_ERROR;
510                 }
511         }
512
513         ret = sqlite3_step(stmt);
514         sqlite3_finalize(stmt);
515         if (ret == SQLITE_CONSTRAINT) {
516                 ret = sqlite3_prepare_v2(db, query_update, strlen(query_update),
517                                 &stmt, NULL);
518                 if (ret != SQLITE_OK) {
519                         _LOGE("prepare error: %s", sqlite3_errmsg(db));
520                         return PMINFO_R_ERROR;
521                 }
522
523                 if (sqlite3_bind_text(stmt, 1, pkgid, -1, SQLITE_STATIC)) {
524                         _LOGE("bind error: %s", sqlite3_errmsg(db));
525                         sqlite3_finalize(stmt);
526                         return PMINFO_R_ERROR;
527                 }
528
529                 ret = sqlite3_step(stmt);
530                 sqlite3_finalize(stmt);
531         }
532
533         if (ret != SQLITE_DONE) {
534                 _LOGE("step error: %s", sqlite3_errmsg(db));
535                 return PMINFO_R_ERROR;
536         }
537
538         return PMINFO_R_OK;
539 }
540
541 static int _pkginfo_save_cert_index_info(sqlite3 *db, char *cert_info[])
542 {
543         static const char query[] =
544                 "INSERT OR REPLACE INTO package_cert_index_info "
545                 "(cert_info, cert_id, cert_ref_count) "
546                 "VALUES ( "
547                 " ?, "
548                 " (SELECT cert_id FROM package_cert_index_info "
549                 "  WHERE cert_info=?), "
550                 " COALESCE( "
551                 "  ((SELECT cert_ref_count FROM package_cert_index_info "
552                 "    WHERE cert_info=?) + 1), 1))";
553         int ret;
554         sqlite3_stmt *stmt;
555         int i;
556         int idx;
557
558         ret = sqlite3_prepare_v2(db, query, strlen(query), &stmt, NULL);
559         if (ret != SQLITE_OK) {
560                 _LOGE("prepare error: %s", sqlite3_errmsg(db));
561                 return PMINFO_R_ERROR;
562         }
563
564         for (i = 0; i < MAX_CERT_TYPE; i++) {
565                 if (cert_info[i] == NULL)
566                         continue;
567                 idx = 1;
568                 ret = sqlite3_bind_text(stmt, idx++, cert_info[i], -1, SQLITE_STATIC);
569                 if (ret != SQLITE_OK) {
570                         _LOGE("bind failed: %s", sqlite3_errmsg(db));
571                         sqlite3_finalize(stmt);
572                         return PMINFO_R_ERROR;
573                 }
574                 ret = sqlite3_bind_text(stmt, idx++, cert_info[i], -1, SQLITE_STATIC);
575                 if (ret != SQLITE_OK) {
576                         _LOGE("bind failed: %s", sqlite3_errmsg(db));
577                         sqlite3_finalize(stmt);
578                         return PMINFO_R_ERROR;
579                 }
580                 ret = sqlite3_bind_text(stmt, idx++, cert_info[i], -1, SQLITE_STATIC);
581                 if (ret != SQLITE_OK) {
582                         _LOGE("bind failed: %s", sqlite3_errmsg(db));
583                         sqlite3_finalize(stmt);
584                         return PMINFO_R_ERROR;
585                 }
586
587                 ret = sqlite3_step(stmt);
588                 if (ret != SQLITE_DONE) {
589                         _LOGE("step failed: %s", sqlite3_errmsg(db));
590                         sqlite3_finalize(stmt);
591                         return PMINFO_R_ERROR;
592                 }
593
594                 sqlite3_reset(stmt);
595                 sqlite3_clear_bindings(stmt);
596         }
597
598         sqlite3_finalize(stmt);
599
600         return PMINFO_R_OK;
601 }
602
603 API int pkgmgrinfo_save_certinfo(const char *pkgid, pkgmgrinfo_instcertinfo_h handle, uid_t uid)
604 {
605         int ret;
606         sqlite3 *db;
607         char *dbpath;
608         pkgmgr_certinfo_x *info = (pkgmgr_certinfo_x *)handle;
609
610         if (pkgid == NULL || handle == NULL) {
611                 _LOGE("invalid parameter");
612                 return PMINFO_R_EINVAL;
613         }
614
615         _check_create_cert_db();
616
617         /* open unified global cert db */
618         dbpath = getUserPkgCertDBPath();
619         if (dbpath == NULL)
620                 return PMINFO_R_ERROR;
621
622         ret = __open_db(dbpath, &db, SQLITE_OPEN_READWRITE);
623         if (ret != SQLITE_OK) {
624                 _LOGE("failed to open db: %d", ret);
625                 free(dbpath);
626                 return PMINFO_R_ERROR;
627         }
628         free(dbpath);
629
630         ret = sqlite3_exec(db, "BEGIN DEFERRED", NULL, NULL, NULL);
631         if (ret != SQLITE_OK) {
632                 _LOGE("failed to begin transaction");
633                 sqlite3_close_v2(db);
634                 return PMINFO_R_ERROR;
635         }
636
637         if (_pkginfo_save_cert_index_info(db, info->cert_info)) {
638                 _LOGE("failed to save cert index info, rollback now");
639                 ret = sqlite3_exec(db, "ROLLBACK", NULL, NULL, NULL);
640                 if (ret != SQLITE_OK)
641                         LOGE("Rollback is failed. error(%s)", sqlite3_errmsg(db));
642                 sqlite3_close_v2(db);
643                 return PMINFO_R_ERROR;
644         }
645
646         if (_pkginfo_save_cert_info(db, pkgid, info->cert_info)) {
647                 _LOGE("failed to save cert info, rollback now");
648                 ret = sqlite3_exec(db, "ROLLBACK", NULL, NULL, NULL);
649                 if (ret != SQLITE_OK)
650                         LOGE("Rollback is failed. error(%s)", sqlite3_errmsg(db));
651                 sqlite3_close_v2(db);
652                 return PMINFO_R_ERROR;
653         }
654
655         ret = sqlite3_exec(db, "COMMIT", NULL, NULL, NULL);
656         if (ret != SQLITE_OK) {
657                 _LOGE("failed to commit transaction, rollback now");
658                 ret = sqlite3_exec(db, "ROLLBACK", NULL, NULL, NULL);
659                 if (ret != SQLITE_OK)
660                         LOGE("Rollback is failed. error(%s)", sqlite3_errmsg(db));
661                 sqlite3_close_v2(db);
662                 return PMINFO_R_ERROR;
663         }
664
665         sqlite3_close_v2(db);
666
667         return PMINFO_R_OK;
668 }
669
670 API int pkgmgrinfo_destroy_certinfo_set_handle(pkgmgrinfo_instcertinfo_h handle)
671 {
672         retvm_if(handle == NULL, PMINFO_R_EINVAL, "Argument supplied is NULL\n");
673         int i = 0;
674         pkgmgr_certinfo_x *certinfo = NULL;
675         certinfo = (pkgmgr_certinfo_x *)handle;
676         if (certinfo->pkgid) {
677                 free(certinfo->pkgid);
678                 certinfo->pkgid = NULL;
679         }
680         for (i = 0; i < MAX_CERT_TYPE; i++) {
681                 if ((certinfo->cert_info)[i]) {
682                         free((certinfo->cert_info)[i]);
683                         (certinfo->cert_info)[i] = NULL;
684                 }
685         }
686         free(certinfo);
687         certinfo = NULL;
688         return PMINFO_R_OK;
689 }
690
691 static int _pkginfo_delete_certinfo(sqlite3 *db, const char *pkgid)
692 {
693         static const char query[] =
694                 "UPDATE package_cert_info "
695                 "SET package_count = package_count - 1 "
696                 "WHERE package=?";
697         int ret;
698         sqlite3_stmt *stmt;
699
700         ret = sqlite3_prepare_v2(db, query, strlen(query), &stmt, NULL);
701         if (ret != SQLITE_OK) {
702                 _LOGE("prepare error: %s", sqlite3_errmsg(db));
703                 return PMINFO_R_ERROR;
704         }
705
706         ret = sqlite3_bind_text(stmt, 1, pkgid, -1, SQLITE_STATIC);
707         if (ret != SQLITE_OK) {
708                 _LOGE("bind error: %s", sqlite3_errmsg(db));
709                 sqlite3_finalize(stmt);
710                 return PMINFO_R_ERROR;
711         }
712
713         ret = sqlite3_step(stmt);
714         sqlite3_finalize(stmt);
715         if (ret != SQLITE_DONE) {
716                 _LOGE("step error: %s", sqlite3_errmsg(db));
717                 return PMINFO_R_ERROR;
718         }
719
720         return PMINFO_R_OK;
721 }
722
723 API int pkgmgrinfo_delete_usr_certinfo(const char *pkgid, uid_t uid)
724 {
725         int ret;
726         sqlite3 *db;
727         char *dbpath;
728
729         if (pkgid == NULL) {
730                 _LOGE("invalid parameter");
731                 return PMINFO_R_EINVAL;
732         }
733
734         /* open unified global cert db */
735         dbpath = getUserPkgCertDBPath();
736         if (dbpath == NULL)
737                 return PMINFO_R_ERROR;
738
739         ret = __open_db(dbpath, &db, SQLITE_OPEN_READWRITE);
740         if (ret != SQLITE_OK) {
741                 _LOGE("failed to open db: %d", ret);
742                 free(dbpath);
743                 return PMINFO_R_ERROR;
744         }
745         free(dbpath);
746
747         ret = sqlite3_exec(db, "BEGIN DEFERRED", NULL, NULL, NULL);
748         if (ret != SQLITE_OK) {
749                 _LOGE("failed to begin transaction");
750                 sqlite3_close_v2(db);
751                 return PMINFO_R_ERROR;
752         }
753
754         if (_pkginfo_delete_certinfo(db, pkgid)) {
755                 _LOGE("failed to delete certinfo of %s, rollback now", pkgid);
756                 ret = sqlite3_exec(db, "ROLLBACK", NULL, NULL, NULL);
757                 if (ret != SQLITE_OK)
758                         LOGE("Rollback is failed. error(%s)", sqlite3_errmsg(db));
759                 sqlite3_close_v2(db);
760                 return PMINFO_R_ERROR;
761         }
762
763         ret = sqlite3_exec(db, "COMMIT", NULL, NULL, NULL);
764         if (ret != SQLITE_OK) {
765                 _LOGE("failed to commit transaction, rollback now");
766                 ret = sqlite3_exec(db, "ROLLBACK", NULL, NULL, NULL);
767                 if (ret != SQLITE_OK)
768                         LOGE("Rollback is failed. error(%s)", sqlite3_errmsg(db));
769                 sqlite3_close_v2(db);
770                 return PMINFO_R_ERROR;
771         }
772
773         sqlite3_close_v2(db);
774
775         return PMINFO_R_OK;
776 }
777
778 API int pkgmgrinfo_delete_certinfo(const char *pkgid)
779 {
780         return pkgmgrinfo_delete_usr_certinfo(pkgid, _getuid());
781 }
782