Remove unused vconf key
[platform/core/appfw/ail.git] / src / ail_desktop.c
1 /*
2  * ail
3  *
4  * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved.
5  *
6  * Contact: Jayoun Lee <airjany@samsung.com>, Sewook Park <sewook7.park@samsung.com>, Jaeho Lee <jaeho81.lee@samsung.com>
7  *
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
11  *
12  * http://www.apache.org/licenses/LICENSE-2.0
13  *
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.
19  *
20  */
21
22
23
24 #define _GNU_SOURCE
25 #include <errno.h>
26 #include <stdio.h>
27 #include <string.h>
28 #include <stdlib.h>
29 #include <unistd.h>
30 #include <time.h>
31 #include <sys/types.h>
32 #include <sys/wait.h>
33 #include <tzplatform_config.h>
34 #include <xdgmime.h>
35
36 #include <glib.h>
37 #include <grp.h>
38 #include <pwd.h>
39
40 #include "ail_private.h"
41 #include "ail_db.h"
42 #include "ail_sql.h"
43 #include "ail.h"
44 #include "ail_vconf.h"
45
46 #define BUFSIZE 4096
47 #define GLOBAL_USER tzplatform_getuid(TZ_SYS_GLOBALAPP_USER)
48
49 #define whitespace(c) (((c) == ' ') || ((c) == '\t'))
50 #define argsdelimiter   " \t"
51
52 #define SQL_INSERT_LOCALNAME_STR "insert into localname (package, locale, name) values "
53 #define SQL_INSERT_LOCALNAME_STR_LEN (sizeof(SQL_INSERT_LOCALNAME_STR)-1)
54
55 #define SQL_INSERT_LOCALNAME_INIT_STR  SQL_INSERT_LOCALNAME_STR"( ?, ?, ?) "
56
57 #define SQL_LOCALNAME_TRIPLET_STR  ", ( ?, ?, ?)"
58 #define SQL_LOCALNAME_TRIPLET_STR_LEN (sizeof(SQL_LOCALNAME_TRIPLET_STR)-1)
59
60 typedef enum {
61         NOTI_ADD,
62         NOTI_UPDATE,
63         NOTI_REMOVE,
64         NOTI_MAX,
65 } noti_type;
66
67 struct entry_parser {
68         const char *field;
69         ail_error_e (*value_cb)(void *data, char *tag, char *value, uid_t uid);
70 };
71
72 inline static char *_ltrim(char *str)
73 {
74         if (!str) return NULL;
75
76         while (*str == ' ' || *str == '\t' || *str == '\n') str ++;
77
78         return str;
79 }
80
81
82
83 inline static int _rtrim(char *str)
84 {
85         int len;
86
87         len = strlen(str);
88         while (--len >= 0 && (str[len] == ' ' || str[len] == '\n' || str[len] == '\t')) str[len] = '\0';
89
90         return len;
91 }
92
93 struct name_item {
94         char *locale;
95         char *name;
96 };
97
98 typedef struct {
99         const char*     package;
100         char*           exec;
101         char*           name;
102         char*           type;
103         char*           icon;
104         char*           categories;
105         char*           version;
106         char*           mimetype;
107         char*           x_slp_service;
108         char*           x_slp_packagetype;
109         char*           x_slp_packagecategories;
110         char*           x_slp_packageid;
111         char*           x_slp_uri;
112         char*           x_slp_svc;
113         char*           x_slp_exe_path;
114         char*           x_slp_appid;
115         char*           x_slp_pkgid;
116         char*           x_slp_domain;
117         char*           x_slp_submodemainid;
118         char*           x_slp_installedstorage;
119         int             x_slp_baselayoutwidth;
120         int             x_slp_installedtime;
121         int             nodisplay;
122         int             x_slp_taskmanage;
123         int             x_slp_multiple;
124         int             x_slp_removable;
125         int             x_slp_ishorizontalscale;
126         int             x_slp_enabled;
127         int             x_slp_submode;
128         char*           desktop;
129         GSList*         localname;
130 } desktop_info_s;
131
132
133
134 static ail_error_e _read_exec(void *data, char *tag, char *value, uid_t uid)
135 {
136         desktop_info_s *info = data;
137         char *token_exe_path;
138         char *save_ptr;
139         char *temp_exec;
140
141         retv_if(!data, AIL_ERROR_INVALID_PARAMETER);
142         retv_if(!value, AIL_ERROR_INVALID_PARAMETER);
143
144         SAFE_FREE_AND_STRDUP(value, info->exec);
145         retv_if(!info->exec, AIL_ERROR_OUT_OF_MEMORY);
146
147         temp_exec = strdup(value);
148         if(!temp_exec) {
149                 free(info->exec);
150                 return AIL_ERROR_OUT_OF_MEMORY;
151         }
152
153         token_exe_path = strtok_r(temp_exec, argsdelimiter, &save_ptr);
154
155         info->x_slp_exe_path = strdup(token_exe_path);
156         if(!info->x_slp_exe_path) {
157                 free(info->exec);
158                 info->exec = NULL;
159                 free(temp_exec);
160                 return AIL_ERROR_OUT_OF_MEMORY;
161         }
162
163         free(temp_exec);
164
165         return AIL_ERROR_OK;
166 }
167
168
169
170 static ail_error_e _read_name(void *data, char *tag, char *value, uid_t uid)
171 {
172         desktop_info_s *info = data;
173
174         retv_if(!data, AIL_ERROR_INVALID_PARAMETER);
175         retv_if(!value, AIL_ERROR_INVALID_PARAMETER);
176         retv_if(0 == strlen(value), AIL_ERROR_FAIL);
177
178         if (tag && strlen(tag) > 0) {
179                 struct name_item *item;
180                 item = (struct name_item *)calloc(1, sizeof(struct name_item));
181                 retv_if (NULL == item, AIL_ERROR_OUT_OF_MEMORY);
182
183                 SAFE_FREE_AND_STRDUP(tag, item->locale);
184                 if(NULL == item->locale) {
185                         _E("(NULL == item->locale) return\n");
186                         free(item);
187                         return AIL_ERROR_OUT_OF_MEMORY;
188                 }
189
190                 SAFE_FREE_AND_STRDUP(value, item->name);
191                 if(NULL == item->name) {
192                         _E("(NULL == item->name) return\n");
193                         free(item->locale);
194                         free(item);
195                         return AIL_ERROR_OUT_OF_MEMORY;
196                 }
197
198                 info->localname = g_slist_append(info->localname, item);
199
200                 return AIL_ERROR_OK;
201         } else {
202                 SAFE_FREE_AND_STRDUP(value, info->name);
203                 retv_if (!info->name, AIL_ERROR_OUT_OF_MEMORY);
204
205                 return AIL_ERROR_OK;
206         }
207 }
208
209
210
211 static ail_error_e _read_type(void *data, char *tag, char *value, uid_t uid)
212 {
213         desktop_info_s *info = data;
214
215         retv_if(!data, AIL_ERROR_INVALID_PARAMETER);
216         retv_if(!value, AIL_ERROR_INVALID_PARAMETER);
217
218         SAFE_FREE_AND_STRDUP(value, info->type);
219         retv_if (!info->type, AIL_ERROR_OUT_OF_MEMORY);
220
221         return AIL_ERROR_OK;
222 }
223
224
225 static char*
226 _get_package_from_icon(char* icon)
227 {
228         char* package;
229         char* extension;
230
231         retv_if(!icon, NULL);
232
233         package = strdup(icon);
234         retv_if(!package, NULL);
235         extension = rindex(package, '.');
236         if (extension) {
237                 *extension = '\0';
238         } else {
239                 _E("cannot extract from icon [%s] to package.", icon);
240         }
241
242         return package;
243 }
244
245
246 static char*
247 _get_icon_with_path(char* icon, uid_t uid)
248 {
249         retv_if(!icon, NULL);
250
251         if (index(icon, '/') == NULL) {
252                 char* package;
253                 char* theme = NULL;
254                 char* icon_with_path = NULL;
255                 int len;
256                 char *app_path = NULL;
257
258                 package = _get_package_from_icon(icon);
259                 retv_if(!package, NULL);
260
261 /* "db/setting/theme" is not exist */
262 #if 0
263                 theme = ail_vconf_get_str("db/setting/theme");
264                 if (!theme) {
265                         theme = strdup("default");
266                         if(!theme) {
267                                 free(package);
268                                 return NULL;
269                         }
270                 }
271 #else
272                 theme = strdup("default");
273 #endif
274
275                 len = (0x01 << 7) + strlen(icon) + strlen(package) + strlen(theme);
276                 icon_with_path = malloc(len);
277                 if(icon_with_path == NULL) {
278                         _E("icon_with_path == NULL\n");
279                         free(package);
280                         free(theme);
281                         return NULL;
282                 }
283
284                 memset(icon_with_path, 0, len);
285                 if (uid != GLOBAL_USER)
286                         sqlite3_snprintf( len, icon_with_path, "%s%q", ail_get_icon_path(uid), icon);
287                 else
288                         sqlite3_snprintf( len, icon_with_path, "%s/%q/small/%q", ail_get_icon_path(GLOBAL_USER), theme, icon);
289                         
290                 if (access (icon_with_path, F_OK)) {
291                         app_path = tzplatform_getenv(TZ_SYS_RW_APP);
292                         if (app_path)
293                                 sqlite3_snprintf( len, icon_with_path, "%s/%q/res/icons/%q/small/%q",app_path, package, theme, icon);
294                         if (access (icon_with_path, F_OK))
295                                 _E("Cannot find icon path");
296                 }
297                 free(theme);
298                 free(package);
299                 _D("Icon path : %s", icon_with_path);
300                 return icon_with_path;
301         } else {
302                 char* confirmed_icon = NULL;
303
304                 confirmed_icon = strdup(icon);
305                 retv_if(!confirmed_icon, NULL);
306                 return confirmed_icon;
307         }
308 }
309
310
311 static ail_error_e _read_icon(void *data, char *tag, char *value, uid_t uid)
312 {
313         desktop_info_s *info = data;
314
315         retv_if(!data, AIL_ERROR_INVALID_PARAMETER);
316         retv_if(!value, AIL_ERROR_INVALID_PARAMETER);
317
318         info->icon = _get_icon_with_path(value, uid);
319
320         retv_if (!info->icon, AIL_ERROR_OUT_OF_MEMORY);
321
322         return AIL_ERROR_OK;
323 }
324
325
326
327 static ail_error_e _read_categories(void *data, char *tag, char *value, uid_t uid)
328 {
329         desktop_info_s *info = data;
330
331         retv_if(!data, AIL_ERROR_INVALID_PARAMETER);
332         retv_if(!value, AIL_ERROR_INVALID_PARAMETER);
333
334         SAFE_FREE_AND_STRDUP(value, info->categories);
335         retv_if (!info->categories, AIL_ERROR_OUT_OF_MEMORY);
336
337         return AIL_ERROR_OK;
338 }
339
340
341
342 static ail_error_e _read_version(void *data, char *tag, char *value, uid_t uid)
343 {
344         desktop_info_s *info = data;
345
346         retv_if(!data, AIL_ERROR_INVALID_PARAMETER);
347         retv_if(!value, AIL_ERROR_INVALID_PARAMETER);
348
349         SAFE_FREE_AND_STRDUP(value, info->version);
350         retv_if (!info->version, AIL_ERROR_OUT_OF_MEMORY);
351
352         return AIL_ERROR_OK;
353 }
354
355
356
357 static ail_error_e _read_mimetype(void *data, char *tag, char *value, uid_t uid)
358 {
359         desktop_info_s *info = data;
360         int size, total_len = 0;
361         char *mimes_origin, *mimes_changed, *token_unalias, *save_ptr;
362
363         retv_if(!data, AIL_ERROR_INVALID_PARAMETER);
364         retv_if(!value, AIL_ERROR_INVALID_PARAMETER);
365         retv_if(!strlen(value), AIL_ERROR_FAIL);
366
367         mimes_origin = strdup(value);
368         retv_if(!mimes_origin, AIL_ERROR_OUT_OF_MEMORY);
369
370         size = getpagesize();
371         mimes_changed = calloc(1, size);
372         if(mimes_changed == NULL) {
373                 _E("(mimes_changed == NULL) return\n");
374                 free(mimes_origin);
375                 return AIL_ERROR_OUT_OF_MEMORY;
376         }
377
378         token_unalias = strtok_r(mimes_origin, ";", &save_ptr);
379
380         while (token_unalias) {
381                 int token_len;
382                 const char *token_alias;
383
384                 _rtrim(token_unalias);
385                 token_unalias = _ltrim(token_unalias);
386
387                 token_alias = xdg_mime_unalias_mime_type(token_unalias);
388                 if (!token_alias) continue;
389
390                 token_len = strlen(token_alias);
391                 if (total_len + token_len + (1<<1) >= size) {
392                         char *tmp;
393                         size *= 2;
394                         tmp = realloc(mimes_changed, size);
395                         if(!tmp) {
396                                 free(mimes_changed);
397                                 return AIL_ERROR_OUT_OF_MEMORY;
398                         }
399                         mimes_changed = tmp;
400                 }
401
402                 strncat(mimes_changed, token_alias, size-1);
403                 total_len += token_len;
404
405                 token_unalias = strtok_r(NULL, ";", &save_ptr);
406                 if (token_unalias) {
407                         strncat(mimes_changed, ";", size-strlen(mimes_changed)-1);
408                 }
409         }
410
411         SAFE_FREE(info->mimetype);
412         info->mimetype = mimes_changed;
413
414         return AIL_ERROR_OK;
415 }
416
417
418
419 static ail_error_e _read_nodisplay(void *data, char *tag, char *value, uid_t uid)
420 {
421         desktop_info_s* info = data;
422
423         retv_if(!data, AIL_ERROR_INVALID_PARAMETER);
424         retv_if(!value, AIL_ERROR_INVALID_PARAMETER);
425
426         info->nodisplay = !strcasecmp(value, "true");
427
428         return AIL_ERROR_OK;
429 }
430
431
432
433 static ail_error_e _read_x_slp_service(void *data, char *tag, char *value, uid_t uid)
434 {
435         desktop_info_s *info = data;
436
437         retv_if(!data, AIL_ERROR_INVALID_PARAMETER);
438         retv_if(!value, AIL_ERROR_INVALID_PARAMETER);
439
440         SAFE_FREE_AND_STRDUP(value, info->x_slp_service);
441         retv_if(!info->x_slp_service, AIL_ERROR_OUT_OF_MEMORY);
442
443         return AIL_ERROR_OK;
444 }
445
446
447
448 static ail_error_e _read_x_slp_packagetype(void *data, char *tag, char *value, uid_t uid)
449 {
450         desktop_info_s *info = data;
451
452         retv_if(!data, AIL_ERROR_INVALID_PARAMETER);
453         retv_if(!value, AIL_ERROR_INVALID_PARAMETER);
454
455         SAFE_FREE_AND_STRDUP(value, info->x_slp_packagetype);
456         retv_if(!info->x_slp_packagetype, AIL_ERROR_OUT_OF_MEMORY);
457
458         return AIL_ERROR_OK;
459 }
460
461
462
463 static ail_error_e _read_x_slp_packagecategories(void *data, char *tag, char *value, uid_t uid)
464 {
465         desktop_info_s *info = data;
466
467         retv_if(!data, AIL_ERROR_INVALID_PARAMETER);
468         retv_if(!value, AIL_ERROR_INVALID_PARAMETER);
469
470         SAFE_FREE_AND_STRDUP(value, info->x_slp_packagecategories);
471         retv_if(!info->x_slp_packagecategories, AIL_ERROR_OUT_OF_MEMORY);
472
473         return AIL_ERROR_OK;
474 }
475
476
477
478 static ail_error_e _read_x_slp_packageid(void *data, char *tag, char *value, uid_t uid)
479 {
480         desktop_info_s *info = data;
481
482         retv_if(!data, AIL_ERROR_INVALID_PARAMETER);
483         retv_if(!value, AIL_ERROR_INVALID_PARAMETER);
484
485         SAFE_FREE_AND_STRDUP(value, info->x_slp_packageid);
486         retv_if(!info->x_slp_packageid, AIL_ERROR_OUT_OF_MEMORY);
487
488         return AIL_ERROR_OK;
489 }
490
491 static ail_error_e _read_x_slp_submodemainid(void *data, char *tag, char *value, uid_t uid)
492 {
493         desktop_info_s *info = data;
494
495         retv_if(!data, AIL_ERROR_INVALID_PARAMETER);
496         retv_if(!value, AIL_ERROR_INVALID_PARAMETER);
497
498         SAFE_FREE_AND_STRDUP(value, info->x_slp_submodemainid);
499         retv_if(!info->x_slp_submodemainid, AIL_ERROR_OUT_OF_MEMORY);
500
501         return AIL_ERROR_OK;
502 }
503
504 static ail_error_e _read_x_slp_installedstorage(void *data, char *tag, char *value, uid_t uid)
505 {
506         desktop_info_s *info = data;
507
508         retv_if(!data, AIL_ERROR_INVALID_PARAMETER);
509         retv_if(!value, AIL_ERROR_INVALID_PARAMETER);
510
511         SAFE_FREE_AND_STRDUP(value, info->x_slp_installedstorage);
512         retv_if(!info->x_slp_installedstorage, AIL_ERROR_OUT_OF_MEMORY);
513
514         return AIL_ERROR_OK;
515 }
516
517 static ail_error_e _read_x_slp_uri(void *data, char *tag, char *value, uid_t uid)
518 {
519         desktop_info_s *info = data;
520
521         retv_if(!data, AIL_ERROR_INVALID_PARAMETER);
522         retv_if(!value, AIL_ERROR_INVALID_PARAMETER);
523
524         SAFE_FREE_AND_STRDUP(value, info->x_slp_uri);
525         retv_if(!info->x_slp_uri, AIL_ERROR_OUT_OF_MEMORY);
526
527         return AIL_ERROR_OK;
528 }
529
530
531
532 static ail_error_e _read_x_slp_svc(void *data, char *tag, char *value, uid_t uid)
533 {
534         desktop_info_s *info = data;
535
536         retv_if(!data, AIL_ERROR_INVALID_PARAMETER);
537         retv_if(!value, AIL_ERROR_INVALID_PARAMETER);
538
539         SAFE_FREE_AND_STRDUP(value, info->x_slp_svc);
540         retv_if(!info->x_slp_svc, AIL_ERROR_OUT_OF_MEMORY);
541
542         return AIL_ERROR_OK;
543 }
544
545
546
547 static ail_error_e _read_x_slp_taskmanage(void *data, char *tag, char *value, uid_t uid)
548 {
549         desktop_info_s *info = data;
550
551         retv_if(!data, AIL_ERROR_INVALID_PARAMETER);
552         retv_if(!value, AIL_ERROR_INVALID_PARAMETER);
553
554         info->x_slp_taskmanage = !strcasecmp(value, "true");
555
556         return AIL_ERROR_OK;
557 }
558
559
560
561 static ail_error_e _read_x_slp_multiple(void *data, char *tag, char *value, uid_t uid)
562 {
563         desktop_info_s *info = data;
564
565         retv_if(!data, AIL_ERROR_INVALID_PARAMETER);
566         retv_if(!value, AIL_ERROR_INVALID_PARAMETER);
567
568         info->x_slp_multiple = !strcasecmp(value, "true");
569
570         return AIL_ERROR_OK;
571 }
572
573
574
575 static ail_error_e _read_x_slp_removable(void *data, char *tag, char *value, uid_t uid)
576 {
577         desktop_info_s *info = data;
578
579         retv_if(!data, AIL_ERROR_INVALID_PARAMETER);
580         retv_if(!value, AIL_ERROR_INVALID_PARAMETER);
581
582         info->x_slp_removable = !strcasecmp(value, "true");
583
584         return AIL_ERROR_OK;
585 }
586
587
588 static ail_error_e _read_x_slp_submode(void *data, char *tag, char *value, uid_t uid)
589 {
590         desktop_info_s *info = data;
591
592         retv_if(!data, AIL_ERROR_INVALID_PARAMETER);
593         retv_if(!value, AIL_ERROR_INVALID_PARAMETER);
594
595         info->x_slp_submode = !strcasecmp(value, "true");
596
597         return AIL_ERROR_OK;
598 }
599
600 static ail_error_e _read_x_slp_appid(void *data, char *tag, char *value, uid_t uid)
601 {
602         desktop_info_s *info = data;
603
604         retv_if(!data, AIL_ERROR_INVALID_PARAMETER);
605         retv_if(!value, AIL_ERROR_INVALID_PARAMETER);
606
607         SAFE_FREE_AND_STRDUP(value, info->x_slp_appid);
608         retv_if(!info->x_slp_appid, AIL_ERROR_OUT_OF_MEMORY);
609
610         return AIL_ERROR_OK;
611 }
612
613
614 static ail_error_e _read_x_slp_pkgid(void *data, char *tag, char *value, uid_t uid)
615 {
616         desktop_info_s *info = data;
617
618         retv_if(!data, AIL_ERROR_INVALID_PARAMETER);
619         retv_if(!value, AIL_ERROR_INVALID_PARAMETER);
620
621         SAFE_FREE_AND_STRDUP(value, info->x_slp_pkgid);
622         retv_if(!info->x_slp_pkgid, AIL_ERROR_OUT_OF_MEMORY);
623
624         return AIL_ERROR_OK;
625 }
626
627
628 static ail_error_e _read_x_slp_domain(void *data, char *tag, char *value, uid_t uid)
629 {
630         desktop_info_s *info = data;
631
632         retv_if(!data, AIL_ERROR_INVALID_PARAMETER);
633         retv_if(!value, AIL_ERROR_INVALID_PARAMETER);
634
635         SAFE_FREE_AND_STRDUP(value, info->x_slp_domain);
636         retv_if(!info->x_slp_appid, AIL_ERROR_OUT_OF_MEMORY);
637
638         return AIL_ERROR_OK;
639 }
640
641
642 static ail_error_e _read_x_slp_enabled(void *data, char *tag, char *value, uid_t uid)
643 {
644         desktop_info_s *info = data;
645
646         retv_if(!data, AIL_ERROR_INVALID_PARAMETER);
647         retv_if(!value, AIL_ERROR_INVALID_PARAMETER);
648
649         info->x_slp_enabled = !strcasecmp(value, "true");
650
651         return AIL_ERROR_OK;
652 }
653
654
655 static struct entry_parser entry_parsers[] = {
656         {
657                 .field = "exec",
658                 .value_cb = _read_exec,
659         },
660         {
661                 .field = "name",
662                 .value_cb = _read_name,
663         },
664         {
665                 .field = "type",
666                 .value_cb = _read_type,
667         },
668         {
669                 .field = "icon",
670                 .value_cb = _read_icon,
671         },
672         {
673                 .field = "categories",
674                 .value_cb = _read_categories,
675         },
676         {
677                 .field = "version",
678                 .value_cb = _read_version,
679         },
680         {
681                 .field = "mimetype",
682                 .value_cb = _read_mimetype,
683         },
684         {
685                 .field = "x-tizen-service",
686                 .value_cb = _read_x_slp_service,
687         },
688         {
689                 .field = "x-tizen-packagetype",
690                 .value_cb = _read_x_slp_packagetype,
691         },
692         {
693                 .field = "x-tizen-packagecategories",
694                 .value_cb = _read_x_slp_packagecategories,
695         },
696         {
697                 .field = "x-tizen-packageid",
698                 .value_cb = _read_x_slp_packageid,
699         },
700         {
701                 .field = "x-tizen-submodemainid",
702                 .value_cb = _read_x_slp_submodemainid,
703         },
704         {
705                 .field = "x-tizen-installedstorage",
706                 .value_cb = _read_x_slp_installedstorage,
707         },
708         {
709                 .field = "x-tizen-uri",
710                 .value_cb = _read_x_slp_uri,
711         },
712         {
713                 .field = "x-tizen-svc",
714                 .value_cb = _read_x_slp_svc,
715         },
716         {
717                 .field = "nodisplay",
718                 .value_cb = _read_nodisplay,
719         },
720         {
721                 .field = "x-tizen-taskmanage",
722                 .value_cb = _read_x_slp_taskmanage,
723         },
724         {
725                 .field = "x-tizen-enabled",
726                 .value_cb = _read_x_slp_enabled,
727         },
728         {
729                 .field = "x-tizen-submode",
730                 .value_cb = _read_x_slp_submode,
731         },
732         {
733                 .field = "x-tizen-multiple",
734                 .value_cb = _read_x_slp_multiple,
735         },
736         {
737                 .field = "x-tizen-removable",
738                 .value_cb = _read_x_slp_removable,
739         },
740         {
741                 .field = "x-tizen-appid",
742                 .value_cb = _read_x_slp_appid,
743         },
744         {
745                 .field = "x-tizen-pkgid",
746                 .value_cb = _read_x_slp_pkgid,
747         },
748         {
749                 .field = "x-tizen-domain",
750                 .value_cb = _read_x_slp_domain,
751         },
752         {
753                 .field = "x-tizen-enabled",
754                 .value_cb = _read_x_slp_domain,
755         },
756         {
757                 .field = NULL,
758                 .value_cb = NULL,
759         },
760 };
761
762
763
764 /* Utility functions */
765 static int _count_all(uid_t uid)
766 {
767         ail_error_e ret;
768         int count;
769
770         if (uid != GLOBAL_USER)
771                 ret = ail_filter_count_usr_appinfo(NULL, &count, uid);
772         else
773                 ret = ail_filter_count_appinfo(NULL, &count);   
774         if(ret != AIL_ERROR_OK) {
775                 _E("cannot count appinfo");
776                 count = -1;
777         }
778
779         retv_if(ret != AIL_ERROR_OK, -1);
780
781         return count;
782 }
783
784 char *_pkgname_to_desktop(const char *package, uid_t uid)
785 {
786         char *desktop;
787         char *desktop_path;
788         int size;
789
790         retv_if(!package, NULL);
791
792   desktop_path = ail_get_desktop_path(uid);
793
794         size = strlen(desktop_path) + strlen(package) + 10;
795         desktop = malloc(size);
796         retv_if(!desktop, NULL);
797
798   snprintf(desktop, size, "%s/%s.desktop", desktop_path, package);
799
800   _D("uid: %d / desktop: [%s]\n",  uid, desktop);
801
802         return desktop;
803 }
804
805 static inline int _bind_local_info(desktop_info_s* info, sqlite3_stmt * stmt)
806 {
807         int ret = 0;
808         unsigned long i = 0;
809         struct name_item *item;
810         GSList* localname;
811         retv_if(!info, AIL_ERROR_INVALID_PARAMETER);
812         retv_if(!info->localname, AIL_ERROR_INVALID_PARAMETER);
813         retv_if(!stmt, AIL_ERROR_INVALID_PARAMETER);
814         localname = info->localname;
815         while (localname) {
816                 item = (struct name_item *)     localname->data;
817                 if (item && item->locale && item->name) {
818                         // Bind values for a triplet : package, locale, name
819                         retv_if(db_bind_text(stmt, i+1, info->package) != AIL_ERROR_OK, AIL_ERROR_DB_FAILED);
820                         retv_if(db_bind_text(stmt, i+2, item->locale) != AIL_ERROR_OK, AIL_ERROR_DB_FAILED);
821                         retv_if(db_bind_text(stmt, i+3, item->name) != AIL_ERROR_OK, AIL_ERROR_DB_FAILED);
822                         i += 3;
823                 }
824                 localname = g_slist_next(localname);
825         }
826         return AIL_ERROR_OK;
827 }
828
829
830 static inline int _len_local_info(desktop_info_s* info)
831 {
832         int len = 0;
833         struct name_item *item;
834         GSList* localname;
835         retv_if(!info, AIL_ERROR_INVALID_PARAMETER);
836         if(info->localname)     {
837                 localname = info->localname;
838                 while (localname) {
839                         item = (struct name_item *)     localname->data;
840                         if (item && item->locale && item->name)
841                                 len ++;
842                         localname = g_slist_next(localname);
843                 }
844         }
845         return len;
846 }
847
848
849 static inline int _insert_local_info(desktop_info_s* info, uid_t uid)
850 {
851         int len_query = SQL_INSERT_LOCALNAME_STR_LEN;
852         int nb_locale_args;
853         char *query;
854         int ret = AIL_ERROR_OK;
855         sqlite3_stmt *stmt = NULL;
856         int i = 0;
857         retv_if(!info, AIL_ERROR_INVALID_PARAMETER);
858         retv_if(!info->localname, AIL_ERROR_INVALID_PARAMETER);
859
860         nb_locale_args = _len_local_info(info);
861
862         retv_if(!nb_locale_args, AIL_ERROR_INVALID_PARAMETER);
863
864         len_query += SQL_LOCALNAME_TRIPLET_STR_LEN*nb_locale_args +1;
865
866         query = (char *) malloc(len_query);
867         retv_if(!query, AIL_ERROR_OUT_OF_MEMORY);
868         stpncpy(query, SQL_INSERT_LOCALNAME_INIT_STR, len_query);
869         for (i = 0; i <  nb_locale_args - 1; i++)
870                 strcat(query, SQL_LOCALNAME_TRIPLET_STR);
871
872         do {
873                 if(uid != GLOBAL_USER)
874                         ret = db_prepare_rw(query, &stmt);
875                 else 
876                         ret = db_prepare_globalrw(query, &stmt);
877                 if (ret < 0) break;
878
879                 ret = _bind_local_info(info, stmt);
880                 if (ret < 0) {
881                         _E("Can't bind locale information to this query - %s. ",query);
882                         db_finalize(stmt);
883                         break;
884                 }
885                 ret = db_step(stmt);
886                 if (ret != AIL_ERROR_NO_DATA) {
887                         /* Insert Request doesn't return any data.
888                          * db_step should returns AIL_ERROR_NO_DATA in this case. */
889                         _E("Can't execute this query - %s. ",query);
890                         db_finalize(stmt);
891                         break;
892                 }
893                 ret = db_finalize(stmt);
894         } while(0);
895
896         free(query);
897         return ret;
898 }
899
900 static inline int _strlen_desktop_info(desktop_info_s* info)
901 {
902         int len = 0;
903
904         retv_if(!info, AIL_ERROR_INVALID_PARAMETER);
905
906         if (info->package) len += strlen(info->package);
907         if (info->exec) len += strlen(info->exec);
908         if (info->name) len += strlen(info->name);
909         if (info->type) len += strlen(info->type);
910         if (info->icon) len += strlen(info->icon);
911         if (info->categories) len += strlen(info->categories);
912         if (info->version) len += strlen(info->version);
913         if (info->mimetype) len += strlen(info->mimetype);
914         if (info->x_slp_service) len += strlen(info->x_slp_service);
915         if (info->x_slp_packagetype) len += strlen(info->x_slp_packagetype);
916         if (info->x_slp_packagecategories) len += strlen(info->x_slp_packagecategories);
917         if (info->x_slp_packageid) len += strlen(info->x_slp_packageid);
918         if (info->x_slp_uri) len += strlen(info->x_slp_uri);
919         if (info->x_slp_svc) len += strlen(info->x_slp_svc);
920         if (info->x_slp_exe_path) len += strlen(info->x_slp_exe_path);
921         if (info->x_slp_appid) len += strlen(info->x_slp_appid);
922         if (info->desktop) len += strlen(info->desktop);
923         if (info->x_slp_submodemainid) len += strlen(info->x_slp_submodemainid);
924         if (info->x_slp_installedstorage) len += strlen(info->x_slp_installedstorage);
925
926         return len;
927 }
928
929
930 int __is_ail_initdb(void)
931 {
932         if( getenv("AIL_INITDB") || getenv("INITDB") )
933                 return 1;
934         else
935                 return 0;
936 }
937
938 /* Manipulating desktop_info functions */
939 static ail_error_e _init_desktop_info(desktop_info_s *info, const char *package, uid_t uid)
940 {
941         static int is_initdb = -1;
942
943   _D("package - [%s].", package);
944
945         if(is_initdb == -1)
946                 is_initdb = __is_ail_initdb();
947
948         retv_if(!info, AIL_ERROR_INVALID_PARAMETER);
949         retv_if(!package, AIL_ERROR_INVALID_PARAMETER);
950
951         /* defaults */
952         info->package = package;
953
954         info->x_slp_taskmanage = 1;
955         info->x_slp_removable = 1;
956         info->x_slp_submode = 0;
957
958         if(is_initdb)
959                 info->x_slp_installedtime = 0;
960         else
961                 info->x_slp_installedtime = time(NULL);
962
963 #ifdef PKGTYPE
964         info->x_slp_packagetype = strdup(PKGTYPE);
965 #else
966         info->x_slp_packagetype = strdup("rpm");
967 #endif
968         retv_if(!info->x_slp_packagetype, AIL_ERROR_OUT_OF_MEMORY);
969
970         info->x_slp_packageid = strdup(package);
971         retv_if(!info->x_slp_packageid, AIL_ERROR_OUT_OF_MEMORY);
972         info->x_slp_appid = strdup(package);
973         retv_if(!info->x_slp_appid, AIL_ERROR_OUT_OF_MEMORY);
974
975         info->x_slp_enabled = 1;
976
977         info->desktop = _pkgname_to_desktop(package, uid);
978         retv_if(!info->desktop, AIL_ERROR_FAIL);
979
980   _D("desktop - [%s].", info->desktop);
981
982         return AIL_ERROR_OK;
983 }
984
985
986
987 static ail_error_e _read_desktop_info(desktop_info_s* info,uid_t uid)
988 {
989         char *line = NULL;
990         FILE *fp;
991         size_t size = 0;
992         ssize_t read;
993
994         retv_if(!info, AIL_ERROR_INVALID_PARAMETER);
995
996         fp = fopen(info->desktop, "r");
997         retv_if(!fp, AIL_ERROR_FAIL);
998
999         while ((read = getline(&line, &size, fp)) != -1) {
1000                 int len, idx;
1001                 char *tmp, *field, *field_name, *tag, *value;
1002
1003                 tmp = _ltrim(line);
1004                 if(tmp == NULL) continue;
1005                 if (*tmp == '#') continue;
1006                 if (_rtrim(tmp) <= 0) continue;
1007
1008                 len = strlen(line) + 1;
1009                 field = calloc(1, len);
1010                 field_name = calloc(1, len);
1011                 tag = calloc(1, len);
1012                 value = calloc(1, len);
1013
1014                 if (!field || !field_name || !tag || !value) {
1015                         goto NEXT;
1016                 }
1017
1018                 sscanf(tmp, "%[^=]=%[^\n]", field, value);
1019                 _rtrim(field);
1020                 tmp = _ltrim(value);
1021
1022                 sscanf(field, "%[^[][%[^]]]", field_name, tag);
1023
1024                 if (!field_name || !strlen(field_name)){
1025                         goto NEXT;
1026                 }
1027
1028                 for (idx = 0; entry_parsers[idx].field; idx ++) {
1029                         if (!g_ascii_strcasecmp(entry_parsers[idx].field, field_name) && entry_parsers[idx].value_cb) {
1030                                 if (entry_parsers[idx].value_cb(info, tag, tmp,uid) != AIL_ERROR_OK) {
1031                                         _E("field - [%s] is wrong.", field_name);
1032                                 }
1033                                 break;
1034                         }
1035                 }
1036 NEXT:
1037                 SAFE_FREE(field);
1038                 SAFE_FREE(field_name);
1039                 SAFE_FREE(tag);
1040                 SAFE_FREE(value);
1041         }
1042
1043         _D("Read (%s).", info->package);
1044         fclose(fp);
1045
1046         return AIL_ERROR_OK;
1047 }
1048
1049
1050 static ail_error_e _retrieve_all_column_to_desktop_info(desktop_info_s* info, sqlite3_stmt *stmt)
1051 {
1052         int i, j;
1053         ail_error_e err;
1054         char **values;
1055         char *col;
1056
1057         retv_if(!info, AIL_ERROR_INVALID_PARAMETER);
1058
1059         values = calloc(NUM_OF_PROP, sizeof(char *));
1060         retv_if(!values, AIL_ERROR_OUT_OF_MEMORY);
1061
1062         for (i = 0; i < NUM_OF_PROP; i++) {
1063                 err = db_column_str(stmt, i, &col);
1064                 if (AIL_ERROR_OK != err)
1065                         break;
1066
1067                 if (!col) {
1068                         values[i] = NULL;
1069                 } else {
1070                         values[i] = strdup(col);
1071                         if (!values[i]) {
1072                                 err = AIL_ERROR_OUT_OF_MEMORY;
1073                                 goto NEXT;
1074                         }
1075                 }
1076         }
1077
1078         SAFE_FREE_AND_STRDUP(values[E_AIL_PROP_EXEC_STR], info->exec);
1079         SAFE_FREE_AND_STRDUP(values[E_AIL_PROP_NAME_STR], info->name);
1080         SAFE_FREE_AND_STRDUP(values[E_AIL_PROP_TYPE_STR], info->type);
1081         SAFE_FREE_AND_STRDUP(values[E_AIL_PROP_ICON_STR], info->icon);
1082         SAFE_FREE_AND_STRDUP(values[E_AIL_PROP_CATEGORIES_STR], info->categories);
1083         SAFE_FREE_AND_STRDUP(values[E_AIL_PROP_VERSION_STR], info->version);
1084         SAFE_FREE_AND_STRDUP(values[E_AIL_PROP_MIMETYPE_STR], info->mimetype);
1085         SAFE_FREE_AND_STRDUP(values[E_AIL_PROP_X_SLP_SERVICE_STR], info->x_slp_service);
1086         SAFE_FREE_AND_STRDUP(values[E_AIL_PROP_X_SLP_PACKAGETYPE_STR], info->x_slp_packagetype);
1087         SAFE_FREE_AND_STRDUP(values[E_AIL_PROP_X_SLP_PACKAGECATEGORIES_STR], info->x_slp_packagecategories);
1088         SAFE_FREE_AND_STRDUP(values[E_AIL_PROP_X_SLP_PACKAGEID_STR], info->x_slp_packageid);
1089         SAFE_FREE_AND_STRDUP(values[E_AIL_PROP_X_SLP_URI_STR], info->x_slp_uri);
1090         SAFE_FREE_AND_STRDUP(values[E_AIL_PROP_X_SLP_SVC_STR], info->x_slp_svc);
1091         SAFE_FREE_AND_STRDUP(values[E_AIL_PROP_X_SLP_EXE_PATH], info->x_slp_exe_path);
1092         SAFE_FREE_AND_STRDUP(values[E_AIL_PROP_X_SLP_APPID_STR], info->x_slp_appid);
1093         SAFE_FREE_AND_STRDUP(values[E_AIL_PROP_X_SLP_PKGID_STR], info->x_slp_pkgid);
1094         SAFE_FREE_AND_STRDUP(values[E_AIL_PROP_X_SLP_DOMAIN_STR], info->x_slp_domain);
1095         SAFE_FREE_AND_STRDUP(values[E_AIL_PROP_X_SLP_SUBMODEMAINID_STR], info->x_slp_submodemainid);
1096         SAFE_FREE_AND_STRDUP(values[E_AIL_PROP_X_SLP_INSTALLEDSTORAGE_STR], info->x_slp_installedstorage);
1097
1098         info->x_slp_installedtime = atoi(values[E_AIL_PROP_X_SLP_INSTALLEDTIME_INT]);
1099
1100         info->nodisplay = atoi(values[E_AIL_PROP_NODISPLAY_BOOL]);
1101         info->x_slp_taskmanage = atoi(values[E_AIL_PROP_X_SLP_TASKMANAGE_BOOL]);
1102         info->x_slp_multiple = atoi(values[E_AIL_PROP_X_SLP_MULTIPLE_BOOL]);
1103         info->x_slp_removable = atoi(values[E_AIL_PROP_X_SLP_REMOVABLE_BOOL]);
1104         info->x_slp_ishorizontalscale = atoi(values[E_AIL_PROP_X_SLP_ISHORIZONTALSCALE_BOOL]);
1105         info->x_slp_enabled = atoi(values[E_AIL_PROP_X_SLP_ENABLED_BOOL]);
1106         info->x_slp_submode = atoi(values[E_AIL_PROP_X_SLP_SUBMODE_BOOL]);
1107
1108         err = AIL_ERROR_OK;
1109
1110 NEXT:
1111         for (j = 0; j < i; ++j) {
1112                 if (values[j])
1113                         free(values[j]);
1114         }
1115         if (values)
1116                 free(values);
1117         return err;
1118 }
1119
1120
1121 static ail_error_e _load_desktop_info(desktop_info_s* info, uid_t uid)
1122 {
1123         ail_error_e ret;
1124         char query[AIL_SQL_QUERY_MAX_LEN];
1125         sqlite3_stmt *stmt = NULL;
1126         char w[AIL_SQL_QUERY_MAX_LEN];
1127
1128         retv_if(!info, AIL_ERROR_INVALID_PARAMETER);
1129
1130         snprintf(w, sizeof(w), sql_get_filter(E_AIL_PROP_X_SLP_APPID_STR), info->package);
1131
1132         snprintf(query, sizeof(query), "SELECT %s FROM %s WHERE %s",SQL_FLD_APP_INFO, SQL_TBL_APP_INFO, w);
1133
1134         do {
1135                 ret = db_open(DB_OPEN_RO, uid);
1136                 if (ret < 0) break;
1137
1138                 if (uid != GLOBAL_USER) {
1139                         ret = db_prepare(query, &stmt);
1140                 } else {
1141                         ret = db_prepare_globalro(query, &stmt);
1142                 }
1143
1144                 if (ret < 0) break;
1145
1146                 ret = db_step(stmt);
1147                 if (ret < 0) {
1148                         db_finalize(stmt);
1149                         break;
1150                 }
1151
1152                 ret = _retrieve_all_column_to_desktop_info(info, stmt);
1153                 if (ret < 0) {
1154                         db_finalize(stmt);
1155                         break;
1156                 }
1157
1158                 ret = db_finalize(stmt);
1159                 if (ret < 0) break;
1160
1161                 return AIL_ERROR_OK;
1162         } while(0);
1163
1164         return ret;
1165 }
1166
1167 static ail_error_e _modify_desktop_info_bool(desktop_info_s* info,
1168                                                   const char *property,
1169                                                   bool value)
1170 {
1171         ail_prop_bool_e prop;
1172         int val;
1173
1174         retv_if(!info, AIL_ERROR_INVALID_PARAMETER);
1175         retv_if(!property, AIL_ERROR_INVALID_PARAMETER);
1176
1177         prop = _ail_convert_to_prop_bool(property);
1178
1179         if (prop < E_AIL_PROP_BOOL_MIN || prop > E_AIL_PROP_BOOL_MAX)
1180                 return AIL_ERROR_INVALID_PARAMETER;
1181
1182         switch (prop) {
1183                 case E_AIL_PROP_X_SLP_ENABLED_BOOL:
1184                         info->x_slp_enabled = (int)value;
1185                         break;
1186                 default:
1187                         return AIL_ERROR_FAIL;
1188         }
1189
1190         return AIL_ERROR_OK;
1191 }
1192
1193
1194 static ail_error_e _modify_desktop_info_str(desktop_info_s* info,
1195                                                   const char *property,
1196                                                   const char *value)
1197 {
1198         ail_prop_bool_e prop;
1199         int val;
1200
1201         retv_if(!info, AIL_ERROR_INVALID_PARAMETER);
1202         retv_if(!property, AIL_ERROR_INVALID_PARAMETER);
1203
1204         prop = _ail_convert_to_prop_str(property);
1205
1206         if (prop < E_AIL_PROP_STR_MIN || prop > E_AIL_PROP_STR_MAX)
1207                 return AIL_ERROR_INVALID_PARAMETER;
1208
1209         switch (prop) {
1210                 case E_AIL_PROP_NAME_STR:
1211                         SAFE_FREE_AND_STRDUP(value, info->name);
1212                         retv_if (!info->name, AIL_ERROR_OUT_OF_MEMORY);
1213                         break;
1214                 case E_AIL_PROP_X_SLP_SVC_STR:
1215                         SAFE_FREE_AND_STRDUP(value, info->x_slp_svc);
1216                         retv_if (!info->x_slp_svc, AIL_ERROR_OUT_OF_MEMORY);
1217                         break;
1218                 case E_AIL_PROP_X_SLP_INSTALLEDSTORAGE_STR:
1219                         SAFE_FREE_AND_STRDUP(value, info->x_slp_installedstorage);
1220                         retv_if (!info->x_slp_installedstorage, AIL_ERROR_OUT_OF_MEMORY);
1221                         break;
1222                 default:
1223                         _E("prop[%d] is not defined\n", prop);
1224                         return AIL_ERROR_FAIL;
1225         }
1226
1227         return AIL_ERROR_OK;
1228 }
1229
1230
1231 static inline void _insert_localname(gpointer data, gpointer user_data, uid_t uid)
1232 {
1233         char query[512];
1234
1235         struct name_item *item = (struct name_item *)data;
1236         desktop_info_s *info = (desktop_info_s *)user_data;
1237
1238         sqlite3_snprintf(sizeof(query), query, "insert into localname (package, locale, name, x_slp_pkgid) "
1239                         "values ('%q', '%q', '%q', '%q');",
1240                         info->package, item->locale, item->name, info->x_slp_pkgid);
1241         if(uid != GLOBAL_USER) {
1242                 if (db_exec_usr_rw(query) < 0)
1243                         _E("Failed to insert local name of package[%s]",info->package);
1244         } else {
1245                 if (db_exec_glo_rw(query) < 0)
1246                         _E("Failed to insert local name of package[%s]",info->package);
1247         }
1248 }
1249
1250 static ail_error_e _insert_desktop_info(desktop_info_s *info, uid_t uid)
1251 {
1252         char *query;
1253         int len;
1254         ail_error_e ret;
1255
1256         len = _strlen_desktop_info(info) + (0x01 << 10);
1257         query = calloc(1, len);
1258         retv_if(!query, AIL_ERROR_OUT_OF_MEMORY);
1259
1260         sqlite3_snprintf(len, query, "insert into app_info ("
1261                 "package, "
1262                 "exec, name, "
1263                 "type, "
1264                 "icon, "
1265                 "categories, "
1266                 "version, "
1267                 "mimetype, "
1268                 "x_slp_service, "
1269                 "x_slp_packagetype, "
1270                 "x_slp_packagecategories, "
1271                 "x_slp_packageid, "
1272                 "x_slp_uri, "
1273                 "x_slp_svc, "
1274                 "x_slp_exe_path, "
1275                 "x_slp_appid, "
1276                 "x_slp_pkgid, "
1277                 "x_slp_domain, "
1278                 "x_slp_submodemainid, "
1279                 "x_slp_installedstorage, "
1280                 "x_slp_baselayoutwidth, "
1281                 "x_slp_installedtime, "
1282                 "nodisplay, "
1283                 "x_slp_taskmanage, "
1284                 "x_slp_multiple, "
1285                 "x_slp_removable, "
1286                 "x_slp_ishorizontalscale, "
1287                 "x_slp_enabled, "
1288                 "x_slp_submode, "
1289                 "desktop) "
1290                 "values "
1291                 "('%q', '%q', '%q', '%q', '%q', "
1292                 "'%q', '%q', '%q', '%q', '%q', "
1293                 "'%q', '%q', '%q', '%q', '%q', "
1294                 "'%q', '%q', '%q', '%q', '%q', "
1295                 "%d, %d, %d, %d, %d, %d, %d,"
1296                 "%d, %d, "
1297                 "'%q');",
1298                 info->package,
1299                 info->exec,
1300                 info->name,
1301                 info->type,
1302                 info->icon,
1303                 info->categories,
1304                 info->version,
1305                 info->mimetype,
1306                 info->x_slp_service,
1307                 info->x_slp_packagetype,
1308                 info->x_slp_packagecategories,
1309                 info->x_slp_packageid,
1310                 info->x_slp_uri,
1311                 info->x_slp_svc,
1312                 info->x_slp_exe_path,
1313                 info->x_slp_appid,
1314                 info->x_slp_pkgid,
1315                 info->x_slp_domain,
1316                 info->x_slp_submodemainid,
1317                 info->x_slp_installedstorage,
1318                 info->x_slp_baselayoutwidth,
1319                 info->x_slp_installedtime,
1320                 info->nodisplay,
1321                 info->x_slp_taskmanage,
1322                 info->x_slp_multiple,
1323                 info->x_slp_removable,
1324                 info->x_slp_ishorizontalscale,
1325                 info->x_slp_enabled,
1326                 info->x_slp_submode,
1327                 info->desktop
1328                 );
1329
1330         ret = db_open(DB_OPEN_RW, uid);
1331         if(ret != AIL_ERROR_OK) {
1332                 _E("(tmp == NULL) return\n");
1333                 free(query);
1334                 return AIL_ERROR_DB_FAILED;
1335         }
1336         if (uid != GLOBAL_USER)
1337                 ret = db_exec_usr_rw(query);
1338         else
1339                 ret = db_exec_glo_rw(query);
1340         
1341         free(query);
1342         retv_if(ret != AIL_ERROR_OK, AIL_ERROR_DB_FAILED);
1343
1344         if (info->localname)
1345                 _insert_local_info(info, uid);
1346
1347         _D("Add (%s).", query);
1348
1349         return AIL_ERROR_OK;
1350 }
1351
1352
1353
1354 static ail_error_e _update_desktop_info(desktop_info_s *info, uid_t uid)
1355 {
1356         char *query;
1357         int len;
1358
1359         retv_if (NULL == info, AIL_ERROR_INVALID_PARAMETER);
1360
1361         if (db_open(DB_OPEN_RW, uid) < 0) {
1362                 return AIL_ERROR_DB_FAILED;
1363         }
1364
1365         len = _strlen_desktop_info(info) + (0x01 << 10);
1366         query = calloc(1, len);
1367         retv_if(!query, AIL_ERROR_OUT_OF_MEMORY);
1368
1369         sqlite3_snprintf ( len, query, "update app_info set "
1370                 "exec='%q', "
1371                 "name='%q', "
1372                 "type='%q', "
1373                 "icon='%q', "
1374                 "categories='%q', "
1375                 "version='%q', "
1376                 "mimetype='%q', "
1377                 "x_slp_service='%q', "
1378                 "x_slp_packagetype='%q', "
1379                 "x_slp_packagecategories='%q', "
1380                 "x_slp_packageid='%q', "
1381                 "x_slp_uri='%q', "
1382                 "x_slp_svc='%q', "
1383                 "x_slp_exe_path='%q', "
1384                 "x_slp_appid='%q', "
1385                 "x_slp_pkgid='%q', "
1386                 "x_slp_domain='%q', "
1387                 "x_slp_submodemainid='%q', "
1388                 "x_slp_installedstorage='%q', "
1389                 "x_slp_baselayoutwidth=%d, "
1390                 "x_slp_installedtime=%d, "
1391                 "nodisplay=%d, "
1392                 "x_slp_taskmanage=%d, "
1393                 "x_slp_multiple=%d, "
1394                 "x_slp_removable=%d, "
1395                 "x_slp_ishorizontalscale=%d, "
1396                 "x_slp_enabled=%d, "
1397                 "x_slp_submode=%d, "
1398                 "desktop='%q'"
1399                 "where package='%q'",
1400                 info->exec,
1401                 info->name,
1402                 info->type,
1403                 info->icon,
1404                 info->categories,
1405                 info->version,
1406                 info->mimetype,
1407                 info->x_slp_service,
1408                 info->x_slp_packagetype,
1409                 info->x_slp_packagecategories,
1410                 info->x_slp_packageid,
1411                 info->x_slp_uri,
1412                 info->x_slp_svc,
1413                 info->x_slp_exe_path,
1414                 info->x_slp_appid,
1415                 info->x_slp_pkgid,
1416                 info->x_slp_domain,
1417                 info->x_slp_submodemainid,
1418                 info->x_slp_installedstorage,
1419                 info->x_slp_baselayoutwidth,
1420                 info->x_slp_installedtime,
1421                 info->nodisplay,
1422                 info->x_slp_taskmanage,
1423                 info->x_slp_multiple,
1424                 info->x_slp_removable,
1425                 info->x_slp_ishorizontalscale,
1426                 info->x_slp_enabled,
1427                 info->x_slp_submode,
1428                 info->desktop,
1429                 info->package);
1430
1431         if(uid != GLOBAL_USER) {
1432                 if (db_exec_usr_rw(query) < 0) {
1433                         free (query);
1434                         return AIL_ERROR_DB_FAILED;
1435                 }
1436         } else {
1437                 if (db_exec_glo_rw(query) < 0) {
1438                         free (query);
1439                         return AIL_ERROR_DB_FAILED;
1440                 }
1441         }
1442         snprintf(query, len, "delete from localname where package = '%s'", info->package);
1443         if (uid != GLOBAL_USER) {
1444                 if (db_exec_usr_rw(query) < 0) {
1445                         free (query);
1446                         return AIL_ERROR_DB_FAILED;
1447                 }
1448         } else {
1449                 if (db_exec_glo_rw(query) < 0) {
1450                         free (query);
1451                         return AIL_ERROR_DB_FAILED;
1452                 }
1453         }
1454         if (info->localname)
1455                 _insert_local_info(info, uid);
1456
1457         _D("Update (%s).", info->package);
1458
1459         free(query);
1460
1461         return AIL_ERROR_OK;
1462 }
1463
1464
1465
1466 static ail_error_e _remove_package(const char* package, uid_t uid)
1467 {
1468         char *query;
1469         int size;
1470
1471         retv_if(!package, AIL_ERROR_INVALID_PARAMETER);
1472
1473         if (db_open(DB_OPEN_RW, uid) < 0) {
1474                 return AIL_ERROR_DB_FAILED;
1475         }
1476
1477         size = strlen(package) + (0x01 << 10);
1478         query = calloc(1, size);
1479         retv_if(!query, AIL_ERROR_OUT_OF_MEMORY);
1480
1481         snprintf(query, size, "delete from app_info where package = '%s'", package);
1482
1483         if(uid != GLOBAL_USER) {
1484                 if (db_exec_usr_rw(query) < 0) {
1485                         free(query);
1486                         return AIL_ERROR_DB_FAILED;
1487                 }
1488         } else {
1489                 if (db_exec_glo_rw(query) < 0) {
1490                         free(query);
1491                         return AIL_ERROR_DB_FAILED;
1492                 }
1493         }
1494         snprintf(query, size, "delete from localname where package = '%s'", package);
1495         _D("query=%s",query);
1496         
1497         if(uid != GLOBAL_USER) {
1498                 if (db_exec_usr_rw(query) < 0) {
1499                         free(query);
1500                         return AIL_ERROR_DB_FAILED;
1501                 }
1502         } else {
1503                 if (db_exec_glo_rw(query) < 0) {
1504                         free(query);
1505                         return AIL_ERROR_DB_FAILED;
1506                 }
1507         }
1508         _D("Remove (%s).", package);
1509         free(query);
1510
1511         return AIL_ERROR_OK;
1512 }
1513
1514 static ail_error_e _clean_pkgid_data(const char* pkgid, uid_t uid)
1515 {
1516         char *query;
1517         int size;
1518
1519         retv_if(!pkgid, AIL_ERROR_INVALID_PARAMETER);
1520
1521         if (db_open(DB_OPEN_RW, uid) ){
1522                 return AIL_ERROR_DB_FAILED;
1523         }
1524
1525         size = strlen(pkgid) + (0x01 << 10);
1526         query = calloc(1, size);
1527         retv_if(!query, AIL_ERROR_OUT_OF_MEMORY);
1528
1529         snprintf(query, size, "delete from app_info where x_slp_pkgid = '%s'", pkgid);
1530
1531         if(uid != GLOBAL_USER) {
1532                 if (db_exec_usr_rw(query) < 0) {
1533                         free(query);
1534                         return AIL_ERROR_DB_FAILED;
1535                 }
1536         } else {
1537                 if (db_exec_glo_rw(query) < 0) {
1538                         free(query);
1539                         return AIL_ERROR_DB_FAILED;
1540                 }
1541         }
1542         snprintf(query, size, "delete from localname where x_slp_pkgid = '%s'", pkgid);
1543         _D("query=%s",query);
1544
1545         if(uid != GLOBAL_USER) {
1546                 if (db_exec_usr_rw(query) < 0) {
1547                         free(query);
1548                         return AIL_ERROR_DB_FAILED;
1549                 }
1550         } else {
1551                 if (db_exec_glo_rw(query) < 0) {
1552                         free(query);
1553                         return AIL_ERROR_DB_FAILED;
1554                 }       
1555         }
1556         _D("Clean pkgid data (%s).", pkgid);
1557         free(query);
1558
1559         return AIL_ERROR_OK;
1560 }
1561
1562 static ail_error_e _send_db_done_noti(noti_type type, const char *package)
1563 {
1564         char *type_string, *noti_string;
1565         int size;
1566
1567         retv_if(!package, AIL_ERROR_INVALID_PARAMETER);
1568
1569         switch (type) {
1570                 case NOTI_ADD:
1571                         type_string = "create";
1572                         break;
1573                 case NOTI_UPDATE:
1574                         type_string = "update";
1575                         break;
1576                 case NOTI_REMOVE:
1577                         type_string = "delete";
1578                         break;
1579                 default:
1580                         return AIL_ERROR_FAIL;
1581         }
1582
1583         size = snprintf(NULL, 0, "%s:%s:%u", type_string, package, getuid());
1584         noti_string = (char*) calloc(size + 1, sizeof(char));
1585         retv_if(!noti_string, AIL_ERROR_OUT_OF_MEMORY);
1586
1587         snprintf(noti_string, size + 1, "%s:%s:%u", type_string, package, getuid());
1588         _D("Noti : %s", noti_string);
1589
1590         free(noti_string);
1591
1592         return AIL_ERROR_OK;
1593 }
1594
1595
1596 static void inline _name_item_free_func(gpointer data)
1597 {
1598         struct name_item *item = (struct name_item *)data;
1599         if (item){
1600                 SAFE_FREE(item->locale);
1601                 item->locale = NULL;
1602                 SAFE_FREE(item->name);
1603                 item->name = NULL;
1604         }
1605         SAFE_FREE(item);
1606 }
1607
1608 static void _fini_desktop_info(desktop_info_s *info)
1609 {
1610         SAFE_FREE(info->exec);
1611         SAFE_FREE(info->name);
1612         SAFE_FREE(info->type);
1613         SAFE_FREE(info->icon);
1614         SAFE_FREE(info->categories);
1615         SAFE_FREE(info->version);
1616         SAFE_FREE(info->mimetype);
1617         SAFE_FREE(info->x_slp_service);
1618         SAFE_FREE(info->x_slp_packagetype);
1619         SAFE_FREE(info->x_slp_packagecategories);
1620         SAFE_FREE(info->x_slp_packageid);
1621         SAFE_FREE(info->x_slp_uri);
1622         SAFE_FREE(info->x_slp_svc);
1623         SAFE_FREE(info->x_slp_exe_path);
1624         SAFE_FREE(info->x_slp_appid);
1625         SAFE_FREE(info->x_slp_pkgid);
1626         SAFE_FREE(info->x_slp_domain);
1627         SAFE_FREE(info->x_slp_submodemainid);
1628         SAFE_FREE(info->x_slp_installedstorage);
1629         SAFE_FREE(info->desktop);
1630         if (info->localname) {
1631                 g_slist_free_full(info->localname, _name_item_free_func);
1632                 info->localname = NULL;
1633         }
1634
1635         return;
1636 }
1637
1638 static int __is_authorized()
1639 {
1640         uid_t uid = getuid();
1641         if ((uid_t) GLOBAL_USER == uid )
1642                 return 1;
1643         else
1644                 return 0;
1645 }
1646
1647
1648 /* Public functions */
1649 EXPORT_API ail_error_e ail_usr_desktop_add(const char *appid, uid_t uid)
1650 {
1651         desktop_info_s info = {0,};
1652         ail_error_e ret;
1653
1654         retv_if(!appid, AIL_ERROR_INVALID_PARAMETER);
1655
1656         ret = _init_desktop_info(&info, appid, uid);
1657         retv_if(ret != AIL_ERROR_OK, AIL_ERROR_FAIL);
1658
1659         ret = _read_desktop_info(&info,uid);
1660         retv_if(ret != AIL_ERROR_OK, AIL_ERROR_FAIL);
1661
1662         ret = _insert_desktop_info(&info, uid);
1663         retv_if(ret != AIL_ERROR_OK, AIL_ERROR_FAIL);
1664
1665         ret = _send_db_done_noti(NOTI_ADD, appid);
1666         retv_if(ret != AIL_ERROR_OK, AIL_ERROR_FAIL);
1667
1668         _fini_desktop_info(&info);
1669
1670         return AIL_ERROR_OK;
1671 }
1672
1673 EXPORT_API ail_error_e ail_desktop_add(const char *appid)
1674 {
1675         return ail_usr_desktop_add(appid,GLOBAL_USER);
1676 }
1677
1678 EXPORT_API ail_error_e ail_usr_desktop_update(const char *appid, uid_t uid)
1679 {
1680         desktop_info_s info = {0,};
1681         ail_error_e ret;
1682
1683         retv_if(!appid, AIL_ERROR_INVALID_PARAMETER);
1684
1685         ret = _init_desktop_info(&info, appid, uid);
1686         retv_if(ret != AIL_ERROR_OK, AIL_ERROR_FAIL);
1687
1688         ret = _read_desktop_info(&info,uid);
1689         retv_if(ret != AIL_ERROR_OK, AIL_ERROR_FAIL);
1690
1691         ret = _update_desktop_info(&info, uid);
1692         retv_if(ret != AIL_ERROR_OK, AIL_ERROR_FAIL);
1693
1694         ret = _send_db_done_noti(NOTI_UPDATE, appid);
1695         retv_if(ret != AIL_ERROR_OK, AIL_ERROR_FAIL);
1696
1697         _fini_desktop_info(&info);
1698
1699         return AIL_ERROR_OK;
1700 }
1701
1702 EXPORT_API ail_error_e ail_desktop_update(const char *appid)
1703 {
1704         return ail_usr_desktop_update(appid,GLOBAL_USER);
1705 }
1706
1707
1708 EXPORT_API ail_error_e ail_usr_desktop_remove(const char *appid, uid_t uid)
1709 {
1710         ail_error_e ret;
1711
1712         retv_if(!appid, AIL_ERROR_INVALID_PARAMETER);
1713
1714         ret = _remove_package(appid, uid);
1715         retv_if(ret != AIL_ERROR_OK, AIL_ERROR_FAIL);
1716
1717         ret = _send_db_done_noti(NOTI_REMOVE, appid);
1718         retv_if(ret != AIL_ERROR_OK, AIL_ERROR_FAIL);
1719
1720         return AIL_ERROR_OK;
1721 }
1722
1723 EXPORT_API ail_error_e ail_desktop_remove(const char *appid)
1724 {
1725         return ail_usr_desktop_remove(appid, GLOBAL_USER);
1726 }
1727
1728
1729 EXPORT_API ail_error_e ail_usr_desktop_clean(const char *pkgid, uid_t uid)
1730 {
1731         ail_error_e ret;
1732
1733         retv_if(!pkgid, AIL_ERROR_INVALID_PARAMETER);
1734
1735         _D("ail_desktop_clean=%s",pkgid);
1736
1737         ret = _clean_pkgid_data(pkgid, uid);
1738         retv_if(ret != AIL_ERROR_OK, AIL_ERROR_FAIL);
1739
1740         return AIL_ERROR_OK;
1741 }
1742
1743 EXPORT_API ail_error_e ail_desktop_clean(const char *pkgid)
1744 {
1745         return ail_usr_desktop_clean(pkgid, GLOBAL_USER);
1746 }
1747
1748 EXPORT_API ail_error_e ail_usr_desktop_fota(const char *appid, uid_t uid)
1749 {
1750         desktop_info_s info = {0,};
1751         ail_error_e ret;
1752
1753         retv_if(!appid, AIL_ERROR_INVALID_PARAMETER);
1754
1755         ret = _init_desktop_info(&info, appid, uid);
1756         retv_if(ret != AIL_ERROR_OK, AIL_ERROR_FAIL);
1757
1758         ret = _read_desktop_info(&info,uid);
1759         retv_if(ret != AIL_ERROR_OK, AIL_ERROR_FAIL);
1760
1761         ret = _insert_desktop_info(&info, uid);
1762         retv_if(ret != AIL_ERROR_OK, AIL_ERROR_FAIL);
1763
1764         _fini_desktop_info(&info);
1765
1766         return AIL_ERROR_OK;
1767 }
1768
1769 EXPORT_API ail_error_e ail_desktop_fota(const char *appid)
1770 {
1771         return ail_usr_desktop_fota(appid, GLOBAL_USER);
1772 }
1773
1774
1775 EXPORT_API ail_error_e ail_desktop_appinfo_modify_usr_bool(const char *appid,
1776                                                              const char *property,
1777                                                              bool value,
1778                                                              bool broadcast, uid_t uid)
1779 {
1780         desktop_info_s info = {0,};
1781         ail_error_e ret;
1782
1783         retv_if(!appid, AIL_ERROR_INVALID_PARAMETER);
1784
1785         retv_if(strcmp(property, AIL_PROP_X_SLP_ENABLED_BOOL),
1786                 AIL_ERROR_INVALID_PARAMETER);
1787
1788         ret = _init_desktop_info(&info, appid, uid);
1789         retv_if(ret != AIL_ERROR_OK, AIL_ERROR_FAIL);
1790
1791         ret = _load_desktop_info(&info, uid);
1792         retv_if(ret != AIL_ERROR_OK, AIL_ERROR_FAIL);
1793
1794         ret = _modify_desktop_info_bool(&info, property, value);
1795         retv_if(ret != AIL_ERROR_OK, AIL_ERROR_FAIL);
1796
1797         ret = _update_desktop_info(&info, uid);
1798         retv_if(ret != AIL_ERROR_OK, AIL_ERROR_FAIL);
1799
1800         if (broadcast) {
1801                 ret = _send_db_done_noti(NOTI_UPDATE, appid);
1802                 retv_if(ret != AIL_ERROR_OK, AIL_ERROR_FAIL);
1803         }
1804
1805         _fini_desktop_info(&info);
1806
1807         return AIL_ERROR_OK;
1808 }
1809
1810 EXPORT_API ail_error_e ail_desktop_appinfo_modify_bool(const char *appid,
1811                                                              const char *property,
1812                                                              bool value,
1813                                                              bool broadcast)
1814 {
1815         return ail_desktop_appinfo_modify_usr_bool(appid, property, value, broadcast,
1816                         GLOBAL_USER);
1817 }
1818
1819
1820 EXPORT_API ail_error_e ail_desktop_appinfo_modify_usr_str(const char *appid, uid_t uid,
1821                                                              const char *property,
1822                                                              const char *value,
1823                                                              bool broadcast)
1824 {
1825         desktop_info_s info = {0,};
1826         ail_error_e ret;
1827
1828         retv_if(!appid, AIL_ERROR_INVALID_PARAMETER);
1829
1830         ret = _init_desktop_info(&info, appid, uid);
1831         retv_if(ret != AIL_ERROR_OK, AIL_ERROR_FAIL);
1832
1833         ret = _load_desktop_info(&info, uid);
1834         retv_if(ret != AIL_ERROR_OK, AIL_ERROR_FAIL);
1835
1836         _D("info.name [%s], value [%s]", info.name, value);
1837         ret = _modify_desktop_info_str(&info, property, value);
1838         retv_if(ret != AIL_ERROR_OK, AIL_ERROR_FAIL);
1839         _D("info.name [%s], value [%s]", info.name, value);
1840
1841         ret = _update_desktop_info(&info, uid);
1842         retv_if(ret != AIL_ERROR_OK, AIL_ERROR_FAIL);
1843
1844         if (broadcast) {
1845                 ret = _send_db_done_noti(NOTI_UPDATE, appid);
1846                 retv_if(ret != AIL_ERROR_OK, AIL_ERROR_FAIL);
1847         }
1848
1849         _fini_desktop_info(&info);
1850
1851         return AIL_ERROR_OK;
1852 }
1853
1854 EXPORT_API ail_error_e ail_desktop_appinfo_modify_str(const char *appid,
1855                                                              const char *property,
1856                                                              const char *value,
1857                                                              bool broadcast)
1858 {
1859         return ail_desktop_appinfo_modify_usr_str(appid, GLOBAL_USER, property, value,
1860                                 broadcast);
1861 }
1862
1863 // End of File