Add API for checking the enabled/disabled flag
[platform/framework/web/livebox-service.git] / src / livebox-service.c
1 /*
2  * Copyright 2012  Samsung Electronics Co., Ltd
3  *
4  * Licensed under the Flora License, Version 1.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.tizenopensource.org/license
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16
17 #include <stdio.h>
18 #include <errno.h>
19 #include <stdlib.h> /* malloc */
20 #include <string.h> /* strdup, strerror */
21 #include <sys/types.h>
22 #include <sys/stat.h>
23 #include <unistd.h>
24 #include <sqlite3.h>
25 #include <X11/X.h>
26 #include <X11/Xlib.h>
27 #include <ctype.h>
28
29 #include <com-core_packet.h>
30 #include <packet.h>
31 #include <dlog.h>
32 #include <db-util.h>
33 #include <package-manager.h>
34 #include <vconf.h>
35 #include <vconf-keys.h>
36 #include <ail.h>
37
38 #include "dlist.h"
39 #include "util.h"
40 #include "debug.h"
41 #include "livebox-service.h"
42
43 #define EAPI __attribute__((visibility("default")))
44 #define DEFAULT_TIMEOUT 2.0
45 #define MAX_COLUMN 80
46
47 static struct supported_size_list {
48         int w;
49         int h;
50 } SIZE_LIST[NR_OF_SIZE_LIST] = {
51         { 172, 172 }, /*!< 1x1 */
52         { 348, 172 }, /*!< 2x1 */
53         { 348, 348 }, /*!< 2x2 */
54         { 700, 172 }, /*!< 4x1 */
55         { 700, 348 }, /*!< 4x2 */
56         { 700, 520 }, /*!< 4x3 */
57         { 700, 700 }, /*!< 4x4 */
58         { 207, 207 }, /*!< 21x21 */
59         { 645, 207 }, /*!< 23x21 */
60         { 645, 645 }, /*!< 23x23 */
61 };
62
63 static struct info {
64         sqlite3 *handle;
65         const char *dbfile;
66         const char *conf_file;
67         int init_count;
68         int res_resolved;
69 } s_info = {
70         .handle = NULL,
71         .dbfile = "/opt/dbspace/.livebox.db", 
72         .conf_file = "/usr/share/data-provider-master/resolution.ini",
73         .init_count = 0,
74         .res_resolved = 0,
75 };
76
77 static inline int update_info(int width_type, int height_type, int width, int height)
78 {
79         int idx;
80
81         if (width_type == 1 && height_type == 1) {
82                 DbgPrint("1x1 Updated to %dx%d\n", width, height);
83                 idx = 0;
84         } else if (width_type == 2 && height_type == 1) {
85                 DbgPrint("2x1 Updated to %dx%d\n", width, height);
86                 idx = 1;
87         } else if (width_type == 2 && height_type == 2) {
88                 DbgPrint("2x2 Updated to %dx%d\n", width, height);
89                 idx = 2;
90         } else if (width_type == 4 && height_type == 1) {
91                 DbgPrint("4x1 Updated to %dx%d\n", width, height);
92                 idx = 3;
93         } else if (width_type == 4 && height_type == 2) {
94                 DbgPrint("4x2 Updated to %dx%d\n", width, height);
95                 idx = 4;
96         } else if (width_type == 4 && height_type == 3) {
97                 DbgPrint("4x3 Updated to %dx%d\n", width, height);
98                 idx = 5;
99         } else if (width_type == 4 && height_type == 4) {
100                 DbgPrint("4x4 Updated to %dx%d\n", width, height);
101                 idx = 6;
102         } else if (width_type == 21 && height_type == 21) {
103                 DbgPrint("Easy 1x1 Updated to %dx%d\n", width, height);
104                 idx = 7;
105         } else if (width_type == 23 && height_type == 21) {
106                 DbgPrint("Easy 3x1 Updated to %dx%d\n", width, height);
107                 idx = 8;
108         } else if (width_type == 23 && height_type == 23) {
109                 DbgPrint("Easy 3x3 Updated to %dx%d\n", width, height);
110                 idx = 9;
111         } else {
112                 ErrPrint("Unknown size type: %dx%d (%dx%d)\n", width_type, height_type, width, height);
113                 return 0;
114         }
115
116         SIZE_LIST[idx].w = width;
117         SIZE_LIST[idx].h = height;
118         return 1;
119 }
120
121 static inline int update_from_file(void)
122 {
123         FILE *fp;
124         int updated;
125         int width_type;
126         int height_type;
127         int width;
128         int height;
129         char buffer[MAX_COLUMN];
130         int ch;
131         int idx;
132         enum status {
133                 START = 0x0,
134                 TYPE = 0x01,
135                 SIZE = 0x02,
136                 COMMENT = 0x03,
137                 ERROR = 0x04,
138                 EOL = 0x05,
139                 TYPE_END = 0x06,
140                 SIZE_START = 0x07,
141         } status;
142
143         fp = fopen(s_info.conf_file, "r");
144         if (!fp) {
145                 ErrPrint("Open failed: %s\n", strerror(errno));
146                 return -EIO;
147         }
148
149         updated = 0;
150         status = START;
151         idx = 0;
152         do {
153                 ch = fgetc(fp);
154
155                 if (idx == MAX_COLUMN) {
156                         ErrPrint("Buffer overflow. Too long line. LINE MUST BE SHOT THAN %d\n", MAX_COLUMN);
157                         status = ERROR;
158                 }
159
160                 switch (status) {
161                 case START:
162                         if (isspace(ch) || ch == EOF)
163                                 continue;
164
165                         if (ch == '#') {
166                                 status = COMMENT;
167                         } else {
168                                 status = TYPE;
169                                 idx = 0;
170                                 ungetc(ch, fp);
171                         }
172                         break;
173                 case TYPE:
174                         if (isblank(ch)) {
175                                 buffer[idx] = '\0';
176                                 status = TYPE_END;
177                                 if (sscanf(buffer, "%dx%d", &width_type, &height_type) != 2) {
178                                         ErrPrint("Invalid syntax: [%s]\n", buffer);
179                                         status = ERROR;
180                                 }
181                                 break;
182                         } else if (ch == '=') {
183                                 buffer[idx] = '\0';
184                                 status = SIZE_START;
185                                 if (sscanf(buffer, "%dx%d", &width_type, &height_type) != 2) {
186                                         ErrPrint("Invalid syntax: [%s]\n", buffer);
187                                         status = ERROR;
188                                 }
189                                 break;
190                         } else if (ch == EOF) {
191                                 ErrPrint("Invalid Syntax\n");
192                                 status = ERROR;
193                                 continue;
194                         }
195                         buffer[idx++] = ch;
196                         break;
197                 case TYPE_END:
198                         if (ch == '=')
199                                 status = SIZE_START;
200                         break;
201                 case SIZE_START:
202                         if (isspace(ch) || ch == EOF)
203                                 continue;
204
205                         status = SIZE;
206                         idx = 0;
207                         ungetc(ch, fp);
208                         break;
209                 case SIZE:
210                         if (isspace(ch) || ch == EOF) {
211                                 buffer[idx] = '\0';
212                                 status = EOL;
213
214                                 if (sscanf(buffer, "%dx%d", &width, &height) != 2) {
215                                         ErrPrint("Invalid syntax: [%s]\n", buffer);
216                                         status = ERROR;
217                                 } else if (ch == EOF) {
218                                         updated += update_info(width_type, height_type, width, height);
219                                 }
220                                 break;
221                         }
222                         buffer[idx++] = ch;
223                         break;
224                 case EOL:
225                         updated += update_info(width_type, height_type, width, height);
226                         status = START;
227                         ungetc(ch, fp);
228                         break;
229                 case ERROR:
230                         if (ch == '\n' || ch == '\r' || ch == '\f')
231                                 status = START;
232                         break;
233                 case COMMENT:
234                         if (ch == '\n' || ch == '\r' || ch == '\f')
235                                 status = START;
236                         break;
237                 default:
238                         ErrPrint("Unknown status. couldn't be reach to here\n");
239                         break;
240                 }
241         } while (!feof(fp));
242         fclose(fp);
243
244         return NR_OF_SIZE_LIST - updated;
245 }
246
247 static int update_resolution(void)
248 {
249         Display *disp;
250         Window root;
251         Window dummy;
252         int x, y;
253         unsigned int width;
254         unsigned int height;
255         unsigned int border;
256         unsigned int depth;
257         register int i;
258
259         if (s_info.res_resolved)
260                 return 0;
261
262         disp = XOpenDisplay(NULL);
263         if (!disp) {
264                 ErrPrint("Failed to open a display\n");
265                 return -EFAULT;
266         }
267
268         root = XDefaultRootWindow(disp);
269         if (!XGetGeometry(disp, root, &dummy, &x, &y, &width, &height, &border, &depth)) {
270                 XCloseDisplay(disp);
271                 return -EFAULT;
272         }
273
274         if (update_from_file() == 0)
275                 DbgPrint("Resolution info is all updated by file\n");
276
277         DbgPrint("Screen resolution: %dx%d\n", width, height);
278         for (i = 0; i < NR_OF_SIZE_LIST; i++) {
279                 SIZE_LIST[i].w = (unsigned int)((double)SIZE_LIST[i].w * (double)width / 720.0f);
280                 SIZE_LIST[i].h = (unsigned int)((double)SIZE_LIST[i].h * (double)height / 1280.0f);
281                 DbgPrint("(Ratio)Size is updated [%d] %dx%d\n", i, SIZE_LIST[i].w, SIZE_LIST[i].h);
282         }
283
284         XCloseDisplay(disp);
285         s_info.res_resolved = 1;
286         return 0;
287 }
288
289 static inline sqlite3 *open_db(void)
290 {
291         sqlite3 *handle;
292
293         if (!s_info.handle) {
294                 int ret;
295
296                 ret = db_util_open(s_info.dbfile, &handle, DB_UTIL_REGISTER_HOOK_METHOD);
297                 if (ret != SQLITE_OK) {
298                         ErrPrint("Failed to open a DB\n");
299                         return NULL;
300                 }
301         } else {
302                 handle = s_info.handle;
303         }
304
305         return handle;
306 }
307
308 static inline void close_db(sqlite3 *handle)
309 {
310         if (!s_info.handle)
311                 db_util_close(handle);
312 }
313
314 static inline int convert_size_from_type(enum livebox_size_type type, int *width, int *height)
315 {
316         int idx;
317
318         switch (type) {
319         case LB_SIZE_TYPE_1x1: /*!< 172x172 */
320                 idx = 0;
321                 break;
322         case LB_SIZE_TYPE_2x1: /*!< 348x172 */
323                 idx = 1;
324                 break;
325         case LB_SIZE_TYPE_2x2: /*!< 348x348 */
326                 idx = 2;
327                 break;
328         case LB_SIZE_TYPE_4x1: /*!< 700x172 */
329                 idx = 3;
330                 break;
331         case LB_SIZE_TYPE_4x2: /*!< 700x348 */
332                 idx = 4;
333                 break;
334         case LB_SIZE_TYPE_4x3: /*!< 700x520 */
335                 idx = 5;
336                 break;
337         case LB_SIZE_TYPE_4x4: /*!< 700x700 */
338                 idx = 6;
339                 break;
340         case LB_SIZE_TYPE_EASY_1x1: /*< 207x207 */
341                 idx = 7;
342                 break;
343         case LB_SIZE_TYPE_EASY_3x1: /*!< 645x207 */
344                 idx = 8;
345                 break;
346         case LB_SIZE_TYPE_EASY_3x3: /*!< 645x645 */
347                 idx = 9;
348                 break;
349         default:
350                 return -EINVAL;
351         }
352
353         if (update_resolution() < 0)
354                 ErrPrint("Failed to update resolution\n");
355
356         *width = SIZE_LIST[idx].w;
357         *height = SIZE_LIST[idx].h;
358         return 0;
359 }
360
361 EAPI int livebox_service_trigger_update(const char *pkgname, const char *cluster, const char *category)
362 {
363         struct packet *packet;
364         struct packet *result;
365         int ret;
366
367         if (!pkgname) {
368                 ErrPrint("Invalid argument\n");
369                 return -EINVAL;
370         }
371
372         if (access("/tmp/.live.paused", R_OK) == 0) {
373                 DbgPrint("Provider is paused\n");
374                 return -ECANCELED;
375         }
376
377         if (!cluster)
378                 cluster = "user,created";
379
380         if (!category)
381                 category = "default";
382
383         packet = packet_create("service_update", "sss", pkgname, cluster, category);
384         if (!packet) {
385                 ErrPrint("Failed to create a packet for service_update\n");
386                 return -EFAULT;
387         }
388
389         result = com_core_packet_oneshot_send(SERVICE_SOCKET, packet, DEFAULT_TIMEOUT);
390         packet_unref(packet);
391
392         if (result) {
393                 if (packet_get(result, "i", &ret) != 1) {
394                         ErrPrint("Failed to parse a result packet\n");
395                         ret = -EINVAL;
396                 }
397
398                 packet_unref(result);
399         } else {
400                 ErrPrint("Failed to get result packet\n");
401                 ret = -EFAULT;
402         }
403
404         return ret;
405 }
406
407 EAPI int livebox_service_get_pkglist(int (*cb)(const char *appid, const char *pkgname, int is_prime, void *data), void *data)
408 {
409         int ret;
410         sqlite3_stmt *stmt;
411         char *appid;
412         char *pkgid;
413         int is_prime;
414         sqlite3 *handle;
415
416         if (!cb)
417                 return -EINVAL;
418
419         handle = open_db();
420         if (!handle)
421                 return -EIO;
422
423         ret = sqlite3_prepare_v2(handle, "SELECT appid, pkgid, prime FROM pkgmap", -1, &stmt, NULL);
424         if (ret != SQLITE_OK) {
425                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
426                 ret = -EIO;
427                 goto out;
428         }
429
430         ret = 0;
431         while (sqlite3_step(stmt) == SQLITE_ROW) {
432                 appid = (char *)sqlite3_column_text(stmt, 0);
433                 if (!appid || !strlen(appid)) {
434                         ErrPrint("APPID is not valid\n");
435                         continue;
436                 }
437
438                 pkgid = (char *)sqlite3_column_text(stmt, 1);
439                 if (!pkgid || !strlen(pkgid)) {
440                         ErrPrint("pkgid is not valid\n");
441                         continue;
442                 }
443
444                 is_prime = sqlite3_column_int(stmt, 2);
445
446                 ret++;
447
448                 if (cb(appid, pkgid, is_prime, data) < 0) {
449                         DbgPrint("Callback stopped package crawling\n");
450                         break;
451                 }
452         }
453
454         sqlite3_reset(stmt);
455         sqlite3_finalize(stmt);
456
457 out:
458         close_db(handle);
459         return ret;
460 }
461
462 EAPI int livebox_service_get_supported_size_types(const char *pkgid, int *cnt, int *types)
463 {
464         sqlite3_stmt *stmt;
465         sqlite3 *handle;
466         int size;
467         int ret;
468
469         if (!types || !cnt || !pkgid)
470                 return -EINVAL;
471
472         handle = open_db();
473         if (!handle)
474                 return -EIO;
475
476         ret = sqlite3_prepare_v2(handle, "SELECT size_type FROM box_size WHERE pkgid = ? ORDER BY size_type ASC", -1, &stmt, NULL);
477         if (ret != SQLITE_OK) {
478                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
479                 ret = -EIO;
480                 goto out;
481         }
482
483         ret = sqlite3_bind_text(stmt, 1, pkgid, -1, NULL);
484         if (ret != SQLITE_OK) {
485                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
486                 sqlite3_reset(stmt);
487                 sqlite3_finalize(stmt);
488                 ret = -EIO;
489                 goto out;
490         }
491
492         if (*cnt > NR_OF_SIZE_LIST)
493                 *cnt = NR_OF_SIZE_LIST;
494
495         ret = 0;
496         while (sqlite3_step(stmt) == SQLITE_ROW && ret < *cnt) {
497                 size = sqlite3_column_int(stmt, 0);
498                 types[ret] = size;
499                 ret++;
500         }
501
502         *cnt = ret;
503         sqlite3_reset(stmt);
504         sqlite3_finalize(stmt);
505         ret = 0;
506 out:
507         close_db(handle);
508         return ret;
509 }
510
511 static inline char *cur_locale(void)
512 {
513         char *language;
514         language = vconf_get_str(VCONFKEY_LANGSET);
515         if (language) {
516                 char *ptr;
517
518                 ptr = language;
519                 while (*ptr) {
520                         if (*ptr == '.') {
521                                 *ptr = '\0';
522                                 break;
523                         }
524
525                         if (*ptr == '_')
526                                 *ptr = '-';
527
528                         ptr++;
529                 }
530         } else {
531                 language = strdup("en-us");
532                 if (!language)
533                         ErrPrint("Heap: %s\n", strerror(errno));
534         }
535
536         return language;
537 }
538
539 static inline char *get_default_name(const char *pkgid)
540 {
541         sqlite3_stmt *stmt;
542         sqlite3 *handle;
543         char *name = NULL;
544         int ret;
545
546         handle = open_db();
547         if (!handle)
548                 return NULL;
549
550         ret = sqlite3_prepare_v2(handle, "SELECT name FROM client WHERE pkgid = ?", -1, &stmt, NULL);
551         if (ret != SQLITE_OK) {
552                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
553                 close_db(handle);
554                 return NULL;
555         }
556
557         ret = sqlite3_bind_text(stmt, 1, pkgid, -1, NULL);
558         if (ret != SQLITE_OK) {
559                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
560                 goto out;
561         }
562
563         ret = sqlite3_step(stmt);
564         if (ret ==  SQLITE_ROW) {
565                 const char *tmp;
566
567                 tmp = (const char *)sqlite3_column_text(stmt, 0);
568                 if (tmp && strlen(tmp)) {
569                         name = strdup(tmp);
570                         if (!name)
571                                 ErrPrint("Heap: %s\n", strerror(errno));
572                 }
573         }
574
575 out:
576         sqlite3_reset(stmt);
577         sqlite3_finalize(stmt);
578         close_db(handle);
579         return name;
580 }
581
582 static inline char *get_default_icon(const char *pkgid)
583 {
584         sqlite3_stmt *stmt;
585         sqlite3 *handle;
586         char *icon = NULL;
587         int ret;
588
589         handle = open_db();
590         if (!handle)
591                 return NULL;
592
593         ret = sqlite3_prepare_v2(handle, "SELECT icon FROM client WHERE pkgid = ?", -1, &stmt, NULL);
594         if (ret != SQLITE_OK) {
595                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
596                 close_db(handle);
597                 return NULL;
598         }
599
600         ret = sqlite3_bind_text(stmt, 1, pkgid, -1, NULL);
601         if (ret != SQLITE_OK) {
602                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
603                 goto out;
604         }
605
606         ret = sqlite3_step(stmt);
607         if (ret == SQLITE_ROW) {
608                 const char *tmp;
609
610                 tmp = (const char *)sqlite3_column_text(stmt, 0);
611                 if (tmp && strlen(tmp)) {
612                         icon = strdup(tmp);
613                         if (!icon)
614                                 ErrPrint("Heap: %s\n", strerror(errno));
615                 }
616         }
617
618 out:
619         sqlite3_reset(stmt);
620         sqlite3_finalize(stmt);
621         close_db(handle);
622         return icon;
623 }
624
625 EAPI char *livebox_service_content(const char *pkgid)
626 {
627         sqlite3_stmt *stmt;
628         sqlite3 *handle;
629         char *content = NULL;
630         int ret;
631
632         handle = open_db();
633         if (!handle)
634                 return NULL;
635
636         ret = sqlite3_prepare_v2(handle, "SELECT content FROM client WHERE pkgid = ?", -1, &stmt, NULL);
637         if (ret != SQLITE_OK) {
638                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
639                 close_db(handle);
640                 return NULL;
641         }
642
643         ret = sqlite3_bind_text(stmt, 1, pkgid, -1, NULL);
644         if (ret != SQLITE_OK) {
645                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
646                 goto out;
647         }
648
649         ret = sqlite3_step(stmt);
650         if (ret == SQLITE_ROW) {
651                 const char *tmp;
652
653                 tmp = (const char *)sqlite3_column_text(stmt, 0);
654                 if (tmp && strlen(tmp)) {
655                         content = strdup(tmp);
656                         if (!content)
657                                 ErrPrint("Heap: %s\n", strerror(errno));
658                 }
659         }
660
661 out:
662         sqlite3_reset(stmt);
663         sqlite3_finalize(stmt);
664         close_db(handle);
665         return content;
666 }
667
668 EAPI char *livebox_service_setup_appid(const char *lbid)
669 {
670         sqlite3_stmt *stmt;
671         sqlite3 *handle;
672         int ret;
673         char *appid;
674
675         handle = open_db();
676         if (!handle)
677                 return NULL;
678
679         ret = sqlite3_prepare_v2(handle, "SELECT setup FROM client WHERE pkgid = ?", -1, &stmt, NULL);
680         if (ret != SQLITE_OK) {
681                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
682                 close_db(handle);
683                 return NULL;
684         }
685
686         appid = NULL;
687         ret = sqlite3_bind_text(stmt, 1, lbid, -1, NULL);
688         if (ret != SQLITE_OK) {
689                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
690                 goto out;
691         }
692
693         ret = sqlite3_step(stmt);
694         if (ret == SQLITE_ROW) {
695                 const char *tmp;
696
697                 tmp = (const char *)sqlite3_column_text(stmt, 0);
698                 if (!tmp || !strlen(tmp))
699                         goto out;
700
701                 appid = strdup(tmp);
702                 if (!appid)
703                         ErrPrint("Error: %s\n", strerror(errno));
704         }
705
706 out:
707         sqlite3_reset(stmt);
708         sqlite3_finalize(stmt);
709         close_db(handle);
710         return appid;
711 }
712
713 EAPI int livebox_service_nodisplay(const char *pkgid)
714 {
715         sqlite3_stmt *stmt;
716         sqlite3 *handle;
717         int ret;
718
719         handle = open_db();
720         if (!handle)
721                 return 0;
722
723         ret = sqlite3_prepare_v2(handle, "SELECT nodisplay FROM client WHERE pkgid = ?", -1, &stmt, NULL);
724         if (ret != SQLITE_OK) {
725                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
726                 close_db(handle);
727                 return 0;
728         }
729
730         ret = sqlite3_bind_text(stmt, 1, pkgid, -1, NULL);
731         if (ret != SQLITE_OK) {
732                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
733                 ret = 0;
734                 goto out;
735         }
736
737         ret = sqlite3_step(stmt);
738         if (ret == SQLITE_ROW) 
739                 ret = !!sqlite3_column_int(stmt, 0);
740         else
741                 ret = 0;
742
743 out:
744         sqlite3_reset(stmt);
745         sqlite3_finalize(stmt);
746         close_db(handle);
747         return ret;
748 }
749
750 EAPI int livebox_service_touch_effect(const char *pkgid)
751 {
752         sqlite3_stmt *stmt;
753         sqlite3 *handle;
754         int ret;
755
756         handle = open_db();
757         if (!handle)
758                 return 0;
759
760         ret = sqlite3_prepare_v2(handle, "SELECT touch_effect FROM client WHERE pkgid = ?", -1, &stmt, NULL);
761         if (ret != SQLITE_OK) {
762                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
763                 close_db(handle);
764                 return 0;
765         }
766
767         ret = sqlite3_bind_text(stmt, 1, pkgid, -1, NULL);
768         if (ret != SQLITE_OK) {
769                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
770                 ret = 0;
771                 goto out;
772         }
773
774         ret = sqlite3_step(stmt);
775         if (ret == SQLITE_ROW)
776                 ret = !!sqlite3_column_int(stmt, 0);
777         else
778                 ret = 1;
779
780 out:
781         sqlite3_reset(stmt);
782         sqlite3_finalize(stmt);
783         close_db(handle);
784         return ret;
785 }
786
787 EAPI int livebox_service_mouse_event(const char *pkgid)
788 {
789         sqlite3_stmt *stmt;
790         sqlite3 *handle;
791         int ret;
792
793         handle = open_db();
794         if (!handle)
795                 return 0;
796
797         ret = sqlite3_prepare_v2(handle, "SELECT mouse_event FROM client WHERE pkgid = ?", -1, &stmt, NULL);
798         if (ret != SQLITE_OK) {
799                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
800                 close_db(handle);
801                 return 0;
802         }
803
804         ret = sqlite3_bind_text(stmt, 1, pkgid, -1, NULL);
805         if (ret != SQLITE_OK) {
806                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
807                 ret = 0;
808                 goto out;
809         }
810
811         ret = sqlite3_step(stmt);
812         if (ret == SQLITE_ROW)
813                 ret = !!sqlite3_column_int(stmt, 0);
814         else
815                 ret = 0;
816
817 out:
818         sqlite3_reset(stmt);
819         sqlite3_finalize(stmt);
820         close_db(handle);
821         return ret;
822 }
823
824 EAPI char *livebox_service_preview(const char *pkgid, int size_type)
825 {
826         sqlite3_stmt *stmt;
827         sqlite3 *handle;
828         int ret;
829         char *preview = NULL;
830
831         handle = open_db();
832         if (!handle)
833                 return NULL;
834
835         ret = sqlite3_prepare_v2(handle, "SELECT preview FROM box_size WHERE pkgid = ? AND size_type = ?", -1, &stmt, NULL);
836         if (ret != SQLITE_OK) {
837                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
838                 close_db(handle);
839                 return NULL;
840         }
841
842         ret = sqlite3_bind_text(stmt, 1, pkgid, -1, NULL);
843         if (ret != SQLITE_OK) {
844                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
845                 goto out;
846         }
847
848         ret = sqlite3_bind_int(stmt, 2, size_type);
849         if (ret != SQLITE_OK) {
850                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
851                 goto out;
852         }
853
854         ret = sqlite3_step(stmt);
855         if (ret == SQLITE_ROW) {
856                 const char *tmp;
857                 tmp = (const char *)sqlite3_column_text(stmt, 0);
858                 if (tmp && strlen(tmp)) {
859                         preview = strdup(tmp);
860                         if (!preview)
861                                 ErrPrint("Heap: %s\n", strerror(errno));
862                 }
863         }
864
865 out:
866         sqlite3_reset(stmt);
867         sqlite3_finalize(stmt);
868         close_db(handle);
869         return preview;
870 }
871
872 EAPI char *livebox_service_i18n_icon(const char *pkgid, const char *lang)
873 {
874         sqlite3_stmt *stmt;
875         sqlite3 *handle;
876         char *language;
877         char *icon = NULL;
878         int ret;
879
880         if (lang) {
881                 language = strdup(lang);
882                 if (!language) {
883                         ErrPrint("Heap: %s\n", strerror(errno));
884                         return NULL;
885                 }
886         } else {
887                 language = cur_locale();
888                 if (!language)
889                         return NULL;
890         }
891
892         handle = open_db();
893         if (!handle) {
894                 free(language);
895                 return NULL;
896         }
897
898         ret = sqlite3_prepare_v2(handle, "SELECT icon FROM i18n WHERE pkgid = ? AND lang = ?", -1, &stmt, NULL);
899         if (ret != SQLITE_OK) {
900                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
901                 close_db(handle);
902                 free(language);
903                 return NULL;
904         }
905
906         ret = sqlite3_bind_text(stmt, 1, pkgid, -1, NULL);
907         if (ret != SQLITE_OK) {
908                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
909                 goto out;
910         }
911
912         ret = sqlite3_bind_text(stmt, 2, language, -1, NULL);
913         if (ret != SQLITE_OK) {
914                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
915                 goto out;
916         }
917
918         ret = sqlite3_step(stmt);
919         if (ret == SQLITE_ROW) {
920                 const char *tmp;
921                 tmp = (const char *)sqlite3_column_text(stmt, 0);
922                 if (!tmp || !strlen(tmp)) {
923                         icon = get_default_icon(pkgid);
924                 } else {
925                         icon = strdup(tmp);
926                         if (!icon)
927                                 ErrPrint("Heap: %s\n", strerror(errno));
928                 }
929         } else {
930                 icon = get_default_icon(pkgid);
931         }
932
933 out:
934         sqlite3_reset(stmt);
935         sqlite3_finalize(stmt);
936         close_db(handle);
937         free(language);
938         return icon;
939 }
940
941 EAPI char *livebox_service_i18n_name(const char *pkgid, const char *lang)
942 {
943         sqlite3_stmt *stmt;
944         sqlite3 *handle;
945         char *language;
946         char *name = NULL;
947         int ret;
948
949         if (lang) {
950                 language = strdup(lang);
951                 if (!language) {
952                         ErrPrint("Error: %s\n", strerror(errno));
953                         return NULL;
954                 }
955         } else {
956                 language = cur_locale();
957                 if (!language)
958                         return NULL;
959         }
960
961         handle = open_db();
962         if (!handle) {
963                 free(language);
964                 return NULL;
965         }
966
967         ret = sqlite3_prepare_v2(handle, "SELECT name FROM i18n WHERE pkgid = ? AND lang = ?", -1, &stmt, NULL);
968         if (ret != SQLITE_OK) {
969                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
970                 close_db(handle);
971                 free(language);
972                 return NULL;
973         }
974
975         ret = sqlite3_bind_text(stmt, 1, pkgid, -1, NULL);
976         if (ret != SQLITE_OK) {
977                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
978                 goto out;
979         }
980
981         ret = sqlite3_bind_text(stmt, 2, language, -1, NULL);
982         if (ret != SQLITE_OK) {
983                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
984                 goto out;
985         }
986
987         ret = sqlite3_step(stmt);
988         if (ret == SQLITE_ROW) {
989                 const char *tmp;
990                 tmp = (const char *)sqlite3_column_text(stmt, 0);
991                 if (!tmp || !strlen(tmp)) {
992                         name = get_default_name(pkgid);
993                 } else {
994                         name = strdup(tmp);
995                         if (!name)
996                                 ErrPrint("Heap: %s\n", strerror(errno));
997                 }
998         } else {
999                 name = get_default_name(pkgid);
1000         }
1001
1002 out:
1003         sqlite3_reset(stmt);
1004         sqlite3_finalize(stmt);
1005         close_db(handle);
1006         free(language);
1007         return name;
1008 }
1009
1010 EAPI int livebox_service_get_supported_sizes(const char *pkgid, int *cnt, int *w, int *h)
1011 {
1012         sqlite3_stmt *stmt;
1013         sqlite3 *handle;
1014         int size;
1015         int ret;
1016
1017         if (!w || !h || !cnt || !pkgid)
1018                 return -EINVAL;
1019
1020         handle = open_db();
1021         if (!handle)
1022                 return -EIO;
1023
1024         ret = sqlite3_prepare_v2(handle, "SELECT size_type FROM box_size WHERE pkgid = ? ORDER BY size_type ASC", -1, &stmt, NULL);
1025         if (ret != SQLITE_OK) {
1026                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
1027                 ret = -EIO;
1028                 goto out;
1029         }
1030
1031         ret = sqlite3_bind_text(stmt, 1, pkgid, -1, NULL);
1032         if (ret != SQLITE_OK) {
1033                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
1034                 sqlite3_reset(stmt);
1035                 sqlite3_finalize(stmt);
1036                 ret = -EIO;
1037                 goto out;
1038         }
1039
1040         if (*cnt > NR_OF_SIZE_LIST)
1041                 *cnt = NR_OF_SIZE_LIST;
1042
1043         ret = 0;
1044         while (sqlite3_step(stmt) == SQLITE_ROW && ret < *cnt) {
1045                 size = sqlite3_column_int(stmt, 0);
1046                 ret += (convert_size_from_type(size, w + ret, h + ret) == 0);
1047         }
1048
1049         *cnt = ret;
1050         sqlite3_reset(stmt);
1051         sqlite3_finalize(stmt);
1052         ret = 0;
1053 out:
1054         close_db(handle);
1055         return ret;
1056 }
1057
1058 EAPI char *livebox_service_libexec(const char *pkgid)
1059 {
1060         sqlite3_stmt *stmt;
1061         sqlite3 *handle;
1062         int ret;
1063         char *libexec;
1064         char *appid;
1065         char *path;
1066
1067         if (!pkgid)
1068                 return NULL;
1069
1070         libexec = NULL;
1071         handle = open_db();
1072         if (!handle)
1073                 return NULL;
1074
1075         ret = sqlite3_prepare_v2(handle, "SELECT pkgmap.appid, provider.libexec FROM pkgmap, provider WHERE pkgmap.pkgid = ? AND provider.pkgid = ?", -1, &stmt, NULL);
1076         if (ret != SQLITE_OK) {
1077                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
1078                 goto out;
1079         }
1080
1081         ret = sqlite3_bind_text(stmt, 1, pkgid, -1, NULL);
1082         if (ret != SQLITE_OK) {
1083                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
1084                 sqlite3_finalize(stmt);
1085                 goto out;
1086         }
1087
1088         ret = sqlite3_bind_text(stmt, 2, pkgid, -1, NULL);
1089         if (ret != SQLITE_OK) {
1090                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
1091                 sqlite3_finalize(stmt);
1092                 goto out;
1093         }
1094
1095         if (sqlite3_step(stmt) != SQLITE_ROW) {
1096                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
1097                 sqlite3_reset(stmt);
1098                 sqlite3_finalize(stmt);
1099
1100                 libexec = util_conf_get_libexec(pkgid);
1101                 DbgPrint("Fallback to conf checker: %s\n", libexec);
1102                 goto out;
1103         }
1104
1105         appid = (char *)sqlite3_column_text(stmt, 0);
1106         if (!appid || !strlen(appid)) {
1107                 ErrPrint("Invalid appid: %s\n", sqlite3_errmsg(handle));
1108                 sqlite3_reset(stmt);
1109                 sqlite3_finalize(stmt);
1110                 goto out;
1111         }
1112
1113         path = (char *)sqlite3_column_text(stmt, 1);
1114         if (!path || !strlen(path)) {
1115                 ErrPrint("Invalid libexec: %s\n", sqlite3_errmsg(handle));
1116                 sqlite3_reset(stmt);
1117                 sqlite3_finalize(stmt);
1118                 goto out;
1119         }
1120
1121         libexec = strdup(path);
1122         if (!libexec) {
1123                 ErrPrint("Heap: %s\n", strerror(errno));
1124                 sqlite3_reset(stmt);
1125                 sqlite3_finalize(stmt);
1126                 goto out;
1127         }
1128
1129         DbgPrint("libexec: %s\n", libexec);
1130
1131         sqlite3_reset(stmt);
1132         sqlite3_finalize(stmt);
1133 out:
1134         close_db(handle);
1135         return libexec;
1136 }
1137
1138 static inline char *get_lb_pkgname_by_appid(const char *appid)
1139 {
1140         sqlite3_stmt *stmt;
1141         char *pkgid;
1142         char *tmp;
1143         sqlite3 *handle;
1144         int ret;
1145
1146         if (!appid)
1147                 return NULL;
1148
1149         pkgid = NULL;
1150         handle = open_db();
1151         if (!handle)
1152                 return NULL;
1153
1154         ret = sqlite3_prepare_v2(handle, "SELECT pkgid FROM pkgmap WHERE (appid = ? AND prime = 1) OR pkgid = ?", -1, &stmt, NULL);
1155         if (ret != SQLITE_OK) {
1156                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
1157                 close_db(handle);
1158                 return NULL;
1159         }
1160
1161         ret = sqlite3_bind_text(stmt, 1, appid, -1, NULL);
1162         if (ret != SQLITE_OK) {
1163                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
1164                 goto out;
1165         }
1166
1167         ret = sqlite3_bind_text(stmt, 2, appid, -1, NULL);
1168         if (ret != SQLITE_OK) {
1169                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
1170                 goto out;
1171         }
1172
1173         if (sqlite3_step(stmt) != SQLITE_ROW) {
1174                 ErrPrint("Error: %s (has no record? - %s)\n", sqlite3_errmsg(handle), appid);
1175                 goto out;
1176         }
1177
1178         tmp = (char *)sqlite3_column_text(stmt, 0);
1179         if (tmp && strlen(tmp)) {
1180                 pkgid = strdup(tmp);
1181                 if (!pkgid)
1182                         ErrPrint("Heap: %s\n", strerror(errno));
1183         }
1184
1185 out:
1186         sqlite3_reset(stmt);
1187         sqlite3_finalize(stmt);
1188         close_db(handle);
1189         return pkgid;
1190 }
1191
1192 EAPI char *livebox_service_pkgname(const char *appid)
1193 {
1194         char *lb_pkgname;
1195         pkgmgr_appinfo_h handle;
1196         int ret;
1197         char *new_appid;
1198
1199         if (!appid)
1200                 return NULL;
1201
1202         lb_pkgname = get_lb_pkgname_by_appid(appid);
1203         if (lb_pkgname)
1204                 return lb_pkgname;
1205
1206         /*!
1207          * \note
1208          * Try to get the package id using given appid
1209          */
1210         ret = pkgmgr_appinfo_get_appinfo(appid, &handle);
1211         if (ret != PKGMGR_R_OK) {
1212                 ErrPrint("Failed to get appinfo\n");
1213                 return NULL;
1214         }
1215
1216         ret = pkgmgr_appinfo_get_pkgname(handle, &new_appid);
1217         if (ret != PKGMGR_R_OK) {
1218                 pkgmgr_appinfo_destroy_appinfo(handle);
1219                 ErrPrint("Failed to get pkgname for (%s)\n", appid);
1220                 return NULL;
1221         }
1222
1223         lb_pkgname = get_lb_pkgname_by_appid(new_appid);
1224         pkgmgr_appinfo_destroy_appinfo(handle);
1225
1226         if (!lb_pkgname && util_validate_livebox_package(appid) == 0)
1227                 return strdup(appid);
1228
1229         return lb_pkgname;
1230 }
1231
1232 EAPI char *livebox_service_provider_name(const char *lbid)
1233 {
1234         char *ret;
1235         int stage = 0;
1236         int seq = 0;
1237         int idx = 0;
1238         char *str = "com.samsung.";
1239
1240         if (!lbid)
1241                 return NULL;
1242
1243         while (str[idx] && lbid[idx] && lbid[idx] == str[idx]) {
1244                 idx++;
1245                 if (seq < 2 && lbid[idx] == '.') {
1246                         stage = idx;
1247                         seq++;
1248                 }
1249         }
1250
1251         if (!str[idx] && lbid[idx]) {
1252                 /* Inhouse */
1253                 return strdup(lbid);
1254         } else if (seq < 2) {
1255                 while (seq < 2) {
1256                         if (lbid[idx] == '.') {
1257                                 seq++;
1258                         } else if (!lbid[idx]) {
1259                                 ErrPrint("Invalid lbid: %s\n", lbid);
1260                                 return NULL;
1261                         }
1262
1263                         idx++;
1264                 }
1265
1266                 stage = idx;
1267         } else {
1268                 stage++;
1269         }
1270
1271         ret = strdup(lbid + stage);
1272         if (!ret) {
1273                 ErrPrint("Error: %s\n", strerror(errno));
1274                 return NULL;
1275         }
1276
1277         return ret;
1278 }
1279
1280 EAPI int livebox_service_is_enabled(const char *lbid)
1281 {
1282         ail_appinfo_h ai;
1283         char *pkgname;
1284         bool enabled;
1285         int ret;
1286
1287         pkgname = livebox_service_appid(lbid);
1288         if (!pkgname)
1289                 return 0;
1290
1291         ret = ail_get_appinfo(pkgname, &ai);
1292         if (ret != AIL_ERROR_OK) {
1293                 free(pkgname);
1294                 return 0;
1295         }
1296
1297         if (ail_appinfo_get_bool(ai, AIL_PROP_X_SLP_ENABLED_BOOL, &enabled) != AIL_ERROR_OK)
1298                 enabled = false;
1299
1300         ail_destroy_appinfo(ai);
1301         free(pkgname);
1302         return enabled == true;
1303 }
1304
1305 /*!
1306  * appid == Package ID
1307  * pkgid == Livebox ID
1308  */
1309 EAPI char *livebox_service_appid(const char *pkgname)
1310 {
1311         sqlite3_stmt *stmt;
1312         char *appid;
1313         char *tmp;
1314         sqlite3 *handle;
1315         int is_prime __attribute__((__unused__));
1316         int ret;
1317
1318         if (!pkgname)
1319                 return NULL;
1320
1321         appid = NULL;
1322         handle = open_db();
1323         if (!handle)
1324                 return NULL;
1325
1326         ret = sqlite3_prepare_v2(handle, "SELECT appid, prime FROM pkgmap WHERE pkgid = ? OR appid = ?", -1, &stmt, NULL);
1327         if (ret != SQLITE_OK) {
1328                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
1329                 goto out;
1330         }
1331
1332         ret = sqlite3_bind_text(stmt, 1, pkgname, -1, NULL);
1333         if (ret != SQLITE_OK) {
1334                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
1335                 sqlite3_reset(stmt);
1336                 sqlite3_finalize(stmt);
1337                 goto out;
1338         }
1339
1340         ret = sqlite3_bind_text(stmt, 2, pkgname, -1, NULL);
1341         if (ret != SQLITE_OK) {
1342                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
1343                 sqlite3_reset(stmt);
1344                 sqlite3_finalize(stmt);
1345                 goto out;
1346         }
1347
1348         ret = sqlite3_step(stmt);
1349         if (ret != SQLITE_ROW) {
1350                 pkgmgr_appinfo_h pkg_handle;
1351                 char *new_appid;
1352
1353                 ErrPrint("Has no record?: %s\n", sqlite3_errmsg(handle));
1354                 sqlite3_reset(stmt);
1355                 sqlite3_finalize(stmt);
1356
1357                 ret = pkgmgr_appinfo_get_appinfo(pkgname, &pkg_handle);
1358                 if (ret != PKGMGR_R_OK) {
1359                         ErrPrint("Failed to get appinfo: %s\n", pkgname);
1360                         goto out;
1361                 }
1362
1363                 ret = pkgmgr_appinfo_get_pkgname(pkg_handle, &new_appid);
1364                 if (ret != PKGMGR_R_OK) {
1365                         ErrPrint("Failed to get pkgname for (%s)\n", appid);
1366                         pkgmgr_appinfo_destroy_appinfo(pkg_handle);
1367                         goto out;
1368                 }
1369
1370                 appid = strdup(new_appid);
1371                 if (!appid)
1372                         ErrPrint("Heap: %s\n", strerror(errno));
1373
1374                 pkgmgr_appinfo_destroy_appinfo(pkg_handle);
1375                 goto out;
1376         }
1377
1378         tmp = (char *)sqlite3_column_text(stmt, 0);
1379         if (!tmp || !strlen(tmp)) {
1380                 ErrPrint("APPID is NIL\n");
1381                 sqlite3_reset(stmt);
1382                 sqlite3_finalize(stmt);
1383                 goto out;
1384         }
1385
1386         appid = strdup(tmp);
1387         if (!appid) {
1388                 ErrPrint("Heap: %s\n", strerror(errno));
1389                 sqlite3_reset(stmt);
1390                 sqlite3_finalize(stmt);
1391                 goto out;
1392         }
1393
1394         is_prime = sqlite3_column_int(stmt, 1);
1395
1396         sqlite3_reset(stmt);
1397         sqlite3_finalize(stmt);
1398 out:
1399         close_db(handle);
1400         return appid;
1401 }
1402
1403 EAPI char *livebox_service_lb_script_path(const char *pkgid)
1404 {
1405         sqlite3_stmt *stmt;
1406         sqlite3 *handle;
1407         int ret;
1408         char *path;
1409         char *appid;
1410         char *lb_src;
1411
1412         if (!pkgid)
1413                 return NULL;
1414
1415         path = NULL;
1416         handle = open_db();
1417         if (!handle)
1418                 return NULL;
1419
1420         ret = sqlite3_prepare_v2(handle, "SELECT pkgmap.appid, provider.box_src FROM provider, pkgmap WHERE pkgmap.pkgid = ? AND provider.pkgid = ?", -1, &stmt, NULL);
1421         if (ret != SQLITE_OK) {
1422                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
1423                 goto out;
1424         }
1425
1426         ret = sqlite3_bind_text(stmt, 1, pkgid, -1, NULL);
1427         if (ret != SQLITE_OK) {
1428                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
1429                 sqlite3_finalize(stmt);
1430                 goto out;
1431         }
1432
1433         ret = sqlite3_bind_text(stmt, 2, pkgid, -1, NULL);
1434         if (ret != SQLITE_OK) {
1435                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
1436                 sqlite3_finalize(stmt);
1437                 goto out;
1438         }
1439
1440         ret = sqlite3_step(stmt);
1441         if (ret != SQLITE_ROW) {
1442                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
1443                 sqlite3_reset(stmt);
1444                 sqlite3_finalize(stmt);
1445                 goto out;
1446         }
1447
1448         appid = (char *)sqlite3_column_text(stmt, 0);
1449         if (!appid || !strlen(appid)) {
1450                 ErrPrint("Invalid appid : %s\n", sqlite3_errmsg(handle));
1451                 sqlite3_reset(stmt);
1452                 sqlite3_finalize(stmt);
1453                 goto out;
1454         }
1455
1456         lb_src = (char *)sqlite3_column_text(stmt, 1);
1457         if (!lb_src || !strlen(lb_src)) {
1458                 ErrPrint("No records for lb src : %s\n", sqlite3_errmsg(handle));
1459                 sqlite3_reset(stmt);
1460                 sqlite3_finalize(stmt);
1461                 goto out;
1462         }
1463
1464         path = strdup(lb_src);
1465         if (!path) {
1466                 ErrPrint("Heap: %s\n", strerror(errno));
1467                 sqlite3_reset(stmt);
1468                 sqlite3_finalize(stmt);
1469                 goto out;
1470         }
1471
1472         DbgPrint("LB Src: %s\n", path);
1473
1474         sqlite3_reset(stmt);
1475         sqlite3_finalize(stmt);
1476 out:
1477         close_db(handle);
1478         return path;
1479 }
1480
1481 EAPI char *livebox_service_lb_script_group(const char *pkgid)
1482 {
1483         sqlite3_stmt *stmt;
1484         sqlite3 *handle;
1485         int ret;
1486         char *group;
1487         char *tmp;
1488
1489         if (!pkgid)
1490                 return NULL;
1491
1492         group = NULL;
1493         handle = open_db();
1494         if (!handle)
1495                 return NULL;
1496
1497         ret = sqlite3_prepare_v2(handle, "SELECT box_group FROM provider WHERE pkgid = ?", -1, &stmt, NULL);
1498         if (ret != SQLITE_OK) {
1499                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
1500                 goto out;
1501         }
1502
1503         ret = sqlite3_bind_text(stmt, 1, pkgid, -1, NULL);
1504         if (ret != SQLITE_OK) {
1505                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
1506                 sqlite3_finalize(stmt);
1507                 goto out;
1508         }
1509
1510         ret = sqlite3_step(stmt);
1511         if (ret != SQLITE_ROW) {
1512                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
1513                 sqlite3_reset(stmt);
1514                 sqlite3_finalize(stmt);
1515                 goto out;
1516         }
1517
1518         tmp = (char *)sqlite3_column_text(stmt, 0);
1519         if (tmp && strlen(tmp)) {
1520                 group = strdup(tmp);
1521                 if (!group)
1522                         ErrPrint("Heap: %s\n", strerror(errno));
1523         }
1524
1525         sqlite3_reset(stmt);
1526         sqlite3_finalize(stmt);
1527 out:
1528         close_db(handle);
1529         return group;
1530 }
1531
1532 EAPI char *livebox_service_pd_script_path(const char *pkgid)
1533 {
1534         sqlite3_stmt *stmt;
1535         sqlite3 *handle;
1536         int ret;
1537         char *path;
1538         char *pd_src;
1539         const char *appid;
1540
1541         if (!pkgid)
1542                 return NULL;
1543
1544         path = NULL;
1545         handle = open_db();
1546         if (!handle)
1547                 return NULL;
1548
1549         ret = sqlite3_prepare_v2(handle, "SELECT pkgmap.appid, provider.pd_src FROM provider, pkgmap WHERE provider.pkgid = ? AND pkgmap.pkgid = ?", -1, &stmt, NULL);
1550         if (ret != SQLITE_OK) {
1551                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
1552                 goto out;
1553         }
1554
1555         ret = sqlite3_bind_text(stmt, 1, pkgid, -1, NULL);
1556         if (ret != SQLITE_OK) {
1557                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
1558                 sqlite3_finalize(stmt);
1559                 goto out;
1560         }
1561
1562         ret = sqlite3_bind_text(stmt, 2, pkgid, -1, NULL);
1563         if (ret != SQLITE_OK) {
1564                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
1565                 sqlite3_finalize(stmt);
1566                 goto out;
1567         }
1568
1569         ret = sqlite3_step(stmt);
1570         if (ret != SQLITE_ROW) {
1571                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
1572                 sqlite3_reset(stmt);
1573                 sqlite3_finalize(stmt);
1574                 goto out;
1575         }
1576
1577         appid = (char *)sqlite3_column_text(stmt, 0);
1578         if (!appid || !strlen(appid)) {
1579                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
1580                 sqlite3_reset(stmt);
1581                 sqlite3_finalize(stmt);
1582                 goto out;
1583         }
1584
1585         pd_src = (char *)sqlite3_column_text(stmt, 1);
1586         if (!pd_src || !strlen(pd_src)) {
1587                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
1588                 sqlite3_reset(stmt);
1589                 sqlite3_finalize(stmt);
1590                 goto out;
1591         }
1592
1593         path = strdup(pd_src);
1594         if (!path) {
1595                 ErrPrint("Heap: %s\n", strerror(errno));
1596                 sqlite3_reset(stmt);
1597                 sqlite3_finalize(stmt);
1598                 goto out;
1599         }
1600
1601         DbgPrint("PD Src: %s\n", path);
1602         sqlite3_reset(stmt);
1603         sqlite3_finalize(stmt);
1604 out:
1605         close_db(handle);
1606         return path;
1607 }
1608
1609 EAPI char *livebox_service_pd_script_group(const char *pkgid)
1610 {
1611         sqlite3_stmt *stmt;
1612         sqlite3 *handle;
1613         int ret;
1614         char *group;
1615         char *tmp;
1616
1617         if (!pkgid)
1618                 return NULL;
1619
1620         group = NULL;
1621         handle = open_db();
1622         if (!handle)
1623                 return NULL;
1624
1625         ret = sqlite3_prepare_v2(handle, "SELECT pd_group FROM provider WHERE pkgid = ?", -1, &stmt, NULL);
1626         if (ret != SQLITE_OK) {
1627                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
1628                 goto out;
1629         }
1630
1631         ret = sqlite3_bind_text(stmt, 1, pkgid, -1, NULL);
1632         if (ret != SQLITE_OK) {
1633                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
1634                 sqlite3_finalize(stmt);
1635                 goto out;
1636         }
1637
1638         ret = sqlite3_step(stmt);
1639         if (ret != SQLITE_ROW) {
1640                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
1641                 sqlite3_reset(stmt);
1642                 sqlite3_finalize(stmt);
1643                 goto out;
1644         }
1645
1646         tmp = (char *)sqlite3_column_text(stmt, 0);
1647         if (tmp && strlen(tmp)) {
1648                 group = strdup(tmp);
1649                 if (!group)
1650                         ErrPrint("Heap: %s\n", strerror(errno));
1651         }
1652         sqlite3_reset(stmt);
1653         sqlite3_finalize(stmt);
1654 out:
1655         close_db(handle);
1656         return group;
1657 }
1658
1659 EAPI int livebox_service_enumerate_cluster_list(int (*cb)(const char *cluster, void *data), void *data)
1660 {
1661         sqlite3_stmt *stmt;
1662         sqlite3 *handle;
1663         const char *cluster;
1664         int cnt;
1665         int ret;
1666
1667         if (!cb)
1668                 return -EINVAL;
1669
1670         handle = open_db();
1671         if (!handle)
1672                 return -EIO;
1673
1674         cnt = 0;
1675         ret = sqlite3_prepare_v2(handle, "SELECT DISTINCT cluster FROM groupinfo", -1, &stmt, NULL);
1676         if (ret != SQLITE_OK) {
1677                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
1678                 cnt = -EIO;
1679                 goto out;
1680         }
1681
1682         while (sqlite3_step(stmt) == SQLITE_ROW) {
1683                 cluster = (const char *)sqlite3_column_text(stmt, 0);
1684                 if (!cluster || !strlen(cluster))
1685                         continue;
1686
1687                 if (cb(cluster, data) < 0)
1688                         break;
1689
1690                 cnt++;
1691         }
1692
1693         sqlite3_reset(stmt);
1694         sqlite3_finalize(stmt);
1695 out:
1696         close_db(handle);
1697         return cnt;
1698 }
1699
1700 EAPI int livebox_service_enumerate_category_list(const char *cluster, int (*cb)(const char *cluster, const char *category, void *data), void *data)
1701 {
1702         sqlite3_stmt *stmt;
1703         sqlite3 *handle;
1704         const char *category;
1705         int cnt;
1706         int ret;
1707
1708         if (!cluster || !cb)
1709                 return -EINVAL;
1710
1711         handle = open_db();
1712         if (!handle)
1713                 return -EIO;
1714
1715         ret = sqlite3_prepare_v2(handle, "SELECT DISTINCT category FROM groupinfo WHERE cluster = ?", -1, &stmt, NULL);
1716         if (ret != SQLITE_OK) {
1717                 ErrPrint("Error: %s\n", sqlite3_errmsg(handle));
1718                 cnt = -EIO;
1719                 goto out;
1720         }
1721
1722         cnt = 0;
1723         while (sqlite3_step(stmt) == SQLITE_ROW) {
1724                 category = (const char *)sqlite3_column_text(stmt, 0);
1725                 if (!category || !strlen(category))
1726                         continue;
1727
1728                 if (cb(cluster, category, data) < 0)
1729                         break;
1730
1731                 cnt++;
1732         }
1733
1734         sqlite3_reset(stmt);
1735         sqlite3_finalize(stmt);
1736 out:
1737         close_db(handle);
1738         return cnt;
1739 }
1740
1741 EAPI int livebox_service_init(void)
1742 {
1743         if (s_info.handle) {
1744                 DbgPrint("Already initialized\n");
1745                 s_info.init_count++;
1746                 return 0;
1747         }
1748
1749         s_info.handle = open_db();
1750         if (s_info.handle) {
1751                 s_info.init_count++;
1752                 return 0;
1753         }
1754
1755         return -EIO;
1756 }
1757
1758 EAPI int livebox_service_fini(void)
1759 {
1760         if (!s_info.handle || s_info.init_count <= 0) {
1761                 ErrPrint("Service is not initialized\n");
1762                 return -EIO;
1763         }
1764
1765         s_info.init_count--;
1766         if (s_info.init_count > 0) {
1767                 DbgPrint("Init count %d\n", s_info.init_count);
1768                 return 0;
1769         }
1770
1771         db_util_close(s_info.handle);
1772         s_info.handle = NULL;
1773         return 0;
1774 }
1775
1776 EAPI int livebox_service_get_size(int type, int *width, int *height)
1777 {
1778         int _width;
1779         int _height;
1780
1781         if (!width)
1782                 width = &_width;
1783
1784         if (!height)
1785                 height = &_height;
1786
1787         return convert_size_from_type(type, width, height);
1788 }
1789
1790 EAPI int livebox_service_size_type(int width, int height)
1791 {
1792         int idx;
1793
1794         if (update_resolution() < 0)
1795                 ErrPrint("Failed to update the size list\n");
1796
1797         for (idx = 0; idx < NR_OF_SIZE_LIST; idx++) {
1798                 if (SIZE_LIST[idx].w == width && SIZE_LIST[idx].h == height)
1799                         break;
1800         }
1801
1802         switch (idx) {
1803         case 0:
1804                 return LB_SIZE_TYPE_1x1;
1805         case 1:
1806                 return LB_SIZE_TYPE_2x1;
1807         case 2:
1808                 return LB_SIZE_TYPE_2x2;
1809         case 3:
1810                 return LB_SIZE_TYPE_4x1;
1811         case 4:
1812                 return LB_SIZE_TYPE_4x2;
1813         case 5:
1814                 return LB_SIZE_TYPE_4x3;
1815         case 6:
1816                 return LB_SIZE_TYPE_4x4;
1817         case 7:
1818                 return LB_SIZE_TYPE_EASY_1x1;
1819         case 8:
1820                 return LB_SIZE_TYPE_EASY_3x1;
1821         case 9:
1822                 return LB_SIZE_TYPE_EASY_3x3;
1823         default:
1824                 break;
1825         }
1826
1827         return LB_SIZE_TYPE_UNKNOWN;
1828 }
1829
1830 /* End of a file */