Remove content file only if destroying the common handler
[platform/framework/web/livebox-viewer.git] / src / livebox.c
1 /*
2  * Copyright 2013  Samsung Electronics Co., Ltd
3  *
4  * Licensed under the Flora License, Version 1.1 (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://floralicense.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 */
21 #include <math.h>
22 #include <unistd.h>
23 #include <fcntl.h>
24 #include <sys/stat.h>
25 #include <sys/types.h>
26
27 #include <gio/gio.h>
28 #include <aul.h>
29 #include <dlog.h>
30
31 #include <com-core_packet.h>
32 #include <packet.h>
33 #include <livebox-service.h>
34 #include <livebox-errno.h>
35
36 #include "debug.h"
37 #include "fb.h"
38 #include "livebox.h"
39 #include "livebox_internal.h"
40 #include "dlist.h"
41 #include "util.h"
42 #include "master_rpc.h"
43 #include "client.h"
44 #include "conf.h"
45
46 #define EAPI __attribute__((visibility("default")))
47
48 #if defined(FLOG)
49 FILE *__file_log_fp;
50 #endif
51
52 enum event_state {
53         INFO_STATE_CALLBACK_IN_IDLE = 0x00,
54         INFO_STATE_CALLBACK_IN_PROCESSING = 0x01,
55 };
56
57 static struct info {
58         struct dlist *livebox_list;
59         struct dlist *livebox_common_list;
60
61         struct dlist *event_list;
62         struct dlist *fault_list;
63
64         int init_count;
65         int prevent_overwrite;
66         enum event_state event_state;
67         enum event_state fault_state;
68         guint job_timer;
69         struct dlist *job_list;
70 } s_info = {
71         .livebox_list = NULL,
72         .event_list = NULL,
73         .fault_list = NULL,
74         .init_count = 0,
75         .prevent_overwrite = 0,
76         .event_state = INFO_STATE_CALLBACK_IN_IDLE,
77         .fault_state = INFO_STATE_CALLBACK_IN_IDLE,
78         .job_timer = 0,
79         .job_list = NULL,
80 };
81
82 struct cb_info {
83         ret_cb_t cb;
84         void *data;
85 };
86
87 struct event_info {
88         int is_deleted;
89         int (*handler)(struct livebox *handler, enum livebox_event_type event, void *data);
90         void *user_data;
91 };
92
93 struct fault_info {
94         int is_deleted;
95         int (*handler)(enum livebox_fault_type event, const char *pkgname, const char *filename, const char *func, void *data);
96         void *user_data;
97 };
98
99 static void lb_pixmap_acquired_cb(struct livebox *handler, const struct packet *result, void *data);
100 static void pd_pixmap_acquired_cb(struct livebox *handler, const struct packet *result, void *data);
101
102 static inline void default_create_cb(struct livebox *handler, int ret, void *data)
103 {
104         DbgPrint("Default created event handler: %d\n", ret);
105 }
106
107 static inline void default_delete_cb(struct livebox *handler, int ret, void *data)
108 {
109         DbgPrint("Default deleted event handler: %d\n", ret);
110 }
111
112 static inline void default_pinup_cb(struct livebox *handler, int ret, void *data)
113 {
114         DbgPrint("Default pinup event handler: %d\n", ret);
115 }
116
117 static inline void default_group_changed_cb(struct livebox *handler, int ret, void *data)
118 {
119         DbgPrint("Default group changed event handler: %d\n", ret);
120 }
121
122 static inline void default_period_changed_cb(struct livebox *handler, int ret, void *data)
123 {
124         DbgPrint("Default period changed event handler: %d\n", ret);
125 }
126
127 static inline void default_pd_created_cb(struct livebox *handler, int ret, void *data)
128 {
129         DbgPrint("Default PD created event handler: %d\n", ret);
130 }
131
132 static inline void default_pd_destroyed_cb(struct livebox *handler, int ret, void *data)
133 {
134         DbgPrint("Default PD destroyed event handler: %d\n", ret);
135 }
136
137 static inline void default_lb_size_changed_cb(struct livebox *handler, int ret, void *data)
138 {
139         DbgPrint("Default LB size changed event handler: %d\n", ret);
140 }
141
142 static inline void default_update_mode_cb(struct livebox *handler, int ret, void *data)
143 {
144         DbgPrint("Default update mode set event handler: %d\n", ret);
145 }
146
147 static inline void default_access_event_cb(struct livebox *handler, int ret, void *data)
148 {
149         DbgPrint("Default access event handler: %d\n", ret);
150 }
151
152 static inline void default_key_event_cb(struct livebox *handler, int ret, void *data)
153 {
154         DbgPrint("Default key event handler: %d\n", ret);
155 }
156
157 static inline __attribute__((always_inline)) struct cb_info *create_cb_info(ret_cb_t cb, void *data)
158 {
159         struct cb_info *info;
160
161         info = malloc(sizeof(*info));
162         if (!info) {
163                 ErrPrint("Heap: %s\n", strerror(errno));
164                 return NULL;
165         }
166
167         info->cb = cb;
168         info->data = data;
169         return info;
170 }
171
172 static inline void destroy_cb_info(struct cb_info *info)
173 {
174         free(info);
175 }
176
177 static int do_fb_lock(int fd)
178 {
179         struct flock flock;
180         int ret;
181
182         flock.l_type = F_RDLCK;
183         flock.l_whence = SEEK_SET;
184         flock.l_start = 0;
185         flock.l_len = 0;
186         flock.l_pid = getpid();
187
188         do {
189                 ret = fcntl(fd, F_SETLKW, &flock);
190                 if (ret < 0) {
191                         ret = errno;
192                         ErrPrint("fcntl: %s\n", strerror(errno));
193                 }
194         } while (ret == EINTR);
195
196         return ret;
197 }
198
199 static int do_fb_unlock(int fd)
200 {
201         struct flock flock;
202         int ret;
203
204         flock.l_type = F_UNLCK;
205         flock.l_whence = SEEK_SET;
206         flock.l_start = 0;
207         flock.l_len = 0;
208         flock.l_pid = getpid();
209
210         do {
211                 ret = fcntl(fd, F_SETLKW, &flock);
212                 if (ret < 0) {
213                         ret = errno;
214                         ErrPrint("fcntl: %s\n", strerror(errno));
215                 }
216         } while (ret == EINTR);
217
218         return ret;
219 }
220
221 int lb_destroy_lock_file(struct livebox_common *common, int is_pd)
222 {
223         if (is_pd) {
224                 if (!common->pd.lock) {
225                         return LB_STATUS_ERROR_INVALID;
226                 }
227
228                 if (close(common->pd.lock_fd) < 0) {
229                         ErrPrint("close: %s\n", strerror(errno));
230                 }
231                 common->pd.lock_fd = -1;
232
233                 if (unlink(common->pd.lock) < 0) {
234                         ErrPrint("unlink: %s\n", strerror(errno));
235                 }
236
237                 free(common->pd.lock);
238                 common->pd.lock = NULL;
239         } else {
240                 if (!common->lb.lock) {
241                         return LB_STATUS_ERROR_INVALID;
242                 }
243
244                 if (close(common->lb.lock_fd) < 0) {
245                         ErrPrint("close: %s\n", strerror(errno));
246                 }
247                 common->lb.lock_fd = -1;
248
249                 if (unlink(common->lb.lock) < 0) {
250                         ErrPrint("unlink: %s\n", strerror(errno));
251                 }
252
253                 free(common->lb.lock);
254                 common->lb.lock = NULL;
255         }
256
257         return LB_STATUS_SUCCESS;
258 }
259
260 int lb_create_lock_file(struct livebox_common *common, int is_pd)
261 {
262         int len;
263         char *file;
264
265         len = strlen(common->id);
266         file = malloc(len + 20);
267         if (!file) {
268                 ErrPrint("Heap: %s\n", strerror(errno));
269                 return LB_STATUS_ERROR_MEMORY;
270         }
271
272         snprintf(file, len + 20, "%s.%s.lck", util_uri_to_path(common->id), is_pd ? "pd" : "lb");
273
274         if (is_pd) {
275                 common->pd.lock_fd = open(file, O_RDONLY);
276                 if (common->pd.lock_fd < 0) {
277                         ErrPrint("open: %s\n", strerror(errno));
278                         free(file);
279                         return LB_STATUS_ERROR_IO;
280                 }
281
282                 common->pd.lock = file;
283         } else {
284                 common->lb.lock_fd = open(file, O_RDONLY);
285                 if (common->lb.lock_fd < 0) {
286                         ErrPrint("open: %s\n", strerror(errno));
287                         free(file);
288                         return LB_STATUS_ERROR_IO;
289                 }
290
291                 common->lb.lock = file;
292         }
293
294         return LB_STATUS_SUCCESS;
295 }
296
297 static void update_mode_cb(struct livebox *handler, const struct packet *result, void *data)
298 {
299         int ret;
300
301         if (!result) {
302                 ret = LB_STATUS_ERROR_FAULT;
303                 goto errout;
304         } else if (packet_get(result, "i", &ret) != 1) {
305                 ErrPrint("Invalid argument\n");
306                 ret = LB_STATUS_ERROR_INVALID;
307                 goto errout;
308         }
309
310         if (ret < 0) {
311                 ErrPrint("Resize request is failed: %d\n", ret);
312                 goto errout;
313         }
314
315         return;
316
317 errout:
318         handler->cbs.update_mode.cb(handler, ret, handler->cbs.update_mode.data);
319         handler->cbs.update_mode.cb = NULL;
320         handler->cbs.update_mode.data = NULL;
321         handler->common->request.update_mode = 0;
322
323         if (ret == LB_STATUS_ERROR_NOT_EXIST && handler->refcnt == 2) {
324                 lb_invoke_event_handler(handler, LB_EVENT_DELETED);
325                 lb_unref(handler, 1);
326         }
327 }
328
329 static void resize_cb(struct livebox *handler, const struct packet *result, void *data)
330 {
331         int ret;
332
333         if (!result) {
334                 ret = LB_STATUS_ERROR_FAULT;
335                 goto errout;
336         } else if (packet_get(result, "i", &ret) != 1) {
337                 ErrPrint("Invalid argument\n");
338                 ret = LB_STATUS_ERROR_INVALID;
339                 goto errout;
340         }
341
342         /*!
343          * \note
344          * In case of resize request,
345          * The livebox handler will not have resized value right after this callback,
346          * It can only get the new size when it makes updates.
347          *
348          * So the user can only get the resized value(result) from the first update event
349          * after this request.
350          */
351         if (ret < 0) {
352                 ErrPrint("Resize request is failed: %d\n", ret);
353                 goto errout;
354         }
355
356         return;
357
358 errout:
359         handler->cbs.size_changed.cb(handler, ret, handler->cbs.size_changed.data);
360         handler->cbs.size_changed.cb = NULL;
361         handler->cbs.size_changed.data = NULL;
362         handler->common->request.size_changed = 0;
363
364         if (ret == LB_STATUS_ERROR_NOT_EXIST && handler->refcnt == 2) {
365                 lb_invoke_event_handler(handler, LB_EVENT_DELETED);
366                 lb_unref(handler, 1);
367         }
368 }
369
370 static void text_signal_cb(struct livebox *handler, const struct packet *result, void *data)
371 {
372         int ret;
373         void *cbdata;
374         struct cb_info *info = data;
375         ret_cb_t cb;
376
377         cbdata = info->data;
378         cb = info->cb;
379         destroy_cb_info(info);
380
381         if (!result) {
382                 ret = LB_STATUS_ERROR_FAULT;
383         } else if (packet_get(result, "i", &ret) != 1) {
384                 ErrPrint("Invalid argument\n");
385                 ret = LB_STATUS_ERROR_INVALID;
386         }
387
388         if (cb) {
389                 cb(handler, ret, cbdata);
390         }
391         return;
392 }
393
394 static void set_group_ret_cb(struct livebox *handler, const struct packet *result, void *data)
395 {
396         int ret;
397
398         if (!result) {
399                 ret = LB_STATUS_ERROR_FAULT;
400                 goto errout;
401         } else if (packet_get(result, "i", &ret) != 1) {
402                 ErrPrint("Invalid argument\n");
403                 ret = LB_STATUS_ERROR_INVALID;
404                 goto errout;
405         }
406
407         if (ret < 0) {
408                 goto errout;
409         }
410
411         return;
412
413 errout:
414         handler->cbs.group_changed.cb(handler, ret, handler->cbs.group_changed.data);
415         handler->cbs.group_changed.cb = NULL;
416         handler->cbs.group_changed.data = NULL;
417         handler->common->request.group_changed = 0;
418
419         if (ret == LB_STATUS_ERROR_NOT_EXIST && handler->refcnt == 2) {
420                 lb_invoke_event_handler(handler, LB_EVENT_DELETED);
421                 lb_unref(handler, 1);
422         }
423 }
424
425 static void period_ret_cb(struct livebox *handler, const struct packet *result, void *data)
426 {
427         int ret;
428
429         if (!result) {
430                 ret = LB_STATUS_ERROR_FAULT;
431                 goto errout;
432         } else if (packet_get(result, "i", &ret) != 1) {
433                 ErrPrint("Invalid argument\n");
434                 ret = LB_STATUS_ERROR_INVALID;
435                 goto errout;
436         }
437
438         if (ret < 0) {
439                 goto errout;
440         }
441
442         return;
443
444 errout:
445         handler->cbs.period_changed.cb(handler, ret, handler->cbs.period_changed.data);
446         handler->cbs.period_changed.cb = NULL;
447         handler->cbs.period_changed.data = NULL;
448         handler->common->request.period_changed = 0;
449
450         if (ret == LB_STATUS_ERROR_NOT_EXIST && handler->refcnt == 2) {
451                 lb_invoke_event_handler(handler, LB_EVENT_DELETED);
452                 lb_unref(handler, 1);
453         }
454 }
455
456 static void del_ret_cb(struct livebox *handler, const struct packet *result, void *data)
457 {
458         struct cb_info *info = data;
459         int ret;
460         ret_cb_t cb;
461         void *cbdata;
462
463         cb = info->cb;
464         cbdata = info->data;
465         destroy_cb_info(info);
466
467         if (!result) {
468                 ErrPrint("Connection lost?\n");
469                 ret = LB_STATUS_ERROR_FAULT;
470         } else if (packet_get(result, "i", &ret) != 1) {
471                 ErrPrint("Invalid argument\n");
472                 ret = LB_STATUS_ERROR_INVALID;
473         }
474
475         if (ret == 0) {
476                 handler->cbs.deleted.cb = cb;
477                 handler->cbs.deleted.data = cbdata;
478         } else if (cb) {
479                 cb(handler, ret, cbdata);
480         }
481
482         /*!
483          * \note
484          * Do not call the deleted callback from here.
485          * master will send the "deleted" event.
486          * Then invoke this callback.
487          *
488          * if (handler->cbs.deleted.cb)
489          *      handler->cbs.deleted.cb(handler, ret, handler->cbs.deleted.data);
490          */
491 }
492
493 static void new_ret_cb(struct livebox *handler, const struct packet *result, void *data)
494 {
495         int ret;
496         struct cb_info *info = data;
497         ret_cb_t cb;
498         void *cbdata;
499
500         cb = info->cb;
501         cbdata = info->data;
502         destroy_cb_info(info);
503
504         if (!result) {
505                 ret = LB_STATUS_ERROR_FAULT;
506         } else if (packet_get(result, "i", &ret) != 1) {
507                 ret = LB_STATUS_ERROR_INVALID;
508         }
509
510         if (ret >= 0) {
511                 handler->cbs.created.cb = cb;
512                 handler->cbs.created.data = cbdata;
513
514                 /*!
515                  * \note
516                  * Don't go anymore ;)
517                  */
518                 return;
519         } else if (cb) {
520                 /*!
521                  * \note
522                  * It means the current instance is not created,
523                  * so user has to know about this.
524                  * notice it to user using "deleted" event.
525                  */
526                 cb(handler, ret, cbdata);
527         }
528
529         lb_unref(handler, 1);
530 }
531
532 static void pd_create_cb(struct livebox *handler, const struct packet *result, void *data)
533 {
534         int ret;
535
536         if (!result) {
537                 ret = LB_STATUS_ERROR_FAULT;
538                 goto errout;
539         } else if (packet_get(result, "i", &ret) != 1) {
540                 ret = LB_STATUS_ERROR_INVALID;
541                 goto errout;
542         }
543
544         if (ret < 0) {
545                 ErrPrint("Failed to create a PD[%d]\n", ret);
546                 goto errout;
547         }
548
549         return;
550
551 errout:
552         handler->cbs.pd_created.cb(handler, ret, handler->cbs.pd_created.data);
553         handler->cbs.pd_created.cb = NULL;
554         handler->cbs.pd_created.data = NULL;
555         handler->common->request.pd_created = 0;
556
557         if (ret == LB_STATUS_ERROR_NOT_EXIST && handler->refcnt == 2) {
558                 lb_invoke_event_handler(handler, LB_EVENT_DELETED);
559                 lb_unref(handler, 1);
560         }
561 }
562
563 static void activated_cb(struct livebox *handler, const struct packet *result, void *data)
564 {
565         int ret;
566         struct cb_info *info = data;
567         void *cbdata;
568         ret_cb_t cb;
569         const char *pkgname = "";
570
571         cbdata = info->data;
572         cb = info->cb;
573         destroy_cb_info(info);
574
575         if (!result) {
576                 ret = LB_STATUS_ERROR_FAULT;
577         } else if (packet_get(result, "is", &ret, &pkgname) != 2) {
578                 ret = LB_STATUS_ERROR_INVALID;
579         }
580
581         if (cb) {
582                 cb(handler, ret, cbdata);
583         }
584 }
585
586 static void pd_destroy_cb(struct livebox *handler, const struct packet *result, void *data)
587 {
588         int ret;
589         ret_cb_t cb;
590         void *cbdata;
591         struct cb_info *info = data;
592
593         cbdata = info->data;
594         cb = info->cb;
595         destroy_cb_info(info);
596
597         if (!result) {
598                 ErrPrint("Result is NIL (may connection lost)\n");
599                 ret = LB_STATUS_ERROR_FAULT;
600         } else if (packet_get(result, "i", &ret) != 1) {
601                 ErrPrint("Invalid parameter\n");
602                 ret = LB_STATUS_ERROR_INVALID;
603         }
604
605         if (ret == LB_STATUS_SUCCESS) {
606                 handler->cbs.pd_destroyed.cb = cb;
607                 handler->cbs.pd_destroyed.data = cbdata;
608         } else {
609                 handler->common->is_pd_created = 0;
610                 handler->common->request.pd_destroyed = 0;
611
612                 if (cb) {
613                         cb(handler, ret, cbdata);
614                 }
615         }
616 }
617
618 static void delete_cluster_cb(struct livebox *handler, const struct packet *result, void *data)
619 {
620         struct cb_info *info = data;
621         int ret;
622         ret_cb_t cb;
623         void *cbdata;
624
625         cb = info->cb;
626         cbdata = info->data;
627         destroy_cb_info(info);
628
629         if (!result) {
630                 ret = LB_STATUS_ERROR_FAULT;
631         } else if (packet_get(result, "i", &ret) != 1) {
632                 ret = LB_STATUS_ERROR_INVALID;
633         }
634
635         if (cb) {
636                 cb(handler, ret, cbdata);
637         }
638 }
639
640 static void delete_category_cb(struct livebox *handler, const struct packet *result, void *data)
641 {
642         struct cb_info *info = data;
643         int ret;
644         ret_cb_t cb;
645         void *cbdata;
646
647         cb = info->cb;
648         cbdata = info->data;
649         destroy_cb_info(info);
650
651         if (!result) {
652                 ret = LB_STATUS_ERROR_FAULT;
653         } else if (packet_get(result, "i", &ret) != 1) {
654                 ret = LB_STATUS_ERROR_INVALID;
655         }
656
657         if (cb) {
658                 cb(handler, ret, cbdata);
659         }
660 }
661
662 static int lb_acquire_lb_pixmap(struct livebox *handler, ret_cb_t cb, void *data)
663 {
664         struct packet *packet;
665         struct cb_info *cbinfo;
666         const char *id;
667         int ret;
668
669         id = fb_id(handler->common->lb.fb);
670         if (!id || strncasecmp(id, SCHEMA_PIXMAP, strlen(SCHEMA_PIXMAP))) {
671                 return LB_STATUS_ERROR_INVALID;
672         }
673
674         packet = packet_create("lb_acquire_pixmap", "ss", handler->common->pkgname, handler->common->id);
675         if (!packet) {
676                 ErrPrint("Failed to build a param\n");
677                 return LB_STATUS_ERROR_FAULT;
678         }
679
680         cbinfo = create_cb_info(cb, data);
681         if (!cbinfo) {
682                 packet_destroy(packet);
683                 return LB_STATUS_ERROR_FAULT;
684         }
685
686         ret = master_rpc_async_request(handler, packet, 0, lb_pixmap_acquired_cb, cbinfo);
687         if (ret < 0) {
688                 destroy_cb_info(cbinfo);
689         }
690
691         return ret;
692 }
693
694 static void lb_pixmap_acquired_cb(struct livebox *handler, const struct packet *result, void *data)
695 {
696         int pixmap;
697         int ret = LB_STATUS_ERROR_INVALID;
698         ret_cb_t cb;
699         void *cbdata;
700         struct cb_info *info = data;
701
702         cb = info->cb;
703         cbdata = info->data;
704         destroy_cb_info(info);
705
706         if (!result) {
707                 pixmap = 0; /* PIXMAP 0 means error */
708         } else if (packet_get(result, "ii", &pixmap, &ret) != 2) {
709                 pixmap = 0;
710         }
711
712         if (ret == LB_STATUS_ERROR_BUSY) {
713                 ret = lb_acquire_lb_pixmap(handler, cb, cbdata);
714                 DbgPrint("Busy, Try again: %d\n", ret);
715                 /* Try again */
716         } else if (ret == LB_STATUS_ERROR_NOT_EXIST && handler->refcnt == 2) {
717                 if (cb) {
718                         cb(handler, pixmap, cbdata);
719                 }
720
721                 lb_invoke_event_handler(handler, LB_EVENT_DELETED);
722                 lb_unref(handler, 1);
723         } else {
724                 if (cb) {
725                         cb(handler, pixmap, cbdata);
726                 }
727         }
728 }
729
730 static int lb_acquire_pd_pixmap(struct livebox *handler, ret_cb_t cb, void *data)
731 {
732         struct packet *packet;
733         struct cb_info *cbinfo;
734         const char *id;
735         int ret;
736
737         id = fb_id(handler->common->pd.fb);
738         if (!id || strncasecmp(id, SCHEMA_PIXMAP, strlen(SCHEMA_PIXMAP))) {
739                 return LB_STATUS_ERROR_INVALID;
740         }
741
742         packet = packet_create("pd_acquire_pixmap", "ss", handler->common->pkgname, handler->common->id);
743         if (!packet) {
744                 ErrPrint("Failed to build a param\n");
745                 return LB_STATUS_ERROR_FAULT;
746         }
747
748         cbinfo = create_cb_info(cb, data);
749         if (!cbinfo) {
750                 packet_destroy(packet);
751                 return LB_STATUS_ERROR_FAULT;
752         }
753
754         ret = master_rpc_async_request(handler, packet, 0, pd_pixmap_acquired_cb, cbinfo);
755         if (ret < 0) {
756                 /*!
757                  * \note
758                  * Packet will be destroyed by master_rpc_async_request
759                  */
760                 destroy_cb_info(cbinfo);
761         }
762
763         return ret;
764 }
765
766 static void pd_pixmap_acquired_cb(struct livebox *handler, const struct packet *result, void *data)
767 {
768         int pixmap;
769         int ret;
770         ret_cb_t cb;
771         void *cbdata;
772         struct cb_info *info = data;
773
774         cb = info->cb;
775         cbdata = info->data;
776         destroy_cb_info(info);
777
778         if (!result) {
779                 pixmap = 0; /* PIXMAP 0 means error */
780                 ret = LB_STATUS_ERROR_FAULT;
781         } else if (packet_get(result, "ii", &pixmap, &ret) != 2) {
782                 pixmap = 0;
783                 ret = LB_STATUS_ERROR_INVALID;
784         }
785
786         if (ret == LB_STATUS_ERROR_BUSY) {
787                 ret = lb_acquire_pd_pixmap(handler, cb, cbdata);
788                 DbgPrint("Busy, Try again: %d\n", ret);
789                 /* Try again */
790         } else if (ret == LB_STATUS_ERROR_NOT_EXIST && handler->refcnt == 2) {
791                 if (cb) {
792                         cb(handler, pixmap, cbdata);
793                 }
794                 lb_invoke_event_handler(handler, LB_EVENT_DELETED);
795                 lb_unref(handler, 1);
796         } else {
797                 if (cb) {
798                         DbgPrint("ret: %d, pixmap: %d\n", ret, pixmap);
799                         cb(handler, pixmap, cbdata);
800                 }
801         }
802 }
803
804 static void pinup_done_cb(struct livebox *handler, const struct packet *result, void *data)
805 {
806         int ret;
807
808         if (!result) {
809                 ret = LB_STATUS_ERROR_FAULT;
810                 goto errout;
811         } else if (packet_get(result, "i", &ret) != 1) {
812                 goto errout;
813         }
814
815         if (ret < 0) {
816                 goto errout;
817         }
818
819         return;
820
821 errout:
822         handler->cbs.pinup.cb(handler, ret, handler->cbs.pinup.data);
823         handler->cbs.pinup.cb = NULL;
824         handler->cbs.pinup.data = NULL;
825         handler->common->request.pinup = 0;
826
827         if (ret == LB_STATUS_ERROR_NOT_EXIST && handler->refcnt == 2) {
828                 lb_invoke_event_handler(handler, LB_EVENT_DELETED);
829                 lb_unref(handler, 1);
830         }
831 }
832
833 static void key_ret_cb(struct livebox *handler, const struct packet *result, void *data)
834 {
835         int ret;
836
837         if (!result) {
838                 ret = LB_STATUS_ERROR_FAULT;
839                 return;
840         }
841
842         if (packet_get(result, "i", &ret) != 1) {
843                 ret = LB_STATUS_ERROR_INVALID;
844                 return;
845         }
846
847         if (ret != LB_STATUS_SUCCESS) {
848                 goto errout;
849         }
850
851         return;
852 errout:
853         handler->cbs.key_event.cb(handler, ret, handler->cbs.key_event.data);
854         handler->cbs.key_event.cb = NULL;
855         handler->cbs.key_event.data = NULL;
856         handler->common->request.key_event = 0;
857
858         if (ret == LB_STATUS_ERROR_NOT_EXIST && handler->refcnt == 2) {
859                 lb_invoke_event_handler(handler, LB_EVENT_DELETED);
860                 lb_unref(handler, 1);
861         }
862 }
863
864 static void access_ret_cb(struct livebox *handler, const struct packet *result, void *data)
865 {
866         int ret;
867
868         if (!result) {
869                 ret = LB_STATUS_ERROR_FAULT;
870                 return;
871         }
872
873         if (packet_get(result, "i", &ret) != 1) {
874                 ret = LB_STATUS_ERROR_INVALID;
875                 return;
876         }
877
878         if (ret != LB_STATUS_SUCCESS) {
879                 goto errout;
880         }
881
882         return;
883
884 errout:
885         handler->cbs.access_event.cb(handler, ret, handler->cbs.access_event.data);
886         handler->cbs.access_event.cb = NULL;
887         handler->cbs.access_event.data = NULL;
888         handler->common->request.access_event = 0;
889
890         if (ret == LB_STATUS_ERROR_NOT_EXIST && handler->refcnt == 2) {
891                 lb_invoke_event_handler(handler, LB_EVENT_DELETED);
892                 lb_unref(handler, 1);
893         }
894 }
895
896 static int send_access_event(struct livebox *handler, const char *event, int x, int y)
897 {
898         struct packet *packet;
899         double timestamp;
900
901         timestamp = util_timestamp();
902
903         packet = packet_create(event, "ssdii", handler->common->pkgname, handler->common->id, timestamp, x, y);
904         if (!packet) {
905                 ErrPrint("Failed to build packet\n");
906                 return LB_STATUS_ERROR_FAULT;
907         }
908
909         return master_rpc_async_request(handler, packet, 0, access_ret_cb, NULL);
910 }
911
912 static int send_key_event(struct livebox *handler, const char *event, unsigned int keycode)
913 {
914         struct packet *packet;
915         double timestamp;
916
917         timestamp = util_timestamp();
918         packet = packet_create(event, "ssdi", handler->common->pkgname, handler->common->id, timestamp, keycode);
919         if (!packet) {
920                 ErrPrint("Failed to build packet\n");
921                 return LB_STATUS_ERROR_FAULT;
922         }
923
924         return master_rpc_async_request(handler, packet, 0, key_ret_cb, NULL);
925 }
926
927 static int send_mouse_event(struct livebox *handler, const char *event, int x, int y)
928 {
929         struct packet *packet;
930         double timestamp;
931
932         timestamp = util_timestamp();
933         packet = packet_create_noack(event, "ssdii", handler->common->pkgname, handler->common->id, timestamp, x, y);
934         if (!packet) {
935                 ErrPrint("Failed to build param\n");
936                 return LB_STATUS_ERROR_FAULT;
937         }
938
939         return master_rpc_request_only(handler, packet);
940 }
941
942 static void initialize_livebox(void *disp, int use_thread)
943 {
944 #if defined(FLOG)
945         char filename[BUFSIZ];
946         snprintf(filename, sizeof(filename), "/tmp/%d.box.log", getpid());
947         __file_log_fp = fopen(filename, "w+t");
948         if (!__file_log_fp) {
949                 __file_log_fp = fdopen(1, "w+t");
950         }
951 #endif
952         livebox_service_init();
953         fb_init(disp);
954
955         client_init(use_thread);
956
957         s_info.init_count++;
958 }
959
960 EAPI int livebox_init_with_options(void *disp, int prevent_overwrite, double event_filter, int use_thread)
961 {
962         if (s_info.init_count > 0) {
963                 s_info.init_count++;
964                 return LB_STATUS_SUCCESS;
965         }
966
967         /*!
968          * \note
969          * Some application doesn't want to use the environment value.
970          * So set them using arguments.
971          */
972         s_info.prevent_overwrite = prevent_overwrite;
973         conf_set_event_filter(event_filter);
974
975         initialize_livebox(disp, use_thread);
976         return LB_STATUS_SUCCESS;
977 }
978
979 EAPI int livebox_init(void *disp)
980 {
981         const char *env;
982
983         if (s_info.init_count > 0) {
984                 s_info.init_count++;
985                 return LB_STATUS_SUCCESS;
986         }
987
988         env = getenv("PROVIDER_DISABLE_PREVENT_OVERWRITE");
989         if (env && !strcasecmp(env, "true")) {
990                 s_info.prevent_overwrite = 1;
991         }
992
993         env = getenv("PROVIDER_EVENT_FILTER");
994         if (env) {
995                 double event_filter;
996                 if (sscanf(env, "%lf", &event_filter) == 1) {
997                         conf_set_event_filter(event_filter);
998                 }
999         }
1000
1001         initialize_livebox(disp, 0);
1002         return LB_STATUS_SUCCESS;
1003 }
1004
1005 EAPI int livebox_fini(void)
1006 {
1007         if (s_info.init_count <= 0) {
1008                 ErrPrint("Doesn't initialized\n");
1009                 return LB_STATUS_ERROR_INVALID;
1010         }
1011
1012         s_info.init_count--;
1013         if (s_info.init_count > 0) {
1014                 ErrPrint("init count : %d\n", s_info.init_count);
1015                 return LB_STATUS_SUCCESS;
1016         }
1017
1018         client_fini();
1019         fb_fini();
1020         livebox_service_fini();
1021         return LB_STATUS_SUCCESS;
1022 }
1023
1024 static inline char *lb_pkgname(const char *pkgname)
1025 {
1026         char *lb;
1027
1028         lb = livebox_service_pkgname(pkgname);
1029         if (!lb) {
1030                 if (util_validate_livebox_package(pkgname) == 0) {
1031                         return strdup(pkgname);
1032                 }
1033         }
1034
1035         return lb;
1036 }
1037
1038 static struct livebox_common *find_sharable_common_handle(const char *pkgname, const char *content, int w, int h, const char *cluster, const char *category)
1039 {
1040         struct dlist *l;
1041         struct livebox_common *common;
1042
1043         if (!conf_shared_content()) {
1044                 /*!
1045                  * Shared content option is turnned off.
1046                  */
1047                 return NULL;
1048         }
1049
1050         dlist_foreach(s_info.livebox_common_list, l, common) {
1051                 if (common->state != CREATE) {
1052                         continue;
1053                 }
1054
1055                 if (strcmp(common->pkgname, pkgname)) {
1056                         continue;
1057                 }
1058
1059                 if (strcmp(common->cluster, cluster)) {
1060                         DbgPrint("Cluster mismatched\n");
1061                         continue;
1062                 }
1063
1064                 if (strcmp(common->category, category)) {
1065                         DbgPrint("Category mismatched\n");
1066                         continue;
1067                 }
1068
1069                 if (common->content && content) {
1070                         if (strcmp(common->content, content)) {
1071                                 DbgPrint("%s Content ([%s] <> [%s])\n", common->pkgname, common->content, content);
1072                                 continue;       
1073                         }
1074                 } else {
1075                         int c1_len;
1076                         int c2_len;
1077
1078                         /*!
1079                          * \note
1080                          * We assumes "" (ZERO length string) to NULL
1081                          */
1082                         c1_len = common->content ? strlen(common->content) : 0;
1083                         c2_len = content ? strlen(content) : 0;
1084                         if (c1_len != c2_len) {
1085                                 DbgPrint("%s Content %p <> %p\n", common->pkgname, common->content, content);
1086                                 continue;
1087                         }
1088                 }
1089
1090                 if (common->request.size_changed) {
1091                         DbgPrint("Changing size\n");
1092                         /*!
1093                          * \note
1094                          * Do not re-use resizing instance.
1095                          * We will not use predicted size.
1096                          */
1097                         continue;
1098                 }
1099
1100                 if (common->request.created) {
1101                         DbgPrint("Creating now but re-use it (%s)\n", common->pkgname);
1102                 }
1103
1104                 if (common->lb.width != w || common->lb.height != h) {
1105                         DbgPrint("Size mismatched\n");
1106                         continue;
1107                 }
1108
1109                 DbgPrint("common handle is found: %p\n", common);
1110                 return common;
1111         }
1112
1113         return NULL;
1114 }
1115
1116 /*!
1117  * Just wrapping the livebox_add_with_size function.
1118  */
1119 EAPI struct livebox *livebox_add(const char *pkgname, const char *content, const char *cluster, const char *category, double period, ret_cb_t cb, void *data)
1120 {
1121         return livebox_add_with_size(pkgname, content, cluster, category, period, LB_SIZE_TYPE_UNKNOWN, cb, data);
1122 }
1123
1124 static gboolean job_execute_cb(void *data)
1125 {
1126         struct job_item *item;
1127         struct dlist *l;
1128
1129         l = dlist_nth(s_info.job_list, 0);
1130         if (!l) {
1131                 s_info.job_timer = 0;
1132                 return FALSE;
1133         }
1134
1135         item = dlist_data(l);
1136         s_info.job_list = dlist_remove(s_info.job_list, l);
1137
1138         if (item) {
1139                 item->cb(item->handle, item->ret, item->data);
1140                 lb_unref(item->handle, 1);
1141                 free(item);
1142         }
1143
1144         return TRUE;
1145 }
1146
1147 static int job_add(struct livebox *handle, ret_cb_t job_cb, int ret, void *data)
1148 {
1149         struct job_item *item;
1150
1151         if (!job_cb) {
1152                 ErrPrint("Invalid argument\n");
1153                 return LB_STATUS_ERROR_INVALID;
1154         }
1155
1156         item = malloc(sizeof(*item));
1157         if (!item) {
1158                 ErrPrint("Heap: %s\n", strerror(errno));
1159                 return LB_STATUS_ERROR_MEMORY;
1160         }
1161
1162         item->handle = lb_ref(handle);
1163         item->cb = job_cb;
1164         item->data = data;
1165         item->ret = ret;
1166
1167         s_info.job_list = dlist_append(s_info.job_list, item);
1168
1169         if (!s_info.job_timer) {
1170                 s_info.job_timer = g_timeout_add(1, job_execute_cb, NULL);
1171                 if (!s_info.job_timer) {
1172                         ErrPrint("Failed to create a job timer\n");
1173                 }
1174         }
1175
1176         return LB_STATUS_SUCCESS;
1177 }
1178
1179 static int create_real_instance(struct livebox *handler, ret_cb_t cb, void *data)
1180 {
1181         struct cb_info *cbinfo;
1182         struct packet *packet;
1183         struct livebox_common *common;
1184         int ret;
1185
1186         common = handler->common;
1187
1188         packet = packet_create("new", "dssssdii",
1189                                 common->timestamp, common->pkgname, common->content,
1190                                 common->cluster, common->category,
1191                                 common->lb.period, common->lb.width, common->lb.height);
1192         if (!packet) {
1193                 ErrPrint("Failed to create a new packet\n");
1194                 return LB_STATUS_ERROR_FAULT;
1195         }
1196
1197         cbinfo = create_cb_info(cb, data);
1198         if (!cbinfo) {
1199                 ErrPrint("Failed to create a cbinfo\n");
1200                 packet_destroy(packet);
1201                 return LB_STATUS_ERROR_MEMORY;
1202         }
1203
1204         /*!
1205          * \note
1206          * master_rpc_async_request will destroy the packet (decrease the refcnt)
1207          * So be aware the packet object after return from master_rpc_async_request.
1208          */
1209         ret = master_rpc_async_request(handler, packet, 0, new_ret_cb, cbinfo);
1210         if (ret < 0) {
1211                 ErrPrint("Failed to send a new packet\n");
1212                 destroy_cb_info(cbinfo);
1213                 return LB_STATUS_ERROR_FAULT;
1214         }
1215         handler->common->request.created = 1;
1216         return LB_STATUS_SUCCESS;
1217 }
1218
1219 static void create_cb(struct livebox *handle, int ret, void *data)
1220 {
1221         struct cb_info *cbinfo = data;
1222
1223         if (cbinfo->cb) {
1224                 cbinfo->cb(handle, ret, cbinfo->data);
1225         }
1226
1227         destroy_cb_info(cbinfo);
1228
1229         /*!
1230          * \note
1231          * Forcely generate "updated" event
1232          */
1233         lb_invoke_event_handler(handle, LB_EVENT_LB_UPDATED);
1234 }
1235
1236 static int create_fake_instance(struct livebox *handler, ret_cb_t cb, void *data)
1237 {
1238         struct cb_info *cbinfo;
1239
1240         cbinfo = create_cb_info(cb, data);
1241         if (!cbinfo) {
1242                 ErrPrint("Failed to create a cbinfo\n");
1243                 return LB_STATUS_ERROR_MEMORY;
1244         }
1245
1246         if (job_add(handler, create_cb, LB_STATUS_SUCCESS, cbinfo) != LB_STATUS_SUCCESS) {
1247                 destroy_cb_info(cbinfo);
1248         }
1249
1250         return LB_STATUS_SUCCESS;
1251 }
1252
1253 struct livebox_common *lb_create_common_handle(struct livebox *handle, const char *pkgname, const char *cluster, const char *category)
1254 {
1255         struct livebox_common *common;
1256
1257         common = calloc(1, sizeof(*common));
1258         if (!common) {
1259                 ErrPrint("Heap: %s\n", strerror(errno));
1260                 return NULL;
1261         }
1262
1263         common->pkgname = strdup(pkgname);
1264         if (!common->pkgname) {
1265                 free(common);
1266                 return NULL;
1267         }
1268
1269         common->cluster = strdup(cluster);
1270         if (!common->cluster) {
1271                 ErrPrint("Error: %s\n", strerror(errno));
1272                 free(common->pkgname);
1273                 free(common);
1274                 return NULL;
1275         }
1276
1277         common->category = strdup(category);
1278         if (!common->category) {
1279                 ErrPrint("Error: %s\n", strerror(errno));
1280                 free(common->cluster);
1281                 free(common->pkgname);
1282                 free(common);
1283                 return NULL;
1284         }
1285
1286         /* Data provider will set this */
1287         common->lb.type = _LB_TYPE_FILE;
1288         common->pd.type = _PD_TYPE_SCRIPT;
1289
1290         /* Used for handling the mouse event on a box */
1291         common->lb.mouse_event = livebox_service_mouse_event(common->pkgname);
1292
1293         /* Cluster infomration is not determined yet */
1294         common->nr_of_sizes = 0x01;
1295
1296         common->timestamp = util_timestamp();
1297         common->is_user = 1;
1298         common->delete_type = LB_DELETE_PERMANENTLY;
1299         common->pd.lock = NULL;
1300         common->pd.lock_fd = -1;
1301         common->lb.lock = NULL;
1302         common->lb.lock_fd = -1;
1303
1304         common->state = CREATE;
1305         common->visible = LB_SHOW;
1306
1307         s_info.livebox_common_list = dlist_append(s_info.livebox_common_list, common);
1308         return common;
1309 }
1310
1311 int lb_destroy_common_handle(struct livebox_common *common)
1312 {
1313         dlist_remove_data(s_info.livebox_common_list, common);
1314
1315         common->state = DESTROYED;
1316
1317         if (common->filename) {
1318                 (void)util_unlink(common->filename);
1319         }
1320
1321         free(common->cluster);
1322         free(common->category);
1323         free(common->id);
1324         free(common->pkgname);
1325         free(common->filename);
1326         free(common->lb.auto_launch);
1327         free(common->alt.icon);
1328         free(common->alt.name);
1329
1330         if (common->lb.fb) {
1331                 fb_destroy(common->lb.fb);
1332                 common->lb.fb = NULL;
1333         }
1334
1335         if (common->pd.fb) {
1336                 fb_destroy(common->pd.fb);
1337                 common->pd.fb = NULL;
1338         }
1339
1340         return 0;
1341 }
1342
1343 int lb_common_ref(struct livebox_common *common, struct livebox *handle)
1344 {
1345         common->livebox_list = dlist_append(common->livebox_list, handle);
1346         common->refcnt++;
1347
1348         return common->refcnt;
1349 }
1350
1351 int lb_common_unref(struct livebox_common *common, struct livebox *handle)
1352 {
1353         int refcnt;
1354         dlist_remove_data(common->livebox_list, handle);
1355         refcnt = --common->refcnt;
1356
1357         return refcnt;
1358 }
1359
1360 static void refresh_for_paused_updating_cb(struct livebox *handle, int ret, void *data)
1361 {
1362         if (handle->paused_updating == 0) {
1363                 DbgPrint("Paused updates are cleared\n");
1364                 return;
1365         }
1366
1367         DbgPrint("Pending updates are found\n");
1368         lb_invoke_event_handler(handle, LB_EVENT_LB_UPDATED);
1369 }
1370
1371 static int lb_set_visibility(struct livebox *handler, enum livebox_visible_state state)
1372 {
1373         struct packet *packet;
1374         int need_to_add_job = 0;
1375         int ret;
1376
1377         if (handler->common->visible != LB_SHOW && state == LB_SHOW) {
1378                 need_to_add_job = !!handler->paused_updating;
1379         } else if (handler->common->visible == LB_SHOW && state != LB_SHOW) {
1380                 struct dlist *l;
1381                 struct livebox *item;
1382
1383                 dlist_foreach(handler->common->livebox_list, l, item) {
1384                         if (item->visible == LB_SHOW) {
1385                                 DbgPrint("%s visibility is not changed\n", handler->common->pkgname);
1386                                 return LB_STATUS_SUCCESS;
1387                         }
1388                 }
1389         } else if (handler->common->visible == LB_SHOW && state == LB_SHOW && handler->paused_updating) {
1390                 if (job_add(handler, refresh_for_paused_updating_cb, LB_STATUS_SUCCESS, NULL) < 0) {
1391                         ErrPrint("Unable to add a new job for refreshing box\n");
1392                 }
1393
1394                 return LB_STATUS_SUCCESS;
1395         } else {
1396                 /*!
1397                  * \brief
1398                  * No need to send this to the master
1399                  */
1400                 return LB_STATUS_SUCCESS;
1401         }
1402
1403         packet = packet_create_noack("change,visibility", "ssi", handler->common->pkgname, handler->common->id, (int)state);
1404         if (!packet) {
1405                 ErrPrint("Failed to create a packet\n");
1406                 return LB_STATUS_ERROR_FAULT;
1407         }
1408
1409         ret = master_rpc_request_only(handler, packet);
1410         if (ret == LB_STATUS_SUCCESS) {
1411                 DbgPrint("[%s] visibility is changed 0x[%x]\n", handler->common->pkgname, state);
1412                 handler->common->visible = state;
1413
1414                 if (need_to_add_job) {
1415                         if (job_add(handler, refresh_for_paused_updating_cb, LB_STATUS_SUCCESS, NULL) < 0) {
1416                                 ErrPrint("Unable to add a new job for refreshing box\n");
1417                         }
1418                 }
1419         }
1420
1421         return ret;
1422 }
1423
1424 EAPI struct livebox *livebox_add_with_size(const char *pkgname, const char *content, const char *cluster, const char *category, double period, int type, ret_cb_t cb, void *data)
1425 {
1426         char *lbid;
1427         struct livebox *handler;
1428         int w = 0;
1429         int h = 0;
1430
1431         if (!pkgname || !cluster || !category) {
1432                 ErrPrint("Invalid arguments: pkgname[%p], cluster[%p], category[%p]\n",
1433                                                                 pkgname, cluster, category);
1434                 return NULL;
1435         }
1436
1437         lbid = lb_pkgname(pkgname);
1438         if (!lbid) {
1439                 ErrPrint("Invalid package: %s\n", pkgname);
1440                 return NULL;
1441         }
1442
1443         if (livebox_service_is_enabled(lbid) == 0) {
1444                 DbgPrint("Livebox [%s](%s) is disabled package\n", lbid, pkgname);
1445                 free(lbid);
1446                 return NULL;
1447         }
1448
1449         if (type != LB_SIZE_TYPE_UNKNOWN) {
1450                 (void)livebox_service_get_size(type, &w, &h);
1451         }
1452
1453         handler = calloc(1, sizeof(*handler));
1454         if (!handler) {
1455                 ErrPrint("Error: %s\n", strerror(errno));
1456                 free(lbid);
1457                 return NULL;
1458         }
1459
1460         if (!cb) {
1461                 cb = default_create_cb;
1462         }
1463
1464         handler->common = find_sharable_common_handle(lbid, content, w, h, cluster, category);
1465         if (!handler->common) {
1466                 handler->common = lb_create_common_handle(handler, lbid, cluster, category);
1467                 free(lbid);
1468                 if (!handler->common) {
1469                         ErrPrint("Failed to find common handle\n");
1470                         free(handler);
1471                         return NULL;
1472                 }
1473
1474                 if (!content || !strlen(content)) {
1475                         char *pc;
1476                         /*!
1477                          * \note
1478                          * I know the content should not be modified. use it temporarly without "const"
1479                          */
1480                         pc = livebox_service_content(handler->common->pkgname);
1481                         lb_set_content(handler->common, pc);
1482                         free(pc);
1483                 } else {
1484                         lb_set_content(handler->common, content);
1485                 }
1486
1487                 lb_set_period(handler->common, period);
1488                 lb_set_size(handler->common, w, h);
1489                 lb_common_ref(handler->common, handler);
1490
1491                 if (create_real_instance(handler, cb, data) < 0) {
1492                         if (lb_common_unref(handler->common, handler) == 0) {
1493                                 /*!
1494                                  * Delete common
1495                                  */
1496                                 lb_destroy_common_handle(handler->common);
1497                                 handler->common = NULL;
1498                         }
1499                         free(handler);
1500                         return NULL;
1501                 }
1502         } else {
1503                 free(lbid);
1504
1505                 lb_common_ref(handler->common, handler);
1506
1507                 if (handler->common->request.created) {
1508                         /*!
1509                          * If a box is in creating, wait its result too
1510                          */
1511                         handler->cbs.created.cb = cb;
1512                         handler->cbs.created.data = data;
1513                 } else {
1514                         /*!
1515                          * or fire the fake created_event
1516                          */
1517                         if (create_fake_instance(handler, cb, data) < 0) {
1518                                 if (lb_common_unref(handler->common, handler) == 0) {
1519                                         /*!
1520                                          * Delete common
1521                                          */
1522                                         lb_destroy_common_handle(handler->common);
1523                                 }
1524                                 free(handler);
1525                                 return NULL;
1526                         }
1527                 }
1528         }
1529
1530         handler->visible = LB_SHOW;
1531         handler->state = CREATE;
1532         handler = lb_ref(handler);
1533
1534         if (handler->common->visible != LB_SHOW) {
1535                 lb_set_visibility(handler, LB_SHOW);
1536         }
1537
1538         return handler;
1539 }
1540
1541 EAPI double livebox_period(struct livebox *handler)
1542 {
1543         if (!handler || handler->state != CREATE) {
1544                 ErrPrint("Handler is not valid\n");
1545                 return 0.0f;
1546         }
1547
1548         if (!handler->common || handler->common->state != CREATE) {
1549                 ErrPrint("Invalid handle\n");
1550                 return 0.0f;
1551         }
1552
1553         if (!handler->common->id) {
1554                 ErrPrint("Hnalder is not valid\n");
1555                 return 0.0f;
1556         }
1557
1558         return handler->common->lb.period;
1559 }
1560
1561 EAPI int livebox_set_period(struct livebox *handler, double period, ret_cb_t cb, void *data)
1562 {
1563         struct packet *packet;
1564         int ret;
1565
1566         if (!handler || handler->state != CREATE) {
1567                 ErrPrint("Handler is not valid\n");
1568                 return LB_STATUS_ERROR_INVALID;
1569         }
1570
1571         if (!handler->common || handler->common->state != CREATE) {
1572                 ErrPrint("Invalid handle\n");
1573                 return LB_STATUS_ERROR_INVALID;
1574         }
1575
1576         if (!handler->common->id) {
1577                 ErrPrint("Handler is not valid\n");
1578                 return LB_STATUS_ERROR_INVALID;
1579         }
1580
1581         if (handler->common->request.period_changed) {
1582                 ErrPrint("Previous request for changing period is not finished\n");
1583                 return LB_STATUS_ERROR_BUSY;
1584         }
1585
1586         if (!handler->common->is_user) {
1587                 ErrPrint("CA Livebox is not able to change the period\n");
1588                 return LB_STATUS_ERROR_PERMISSION;
1589         }
1590
1591         if (handler->common->lb.period == period) {
1592                 DbgPrint("No changes\n");
1593                 return LB_STATUS_ERROR_ALREADY;
1594         }
1595
1596         packet = packet_create("set_period", "ssd", handler->common->pkgname, handler->common->id, period);
1597         if (!packet) {
1598                 ErrPrint("Failed to build a packet %s\n", handler->common->pkgname);
1599                 return LB_STATUS_ERROR_FAULT;
1600         }
1601
1602         if (!cb) {
1603                 cb = default_period_changed_cb;
1604         }
1605
1606         ret = master_rpc_async_request(handler, packet, 0, period_ret_cb, NULL);
1607         if (ret == LB_STATUS_SUCCESS) {
1608                 handler->cbs.period_changed.cb = cb;
1609                 handler->cbs.period_changed.data = data;
1610                 handler->common->request.period_changed = 1;
1611         }
1612
1613         return ret;
1614 }
1615
1616 static void lb_update_visibility(struct livebox_common *old_common)
1617 {
1618         struct dlist *l;
1619         struct livebox *item;
1620
1621         item = NULL;
1622         dlist_foreach(old_common->livebox_list, l, item) {
1623                 if (item->visible == LB_SHOW) {
1624                         break;
1625                 }
1626
1627                 item = NULL;
1628         }
1629
1630         if (!item) {
1631                 l = dlist_nth(old_common->livebox_list, 0);
1632                 item = dlist_data(l);
1633
1634                 if (item) {
1635                         lb_set_visibility(item, LB_HIDE_WITH_PAUSE);
1636                 } else {
1637                         ErrPrint("Unable to get the valid handle from common handler\n");
1638                 }
1639         } else {
1640                 lb_set_visibility(item, LB_SHOW);
1641         }
1642 }
1643
1644 /*!
1645  * \note
1646  * The second parameter should be the "return value",
1647  * But in this case, we will use it for "type of deleting instance".
1648  */
1649 static void job_del_cb(struct livebox *handle, int type, void *data)
1650 {
1651         struct cb_info *cbinfo = data;
1652         ret_cb_t cb;
1653
1654         if (handle->visible == LB_SHOW) {
1655                 lb_update_visibility(handle->common);
1656         }
1657
1658         cb = cbinfo->cb;
1659         data = cbinfo->data;
1660         destroy_cb_info(cbinfo);
1661
1662         if (handle->common->state != CREATE) {
1663                 DbgPrint("[%s] %d\n", handle->common->pkgname, handle->refcnt);
1664                 if (cb) {
1665                         cb(handle, LB_STATUS_SUCCESS, data);
1666                 }
1667
1668                 return;
1669         }
1670
1671         if (handle->common->refcnt == 1) {
1672                 handle->common->delete_type = type;
1673                 handle->common->state = DELETE;
1674
1675                 if (!handle->common->id) {
1676                         /*!
1677                          * \note
1678                          * The id is not determined yet.
1679                          * It means a user didn't receive created event yet.
1680                          * Then just stop to delete procedure from here.
1681                          * Because the "created" event handle will release this.
1682                          * By the way, if the user adds any callback for getting return status of this,
1683                          * call it at here.
1684                          */
1685                         if (cb) {
1686                                 cb(handle, LB_STATUS_SUCCESS, data);
1687                         }
1688                 }
1689
1690                 DbgPrint("Send delete request\n");
1691                 lb_send_delete(handle, type, cb, data);
1692         } else {
1693                 if (cb) {
1694                         cb(handle, LB_STATUS_SUCCESS, data);
1695                 }
1696
1697                 DbgPrint("Before unref: %d\n", handle->common->refcnt);
1698                 lb_unref(handle, 1);
1699         }
1700 }
1701
1702 EAPI int livebox_del_NEW(struct livebox *handler, int type, ret_cb_t cb, void *data)
1703 {
1704         struct cb_info *cbinfo;
1705
1706         if (!handler) {
1707                 ErrPrint("Handler is NIL\n");
1708                 return LB_STATUS_ERROR_INVALID;
1709         }
1710
1711         if (handler->state != CREATE) {
1712                 ErrPrint("Handler is already deleted\n");
1713                 return LB_STATUS_ERROR_INVALID;
1714         }
1715
1716         handler->state = DELETE;
1717
1718         cbinfo = create_cb_info(cb, data);
1719         if (!cbinfo) {
1720                 ErrPrint("Failed to create a cbinfo\n");
1721                 return LB_STATUS_ERROR_MEMORY;
1722         }
1723
1724         if (job_add(handler, job_del_cb, type, cbinfo) != LB_STATUS_SUCCESS) {
1725                 ErrPrint("Failed to add a new job\n");
1726                 destroy_cb_info(cbinfo);
1727                 return LB_STATUS_ERROR_FAULT;
1728         }
1729
1730         return LB_STATUS_SUCCESS;
1731 }
1732
1733 EAPI int livebox_del(struct livebox *handler, ret_cb_t cb, void *data)
1734 {
1735         return livebox_del_NEW(handler, LB_DELETE_PERMANENTLY, cb, data);
1736 }
1737
1738 EAPI int livebox_set_fault_handler(int (*cb)(enum livebox_fault_type, const char *, const char *, const char *, void *), void *data)
1739 {
1740         struct fault_info *info;
1741
1742         if (!cb) {
1743                 return LB_STATUS_ERROR_INVALID;
1744         }
1745
1746         info = malloc(sizeof(*info));
1747         if (!info) {
1748                 ErrPrint("Heap: %s\n", strerror(errno));
1749                 return LB_STATUS_ERROR_MEMORY;
1750         }
1751
1752         info->handler = cb;
1753         info->user_data = data;
1754         info->is_deleted = 0;
1755
1756         s_info.fault_list = dlist_append(s_info.fault_list, info);
1757         return LB_STATUS_SUCCESS;
1758 }
1759
1760 EAPI void *livebox_unset_fault_handler(int (*cb)(enum livebox_fault_type, const char *, const char *, const char *, void *))
1761 {
1762         struct fault_info *info;
1763         struct dlist *l;
1764
1765         dlist_foreach(s_info.fault_list, l, info) {
1766                 if (info->handler == cb) {
1767                         void *data;
1768
1769                         data = info->user_data;
1770
1771                         if (s_info.fault_state == INFO_STATE_CALLBACK_IN_PROCESSING) {
1772                                 info->is_deleted = 1;
1773                         } else {
1774                                 s_info.fault_list = dlist_remove(s_info.fault_list, l);
1775                                 free(info);
1776                         }
1777
1778                         return data;
1779                 }
1780         }
1781
1782         return NULL;
1783 }
1784
1785 EAPI int livebox_set_event_handler(int (*cb)(struct livebox *, enum livebox_event_type, void *), void *data)
1786 {
1787         struct event_info *info;
1788
1789         if (!cb) {
1790                 ErrPrint("Invalid argument cb is nil\n");
1791                 return LB_STATUS_ERROR_INVALID;
1792         }
1793
1794         info = malloc(sizeof(*info));
1795         if (!info) {
1796                 ErrPrint("Heap: %s\n", strerror(errno));
1797                 return LB_STATUS_ERROR_MEMORY;
1798         }
1799
1800         info->handler = cb;
1801         info->user_data = data;
1802         info->is_deleted = 0;
1803
1804         s_info.event_list = dlist_append(s_info.event_list, info);
1805         return LB_STATUS_SUCCESS;
1806 }
1807
1808 EAPI void *livebox_unset_event_handler(int (*cb)(struct livebox *, enum livebox_event_type, void *))
1809 {
1810         struct event_info *info;
1811         struct dlist *l;
1812
1813         dlist_foreach(s_info.event_list, l, info) {
1814                 if (info->handler == cb) {
1815                         void *data;
1816
1817                         data = info->user_data;
1818
1819                         if (s_info.event_state == INFO_STATE_CALLBACK_IN_PROCESSING) {
1820                                 info->is_deleted = 1;
1821                         } else {
1822                                 s_info.event_list = dlist_remove(s_info.event_list, l);
1823                                 free(info);
1824                         }
1825
1826                         return data;
1827                 }
1828         }
1829
1830         return NULL;
1831 }
1832
1833 EAPI int livebox_set_update_mode(struct livebox *handler, int active_update, ret_cb_t cb, void *data)
1834 {
1835         struct packet *packet;
1836         int ret;
1837
1838         if (!handler || handler->state != CREATE) {
1839                 ErrPrint("Handler is Invalid\n");
1840                 return LB_STATUS_ERROR_INVALID;
1841         }
1842
1843         if (!handler->common || handler->common->state != CREATE) {
1844                 ErrPrint("Handler is Invalid\n");
1845                 return LB_STATUS_ERROR_INVALID;
1846         }
1847
1848         if (!handler->common->id) {
1849                 ErrPrint("Handler is Invalid\n");
1850                 return LB_STATUS_ERROR_INVALID;
1851         }
1852
1853         if (handler->common->request.update_mode) {
1854                 ErrPrint("Previous update_mode cb is not finished yet\n");
1855                 return LB_STATUS_ERROR_BUSY;
1856         }
1857
1858         if (handler->common->is_active_update == active_update) {
1859                 return LB_STATUS_ERROR_ALREADY;
1860         }
1861
1862         if (!handler->common->is_user) {
1863                 return LB_STATUS_ERROR_PERMISSION;
1864         }
1865
1866         packet = packet_create("update_mode", "ssi", handler->common->pkgname, handler->common->id, active_update);
1867         if (!packet) {
1868                 return LB_STATUS_ERROR_FAULT;
1869         }
1870
1871         if (!cb) {
1872                 cb = default_update_mode_cb;
1873         }
1874
1875         ret = master_rpc_async_request(handler, packet, 0, update_mode_cb, NULL);
1876         if (ret == LB_STATUS_SUCCESS) {
1877                 handler->cbs.update_mode.cb = cb;
1878                 handler->cbs.update_mode.data = data;
1879                 handler->common->request.update_mode = 1;
1880         }
1881
1882         return ret;
1883 }
1884
1885 EAPI int livebox_is_active_update(struct livebox *handler)
1886 {
1887         if (!handler || handler->state != CREATE) {
1888                 ErrPrint("Handler is Invalid\n");
1889                 return LB_STATUS_ERROR_INVALID;
1890         }
1891
1892         if (!handler->common || handler->common->state != CREATE) {
1893                 ErrPrint("Handler is Invalid\n");
1894                 return LB_STATUS_ERROR_INVALID;
1895         }
1896
1897         if (!handler->common->id) {
1898                 return LB_STATUS_ERROR_INVALID;
1899         }
1900
1901         return handler->common->is_active_update;
1902 }
1903
1904 static void resize_job_cb(struct livebox *handler, int ret, void *data)
1905 {
1906         struct cb_info *info = data;
1907
1908         if (info->cb) {
1909                 info->cb(handler, ret, info->data);
1910         }
1911
1912         free(info);
1913
1914         /*!
1915          * \note
1916          * Forcely update the box
1917          */
1918         lb_invoke_event_handler(handler, LB_EVENT_LB_UPDATED);
1919 }
1920
1921 EAPI int livebox_resize(struct livebox *handler, int type, ret_cb_t cb, void *data)
1922 {
1923         struct livebox_common *common;
1924         int w;
1925         int h;
1926         int ret;
1927
1928         /*!
1929          * \TODO
1930          * If this handle is host instance or link instance,
1931          * Create a new instance or find another linkable instance.
1932          */
1933
1934         if (!handler || handler->state != CREATE) {
1935                 ErrPrint("Handler is not valid\n");
1936                 return LB_STATUS_ERROR_INVALID;
1937         }
1938
1939         if (!handler->common || handler->common->state != CREATE) {
1940                 ErrPrint("Invalid handle\n");
1941                 return LB_STATUS_ERROR_INVALID;
1942         }
1943
1944         if (!handler->common->id) {
1945                 ErrPrint("Handler is not valid\n");
1946                 return LB_STATUS_ERROR_INVALID;
1947         }
1948
1949         /*!
1950          * \note
1951          * resize operation should be separated by each handler.
1952          * If a handler is resizing, the other handler can request resize too.
1953          * So we should not use the common->request.size_changed flag.
1954          */
1955         if (handler->cbs.size_changed.cb) {
1956                 ErrPrint("Previous resize request is not finished yet\n");
1957                 return LB_STATUS_ERROR_BUSY;
1958         }
1959
1960         if (livebox_service_get_size(type, &w, &h) != 0) {
1961                 ErrPrint("Invalid size type\n");
1962                 return LB_STATUS_ERROR_INVALID;
1963         }
1964
1965         if (handler->common->lb.width == w && handler->common->lb.height == h) {
1966                 DbgPrint("No changes\n");
1967                 return LB_STATUS_ERROR_ALREADY;
1968         }
1969
1970         if (!handler->common->is_user) {
1971                 ErrPrint("CA Livebox is not able to be resized\n");
1972                 return LB_STATUS_ERROR_PERMISSION;
1973         }
1974
1975         if (handler->common->refcnt <= 1) {
1976                 struct packet *packet;
1977
1978                 /* Only 1 instance */
1979                 packet = packet_create("resize", "ssii", handler->common->pkgname, handler->common->id, w, h);
1980                 if (!packet) {
1981                         ErrPrint("Failed to build param\n");
1982                         return LB_STATUS_ERROR_FAULT;
1983                 }
1984
1985                 if (!cb) {
1986                         cb = default_lb_size_changed_cb;
1987                 }
1988
1989                 ret = master_rpc_async_request(handler, packet, 0, resize_cb, NULL);
1990                 if (ret == LB_STATUS_SUCCESS) {
1991                         handler->cbs.size_changed.cb = cb;
1992                         handler->cbs.size_changed.data = data;
1993                         handler->common->request.size_changed = 1;
1994                 }
1995         } else {
1996                 common = find_sharable_common_handle(handler->common->pkgname, handler->common->content, w, h, handler->common->cluster, handler->common->category);
1997                 if (!common) {
1998                         struct livebox_common *old_common;
1999                         /*!
2000                          * \note
2001                          * If the common handler is in resizing,
2002                          * if user tries to resize a hander, then simply create new one even if the requested size is same with this.
2003
2004                         if (handler->common->request.size_changed) {
2005                         }
2006
2007                          */
2008
2009                         old_common = handler->common;
2010
2011                         common = lb_create_common_handle(handler, old_common->pkgname, old_common->cluster, old_common->category);
2012                         if (!common) {
2013                                 ErrPrint("Failed to create common handle\n");
2014                                 return LB_STATUS_ERROR_FAULT;
2015                         }
2016
2017                         lb_set_size(common, w, h);
2018                         lb_set_content(common, old_common->content);
2019                         lb_set_period(common, old_common->lb.period);
2020
2021                         /*!
2022                          * \note
2023                          * Disconnecting from old one.
2024                          */
2025                         if (lb_common_unref(old_common, handler) == 0) {
2026                                 /*!
2027                                  * \note
2028                                  * Impossible
2029                                  */
2030                                 ErrPrint("Common has no associated handler\n");
2031                         }
2032
2033                         lb_common_ref(common, handler);
2034
2035                         /*!
2036                          * Connect to a new one
2037                          */
2038                         handler->common = common;
2039
2040                         /*!
2041                          * \TODO
2042                          * Need to care, if it fails to create a common handle,
2043                          * the resize operation will be failed.
2044                          * in that case, we should reuse the old common handle
2045                          */
2046                         ret = create_real_instance(handler, cb, data);
2047                         if (ret < 0) {
2048                                 lb_common_unref(common, handler);
2049                                 lb_destroy_common_handle(common);
2050
2051                                 lb_common_ref(old_common, handler);
2052                                 handler->common = old_common;
2053                         } else {
2054                                 /*!
2055                                  * In this case, we should update visibility of old_common's liveboxes
2056                                  */
2057                                 if (handler->visible == LB_SHOW) {
2058                                         lb_update_visibility(old_common);
2059                                 }
2060                         }
2061                 } else {
2062                         struct cb_info *cbinfo;
2063
2064                         cbinfo = create_cb_info(cb, data);
2065                         if (!cbinfo) {
2066                                 ErrPrint("Failed to create a cbinfo\n");
2067                                 ret = LB_STATUS_ERROR_MEMORY;
2068                         } else {
2069                                 ret = job_add(handler, resize_job_cb, LB_STATUS_SUCCESS, cbinfo);
2070                                 if (ret == LB_STATUS_SUCCESS) {
2071                                         struct livebox_common *old_common;
2072
2073                                         old_common = handler->common;
2074
2075                                         if (lb_common_unref(handler->common, handler) == 0) {
2076                                                 ErrPrint("Old common has no associated handler\n");
2077                                         }
2078
2079                                         lb_common_ref(common, handler);
2080                                         handler->common = common;
2081
2082                                         if (handler->visible == LB_SHOW) {
2083                                                 lb_update_visibility(old_common); /* To update visibility: Show --> Paused */
2084                                                 lb_update_visibility(common);   /* To update visibility: Paused --> Show */
2085                                         }
2086                                 } else {
2087                                         destroy_cb_info(cbinfo);
2088                                 }
2089                         }
2090                 }
2091         }
2092
2093         return ret;
2094 }
2095
2096 EAPI int livebox_click(struct livebox *handler, double x, double y)
2097 {
2098         struct packet *packet;
2099         double timestamp;
2100         int ret;
2101
2102         if (!handler || handler->state != CREATE) {
2103                 ErrPrint("Handler is invalid\n");
2104                 return LB_STATUS_ERROR_INVALID;
2105         }
2106
2107         if (!handler->common || handler->common->state != CREATE) {
2108                 ErrPrint("Handler is invalid\n");
2109                 return LB_STATUS_ERROR_INVALID;
2110         }
2111
2112         if (!handler->common->id) {
2113                 ErrPrint("Handler is not valid\n");
2114                 return LB_STATUS_ERROR_INVALID;
2115         }
2116
2117         if (handler->common->lb.auto_launch) {
2118 /*
2119                 service_h service;
2120
2121                 DbgPrint("AUTO_LAUNCH [%s]\n", handler->common->lb.auto_launch);
2122
2123                 ret = service_create(&service);
2124                 if (ret == SERVICE_ERROR_NONE) {
2125                         service_set_package(service, handler->common->lb.auto_launch);
2126                         service_send_launch_request(service, NULL, NULL);
2127                         service_destroy(service);
2128                 } else {
2129                         ErrPrint("Failed to launch an app %s (%d)\n", handler->common->lb.auto_launch, ret);
2130                 }
2131 */
2132                 ret = aul_launch_app(handler->common->lb.auto_launch, NULL);
2133                 if (ret <= 0) {
2134                         ErrPrint("Failed to launch an app %s (%d)\n", handler->common->lb.auto_launch, ret);
2135                 }
2136         }
2137
2138         timestamp = util_timestamp();
2139         DbgPrint("CLICKED: %lf\n", timestamp);
2140
2141         packet = packet_create_noack("clicked", "sssddd", handler->common->pkgname, handler->common->id, "clicked", timestamp, x, y);
2142         if (!packet) {
2143                 ErrPrint("Failed to build param\n");
2144                 return LB_STATUS_ERROR_FAULT;
2145         }
2146
2147         ret = master_rpc_request_only(handler, packet);
2148
2149         if (!handler->common->lb.mouse_event && (handler->common->lb.type == _LB_TYPE_BUFFER || handler->common->lb.type == _LB_TYPE_SCRIPT)) {
2150                 int ret; /* Shadow variable */
2151                 ret = send_mouse_event(handler, "lb_mouse_down", x * handler->common->lb.width, y * handler->common->lb.height);
2152                 if (ret < 0) {
2153                         ErrPrint("Failed to send Down: %d\n", ret);
2154                 }
2155
2156                 ret = send_mouse_event(handler, "lb_mouse_move", x * handler->common->lb.width, y * handler->common->lb.height);
2157                 if (ret < 0) {
2158                         ErrPrint("Failed to send Move: %d\n", ret);
2159                 }
2160
2161                 ret = send_mouse_event(handler, "lb_mouse_up", x * handler->common->lb.width, y * handler->common->lb.height);
2162                 if (ret < 0) {
2163                         ErrPrint("Failed to send Up: %d\n", ret);
2164                 }
2165         }
2166
2167         return ret;
2168 }
2169
2170 EAPI int livebox_has_pd(struct livebox *handler)
2171 {
2172         if (!handler || handler->state != CREATE) {
2173                 ErrPrint("Handler is invalid\n");
2174                 return LB_STATUS_ERROR_INVALID;
2175         }
2176
2177         if (!handler->common || handler->common->state != CREATE) {
2178                 ErrPrint("Handler is invalid\n");
2179                 return LB_STATUS_ERROR_INVALID;
2180         }
2181
2182         if (!handler->common->id) {
2183                 ErrPrint("Handler is not valid\n");
2184                 return LB_STATUS_ERROR_INVALID;
2185         }
2186
2187         return !!handler->common->pd.fb;
2188 }
2189
2190 EAPI int livebox_pd_is_created(struct livebox *handler)
2191 {
2192         if (!handler || handler->state != CREATE) {
2193                 ErrPrint("Handler is invalid\n");
2194                 return LB_STATUS_ERROR_INVALID;
2195         }
2196
2197         if (!handler->common || handler->common->state != CREATE) {
2198                 ErrPrint("Handler is invalid\n");
2199                 return LB_STATUS_ERROR_INVALID;
2200         }
2201
2202         if (!handler->common->pd.fb || !handler->common->id) {
2203                 ErrPrint("Handler is not valid\n");
2204                 return LB_STATUS_ERROR_INVALID;
2205         }
2206
2207         return handler->common->is_pd_created;
2208 }
2209
2210 EAPI int livebox_create_pd(struct livebox *handler, ret_cb_t cb, void *data)
2211 {
2212         return livebox_create_pd_with_position(handler, -1.0, -1.0, cb, data);
2213 }
2214
2215 static void turn_off_pd_destroyed_flag_cb(struct livebox *handler, int ret, void *data)
2216 {
2217         if (handler->common->request.pd_destroyed) {
2218                 ret_cb_t cb;
2219                 void *data;
2220
2221                 DbgPrint("pd_destroyed request is canceled\n");
2222                 handler->common->request.pd_destroyed = 0;
2223                 cb = handler->cbs.pd_destroyed.cb;
2224                 data = handler->cbs.pd_destroyed.data;
2225                 handler->cbs.pd_destroyed.cb = NULL;
2226                 handler->cbs.pd_destroyed.data = NULL;
2227
2228                 if (cb) {
2229                         cb(handler, ret, data);
2230                 }
2231         }
2232 }
2233
2234 EAPI int livebox_create_pd_with_position(struct livebox *handler, double x, double y, ret_cb_t cb, void *data)
2235 {
2236         struct packet *packet;
2237         int ret;
2238
2239         if (!handler || handler->state != CREATE) {
2240                 ErrPrint("Handler is invalid\n");
2241                 return LB_STATUS_ERROR_INVALID;
2242         }
2243
2244         if (!handler->common || handler->common->state != CREATE) {
2245                 ErrPrint("Handler is invalid\n");
2246                 return LB_STATUS_ERROR_INVALID;
2247         }
2248
2249         if (!handler->common->pd.fb || !handler->common->id) {
2250                 ErrPrint("Handler is not valid\n");
2251                 return LB_STATUS_ERROR_INVALID;
2252         }
2253
2254         /*!
2255          * \note
2256          * Only one handler can have a PD
2257          */
2258         if (handler->common->is_pd_created) {
2259                 DbgPrint("PD is already created\n");
2260                 return LB_STATUS_SUCCESS;
2261         }
2262
2263         if (handler->common->request.pd_created) {
2264                 ErrPrint("Previous request is not completed yet\n");
2265                 return LB_STATUS_ERROR_BUSY;
2266         }
2267
2268         /*!
2269          * \note
2270          * Turn off the pd_destroyed request flag
2271          */
2272         if (handler->common->request.pd_destroyed) {
2273                 if (job_add(handler, turn_off_pd_destroyed_flag_cb, LB_STATUS_ERROR_CANCEL, NULL) < 0) {
2274                         ErrPrint("Failed to add pd_destroyed job\n");
2275                 }
2276         }
2277
2278         packet = packet_create("create_pd", "ssdd", handler->common->pkgname, handler->common->id, x, y);
2279         if (!packet) {
2280                 ErrPrint("Failed to build param\n");
2281                 return LB_STATUS_ERROR_FAULT;
2282         }
2283
2284         if (!cb) {
2285                 cb = default_pd_created_cb;
2286         }
2287
2288         DbgPrint("PERF_DBOX\n");
2289         ret = master_rpc_async_request(handler, packet, 0, pd_create_cb, NULL);
2290         if (ret == LB_STATUS_SUCCESS) {
2291                 handler->cbs.pd_created.cb = cb;
2292                 handler->cbs.pd_created.data = data;
2293                 handler->common->request.pd_created = 1;
2294         }
2295
2296         return ret;
2297 }
2298
2299 EAPI int livebox_move_pd(struct livebox *handler, double x, double y)
2300 {
2301         struct packet *packet;
2302
2303         if (!handler || handler->state != CREATE) {
2304                 ErrPrint("Handler is invalid\n");
2305                 return LB_STATUS_ERROR_INVALID;
2306         }
2307
2308         if (!handler->common || handler->common->state != CREATE) {
2309                 ErrPrint("Handler is invalid\n");
2310                 return LB_STATUS_ERROR_INVALID;
2311         }
2312
2313         if (!handler->common->pd.fb || !handler->common->id) {
2314                 ErrPrint("Handler is not valid\n");
2315                 return LB_STATUS_ERROR_INVALID;
2316         }
2317
2318         if (!handler->common->is_pd_created) {
2319                 ErrPrint("PD is not created\n");
2320                 return LB_STATUS_ERROR_INVALID;
2321         }
2322
2323         packet = packet_create_noack("pd_move", "ssdd", handler->common->pkgname, handler->common->id, x, y);
2324         if (!packet) {
2325                 ErrPrint("Failed to build param\n");
2326                 return LB_STATUS_ERROR_FAULT;
2327         }
2328
2329         return master_rpc_request_only(handler, packet);
2330 }
2331
2332 EAPI int livebox_activate(const char *pkgname, ret_cb_t cb, void *data)
2333 {
2334         struct packet *packet;
2335         struct cb_info *cbinfo;
2336         int ret;
2337
2338         if (!pkgname) {
2339                 return LB_STATUS_ERROR_INVALID;
2340         }
2341
2342         packet = packet_create("activate_package", "s", pkgname);
2343         if (!packet) {
2344                 ErrPrint("Failed to build a param\n");
2345                 return LB_STATUS_ERROR_FAULT;
2346         }
2347
2348         cbinfo = create_cb_info(cb, data);
2349         if (!cbinfo) {
2350                 ErrPrint("Unable to create cbinfo\n");
2351                 packet_destroy(packet);
2352                 return LB_STATUS_ERROR_FAULT;
2353         }
2354
2355         ret = master_rpc_async_request(NULL, packet, 0, activated_cb, cbinfo);
2356         if (ret < 0) {
2357                 destroy_cb_info(cbinfo);
2358         }
2359
2360         return ret;
2361 }
2362
2363 static void turn_off_pd_created_flag_cb(struct livebox *handler, int ret, void *data)
2364 {
2365         if (handler->common->request.pd_created) {
2366                 ret_cb_t cb;
2367                 void *data;
2368
2369                 DbgPrint("pd_created request is canceled\n");
2370                 handler->common->request.pd_created = 0;
2371                 cb = handler->cbs.pd_created.cb;
2372                 data = handler->cbs.pd_created.data;
2373                 handler->cbs.pd_created.cb = NULL;
2374                 handler->cbs.pd_created.data = NULL;
2375
2376                 if (cb) {
2377                         cb(handler, ret, data);
2378                 }
2379         }
2380 }
2381
2382 EAPI int livebox_destroy_pd(struct livebox *handler, ret_cb_t cb, void *data)
2383 {
2384         struct packet *packet;
2385         struct cb_info *cbinfo;
2386         int ret;
2387
2388         if (!handler || handler->state != CREATE) {
2389                 ErrPrint("Handler is invalid\n");
2390                 return LB_STATUS_ERROR_INVALID;
2391         }
2392
2393         if (!handler->common || handler->common->state != CREATE) {
2394                 ErrPrint("Handler is invalid\n");
2395                 return LB_STATUS_ERROR_INVALID;
2396         }
2397
2398         if (!handler->common->pd.fb || !handler->common->id) {
2399                 ErrPrint("Handler is not valid\n");
2400                 return LB_STATUS_ERROR_INVALID;
2401         }
2402
2403         /*!
2404          * \FIXME
2405          * Replace the callback check code.
2406          * Use the flag instead of callback.
2407          * the flag should be in the ADT "common"
2408          */
2409         if (!handler->common->is_pd_created && !handler->common->request.pd_created) {
2410                 ErrPrint("PD is not created\n");
2411                 return LB_STATUS_ERROR_INVALID;
2412         }
2413
2414         if (handler->common->request.pd_destroyed) {
2415                 ErrPrint("PD destroy request is already sent\n");
2416                 return LB_STATUS_ERROR_ALREADY;
2417         }
2418
2419         /*!
2420          * \note
2421          * Disable the pd_created request flag
2422          */
2423         if (handler->common->request.pd_created) {
2424                 if (job_add(handler, turn_off_pd_created_flag_cb, LB_STATUS_ERROR_CANCEL, NULL) < 0) {
2425                         ErrPrint("Failed to add a new job\n");
2426                 }
2427         }
2428
2429         DbgPrint("[%s]\n", handler->common->pkgname);
2430
2431         packet = packet_create("destroy_pd", "ss", handler->common->pkgname, handler->common->id);
2432         if (!packet) {
2433                 ErrPrint("Failed to build a param\n");
2434                 return LB_STATUS_ERROR_FAULT;
2435         }
2436
2437         if (!cb) {
2438                 cb = default_pd_destroyed_cb;
2439         }
2440
2441         cbinfo = create_cb_info(cb, data);
2442         if (!cbinfo) {
2443                 packet_destroy(packet);
2444                 return LB_STATUS_ERROR_FAULT;
2445         }
2446
2447         ret = master_rpc_async_request(handler, packet, 0, pd_destroy_cb, cbinfo);
2448         if (ret < 0) {
2449                 destroy_cb_info(cbinfo);
2450         } else {
2451                 handler->common->request.pd_destroyed = 1;
2452         }
2453
2454         return ret;
2455 }
2456
2457 EAPI int livebox_access_event(struct livebox *handler, enum access_event_type type, double x, double y, ret_cb_t cb, void *data)
2458 {
2459         int w = 1;
2460         int h = 1;
2461         char cmd[32] = { '\0', };
2462         char *ptr = cmd;
2463         int ret;
2464
2465         if (!handler || handler->state != CREATE) {
2466                 ErrPrint("Handler is invalid\n");
2467                 return LB_STATUS_ERROR_INVALID;
2468         }
2469
2470         if (!handler->common || handler->common->state != CREATE) {
2471                 ErrPrint("Handler is invalid\n");
2472                 return LB_STATUS_ERROR_INVALID;
2473         }
2474
2475         if (!handler->common->id) {
2476                 ErrPrint("Handler is not valid\n");
2477                 return LB_STATUS_ERROR_INVALID;
2478         }
2479
2480         if (handler->common->request.access_event) {
2481                 ErrPrint("Previous access event is not yet done\n");
2482                 return LB_STATUS_ERROR_BUSY;
2483         }
2484
2485         if (type & ACCESS_EVENT_PD_MASK) {
2486                 if (!handler->common->is_pd_created) {
2487                         ErrPrint("PD is not created\n");
2488                         return LB_STATUS_ERROR_INVALID;
2489                 }
2490                 *ptr++ = 'p';
2491                 *ptr++ = 'd';
2492                 w = handler->common->pd.width;
2493                 h = handler->common->pd.height;
2494         } else if (type & ACCESS_EVENT_LB_MASK) {
2495                 *ptr++ = 'l';
2496                 *ptr++ = 'b';
2497                 w = handler->common->lb.width;
2498                 h = handler->common->lb.height;
2499         } else {
2500                 ErrPrint("Invalid event type\n");
2501                 return LB_STATUS_ERROR_INVALID;
2502         }
2503
2504         switch (type & ~ACCESS_EVENT_PD_MASK) {
2505         case ACCESS_EVENT_HIGHLIGHT:
2506                 strcpy(ptr, "_access_hl");
2507                 break;
2508         case ACCESS_EVENT_HIGHLIGHT_NEXT:
2509                 strcpy(ptr, "_access_hl_next");
2510                 break;
2511         case ACCESS_EVENT_HIGHLIGHT_PREV:
2512                 strcpy(ptr, "_access_hl_prev");
2513                 break;
2514         case ACCESS_EVENT_ACTIVATE:
2515                 strcpy(ptr, "_access_activate");
2516                 break;
2517         case ACCESS_EVENT_ACTION_DOWN:
2518                 strcpy(ptr, "_access_action_down");
2519                 break;
2520         case ACCESS_EVENT_ACTION_UP:
2521                 strcpy(ptr, "_access_action_up");
2522                 break;
2523         case ACCESS_EVENT_UNHIGHLIGHT:
2524                 strcpy(ptr, "_access_unhighlight");
2525                 break;
2526         case ACCESS_EVENT_SCROLL_DOWN:
2527                 strcpy(ptr, "_access_scroll_down");
2528                 break;
2529         case ACCESS_EVENT_SCROLL_MOVE:
2530                 strcpy(ptr, "_access_scroll_move");
2531                 break;
2532         case ACCESS_EVENT_SCROLL_UP:
2533                 strcpy(ptr, "_access_scroll_up");
2534                 break;
2535         default:
2536                 return LB_STATUS_ERROR_INVALID;
2537         }
2538
2539         if (!cb) {
2540                 cb = default_access_event_cb;
2541         }
2542
2543         ret = send_access_event(handler, cmd, x * w, y * h);
2544         if (ret == LB_STATUS_SUCCESS) {
2545                 handler->cbs.access_event.cb = cb;
2546                 handler->cbs.access_event.data = data;
2547                 handler->common->request.access_event = 1;
2548         }
2549
2550         return ret;
2551 }
2552
2553 EAPI int livebox_content_event(struct livebox *handler, enum content_event_type type, double x, double y)
2554 {
2555         return livebox_mouse_event(handler, type, x, y);
2556 }
2557
2558 EAPI int livebox_mouse_event(struct livebox *handler, enum content_event_type type, double x, double y)
2559 {
2560         int w = 1;
2561         int h = 1;
2562         char cmd[32] = { '\0', };
2563         char *ptr = cmd;
2564
2565         if (!handler || handler->state != CREATE) {
2566                 ErrPrint("Handler is invalid\n");
2567                 return LB_STATUS_ERROR_INVALID;
2568         }
2569
2570         if (!handler->common || handler->common->state != CREATE) {
2571                 ErrPrint("Handler is invalid\n");
2572                 return LB_STATUS_ERROR_INVALID;
2573         }
2574
2575         if (!handler->common->id) {
2576                 ErrPrint("Handler is not valid\n");
2577                 return LB_STATUS_ERROR_INVALID;
2578         }
2579
2580         if (!(type & CONTENT_EVENT_MOUSE_MASK)) {
2581                 ErrPrint("Invalid content event is used\n");
2582                 return LB_STATUS_ERROR_INVALID;
2583         }
2584
2585         if (type & CONTENT_EVENT_PD_MASK) {
2586                 int flag = 1;
2587
2588                 if (!handler->common->is_pd_created) {
2589                         ErrPrint("PD is not created\n");
2590                         return LB_STATUS_ERROR_INVALID;
2591                 }
2592
2593                 if (!handler->common->pd.fb) {
2594                         ErrPrint("Handler is not valid\n");
2595                         return LB_STATUS_ERROR_INVALID;
2596                 }
2597
2598                 if (type & CONTENT_EVENT_MOUSE_MOVE) {
2599                         if (fabs(x - handler->common->pd.x) < conf_event_filter() && fabs(y - handler->common->pd.y) < conf_event_filter()) {
2600                                 return LB_STATUS_ERROR_BUSY;
2601                         }
2602                 } else if (type & CONTENT_EVENT_MOUSE_SET) {
2603                         flag = 0;
2604                 }
2605
2606                 if (flag) {
2607                         w = handler->common->pd.width;
2608                         h = handler->common->pd.height;
2609                         handler->common->pd.x = x;
2610                         handler->common->pd.y = y;
2611                 }
2612                 *ptr++ = 'p';
2613                 *ptr++ = 'd';
2614         } else if (type & CONTENT_EVENT_LB_MASK) {
2615                 int flag = 1;
2616
2617                 if (!handler->common->lb.mouse_event) {
2618                         return LB_STATUS_ERROR_INVALID;
2619                 }
2620
2621                 if (!handler->common->lb.fb) {
2622                         ErrPrint("Handler is not valid\n");
2623                         return LB_STATUS_ERROR_INVALID;
2624                 }
2625
2626                 if (type & CONTENT_EVENT_MOUSE_MOVE) {
2627                         if (fabs(x - handler->common->lb.x) < conf_event_filter() && fabs(y - handler->common->lb.y) < conf_event_filter()) {
2628                                 return LB_STATUS_ERROR_BUSY;
2629                         }
2630                 } else if (type & CONTENT_EVENT_MOUSE_SET) {
2631                         flag = 0;
2632                 }
2633
2634                 if (flag) {
2635                         w = handler->common->lb.width;
2636                         h = handler->common->lb.height;
2637                         handler->common->lb.x = x;
2638                         handler->common->lb.y = y;
2639                 }
2640                 *ptr++ = 'l';
2641                 *ptr++ = 'b';
2642         } else {
2643                 ErrPrint("Invalid event type\n");
2644                 return LB_STATUS_ERROR_INVALID;
2645         }
2646
2647         /*!
2648          * Must be short than 29 bytes.
2649          */
2650         switch ((type & ~(CONTENT_EVENT_PD_MASK | CONTENT_EVENT_LB_MASK))) {
2651         case CONTENT_EVENT_MOUSE_ENTER | CONTENT_EVENT_MOUSE_MASK:
2652                 strcpy(ptr, "_mouse_enter");
2653                 break;
2654         case CONTENT_EVENT_MOUSE_LEAVE | CONTENT_EVENT_MOUSE_MASK:
2655                 strcpy(ptr, "_mouse_leave");
2656                 break;
2657         case CONTENT_EVENT_MOUSE_UP | CONTENT_EVENT_MOUSE_MASK:
2658                 strcpy(ptr, "_mouse_up");
2659                 break;
2660         case CONTENT_EVENT_MOUSE_DOWN | CONTENT_EVENT_MOUSE_MASK:
2661                 strcpy(ptr, "_mouse_down");
2662                 break;
2663         case CONTENT_EVENT_MOUSE_MOVE | CONTENT_EVENT_MOUSE_MASK:
2664                 strcpy(ptr, "_mouse_move");
2665                 break;
2666         case CONTENT_EVENT_MOUSE_SET | CONTENT_EVENT_MOUSE_MASK:
2667                 strcpy(ptr, "_mouse_set");
2668                 break;
2669         case CONTENT_EVENT_MOUSE_UNSET | CONTENT_EVENT_MOUSE_MASK:
2670                 strcpy(ptr, "_mouse_unset");
2671                 break;
2672         default:
2673                 ErrPrint("Invalid event type\n");
2674                 return LB_STATUS_ERROR_INVALID;
2675         }
2676
2677         return send_mouse_event(handler, cmd, x * w, y * h);
2678 }
2679
2680 EAPI int livebox_key_event(struct livebox *handler, enum content_event_type type, unsigned int keycode, ret_cb_t cb, void *data)
2681 {
2682         char cmd[32] = { '\0', };
2683         char *ptr = cmd;
2684         int ret;
2685
2686         if (!handler || handler->state != CREATE) {
2687                 ErrPrint("Handler is invalid\n");
2688                 return LB_STATUS_ERROR_INVALID;
2689         }
2690
2691         if (!handler->common || handler->common->state != CREATE) {
2692                 ErrPrint("Handler is invalid\n");
2693                 return LB_STATUS_ERROR_INVALID;
2694         }
2695
2696         if (!handler->common->id) {
2697                 ErrPrint("Handler is not valid\n");
2698                 return LB_STATUS_ERROR_INVALID;
2699         }
2700
2701         if (!(type & CONTENT_EVENT_KEY_MASK)) {
2702                 ErrPrint("Invalid key event is used\n");
2703                 return LB_STATUS_ERROR_INVALID;
2704         }
2705
2706         if (handler->common->request.key_event) {
2707                 ErrPrint("Previous key event is not completed yet\n");
2708                 return LB_STATUS_ERROR_BUSY;
2709         }
2710
2711         if (type & CONTENT_EVENT_PD_MASK) {
2712                 if (!handler->common->is_pd_created) {
2713                         ErrPrint("PD is not created\n");
2714                         return LB_STATUS_ERROR_INVALID;
2715                 }
2716
2717                 if (!handler->common->pd.fb) {
2718                         ErrPrint("Handler is not valid\n");
2719                         return LB_STATUS_ERROR_INVALID;
2720                 }
2721
2722                 if (type & CONTENT_EVENT_KEY_DOWN) {
2723                         /*!
2724                          * \TODO
2725                          * filtering the reproduced events if it is too fast
2726                          */
2727                 } else if (type & CONTENT_EVENT_KEY_SET) {
2728                         /*!
2729                          * \TODO
2730                          * What can I do for this case?
2731                          */
2732                 }
2733
2734                 *ptr++ = 'p';
2735                 *ptr++ = 'd';
2736         } else if (type & CONTENT_EVENT_LB_MASK) {
2737                 if (!handler->common->lb.mouse_event) {
2738                         return LB_STATUS_ERROR_INVALID;
2739                 }
2740
2741                 if (!handler->common->lb.fb) {
2742                         ErrPrint("Handler is not valid\n");
2743                         return LB_STATUS_ERROR_INVALID;
2744                 }
2745
2746                 if (type & CONTENT_EVENT_KEY_DOWN) {
2747                         /*!
2748                          * \TODO
2749                          * filtering the reproduced events if it is too fast
2750                          */
2751                 } else if (type & CONTENT_EVENT_KEY_SET) {
2752                         /*!
2753                          * What can I do for this case?
2754                          */
2755                 }
2756
2757                 *ptr++ = 'l';
2758                 *ptr++ = 'b';
2759         } else {
2760                 ErrPrint("Invalid event type\n");
2761                 return LB_STATUS_ERROR_INVALID;
2762         }
2763
2764         /*!
2765          * Must be short than 29 bytes.
2766          */
2767         switch ((type & ~(CONTENT_EVENT_PD_MASK | CONTENT_EVENT_LB_MASK))) {
2768         case CONTENT_EVENT_KEY_FOCUS_IN | CONTENT_EVENT_KEY_MASK:
2769                 strcpy(ptr, "_key_focus_in");
2770                 break;
2771         case CONTENT_EVENT_KEY_FOCUS_OUT | CONTENT_EVENT_KEY_MASK:
2772                 strcpy(ptr, "_key_focus_out");
2773                 break;
2774         case CONTENT_EVENT_KEY_UP | CONTENT_EVENT_KEY_MASK:
2775                 strcpy(ptr, "_key_up");
2776                 break;
2777         case CONTENT_EVENT_KEY_DOWN | CONTENT_EVENT_KEY_MASK:
2778                 strcpy(ptr, "_key_down");
2779                 break;
2780         case CONTENT_EVENT_KEY_SET | CONTENT_EVENT_KEY_MASK:
2781                 strcpy(ptr, "_key_set");
2782                 break;
2783         case CONTENT_EVENT_KEY_UNSET | CONTENT_EVENT_KEY_MASK:
2784                 strcpy(ptr, "_key_unset");
2785                 break;
2786         default:
2787                 ErrPrint("Invalid event type\n");
2788                 return LB_STATUS_ERROR_INVALID;
2789         }
2790
2791         if (!cb) {
2792                 cb = default_key_event_cb;
2793         }
2794
2795         ret = send_key_event(handler, cmd, keycode);
2796         if (ret == LB_STATUS_SUCCESS) {
2797                 handler->cbs.key_event.cb = cb;
2798                 handler->cbs.key_event.data = data;
2799                 handler->common->request.key_event = 1;
2800         }
2801
2802         return ret;
2803 }
2804
2805 EAPI const char *livebox_filename(struct livebox *handler)
2806 {
2807         if (!handler || handler->state != CREATE) {
2808                 ErrPrint("Handler is invalid\n");
2809                 return NULL;
2810         }
2811
2812         if (!handler->common || handler->common->state != CREATE) {
2813                 ErrPrint("Handler is invalid\n");
2814                 return NULL;
2815         }
2816
2817         if (!handler->common->id) {
2818                 ErrPrint("Handler is not valid\n");
2819                 return NULL;
2820         }
2821
2822         if (handler->common->filename) {
2823                 return handler->common->filename;
2824         }
2825
2826         /* Oooops */
2827         return util_uri_to_path(handler->common->id);
2828 }
2829
2830 EAPI int livebox_get_pdsize(struct livebox *handler, int *w, int *h)
2831 {
2832         int _w;
2833         int _h;
2834
2835         if (!handler || handler->state != CREATE) {
2836                 ErrPrint("Handler is invalid\n");
2837                 return LB_STATUS_ERROR_INVALID;
2838         }
2839
2840         if (!handler->common || handler->common->state != CREATE) {
2841                 ErrPrint("Handler is invalid\n");
2842                 return LB_STATUS_ERROR_INVALID;
2843         }
2844
2845         if (!handler->common->id) {
2846                 ErrPrint("Handler is not valid\n");
2847                 return LB_STATUS_ERROR_INVALID;
2848         }
2849
2850         if (!w) {
2851                 w = &_w;
2852         }
2853         if (!h) {
2854                 h = &_h;
2855         }
2856
2857         if (!handler->common->is_pd_created) {
2858                 *w = handler->common->pd.default_width;
2859                 *h = handler->common->pd.default_height;
2860         } else {
2861                 *w = handler->common->pd.width;
2862                 *h = handler->common->pd.height;
2863         }
2864
2865         return LB_STATUS_SUCCESS;
2866 }
2867
2868 EAPI int livebox_size(struct livebox *handler)
2869 {
2870         int w;
2871         int h;
2872
2873         if (!handler || handler->state != CREATE) {
2874                 ErrPrint("Handler is invalid\n");
2875                 return LB_STATUS_ERROR_INVALID;
2876         }
2877
2878         if (!handler->common || handler->common->state != CREATE) {
2879                 ErrPrint("Handler is invalid\n");
2880                 return LB_STATUS_ERROR_INVALID;
2881         }
2882
2883         if (!handler->common->id) {
2884                 ErrPrint("Handler is not valid\n");
2885                 return LB_STATUS_ERROR_INVALID;
2886         }
2887
2888         w = handler->common->lb.width;
2889         h = handler->common->lb.height;
2890
2891         switch (handler->common->lb.type) {
2892         case _LB_TYPE_BUFFER:
2893         case _LB_TYPE_SCRIPT:
2894                 if (!fb_is_created(handler->common->lb.fb)) {
2895                         w = 0;
2896                         h = 0;
2897                 }
2898                 break;
2899         default:
2900                 break;
2901         }
2902
2903         return livebox_service_size_type(w, h);
2904 }
2905
2906 EAPI int livebox_set_group(struct livebox *handler, const char *cluster, const char *category, ret_cb_t cb, void *data)
2907 {
2908         struct packet *packet;
2909         int ret;
2910
2911         if (!handler) {
2912                 ErrPrint("Handler is NIL\n");
2913                 return LB_STATUS_ERROR_INVALID;
2914         }
2915
2916         if (!cluster || !category || handler->state != CREATE) {
2917                 ErrPrint("Invalid argument\n");
2918                 return LB_STATUS_ERROR_INVALID;
2919         }
2920
2921         if (!handler->common || handler->common->state != CREATE) {
2922                 ErrPrint("Invalid argument\n");
2923                 return LB_STATUS_ERROR_INVALID;
2924         }
2925
2926         if (!handler->common->id) {
2927                 ErrPrint("Invalid argument\n");
2928                 return LB_STATUS_ERROR_INVALID;
2929         }
2930
2931         if (handler->common->request.group_changed) {
2932                 ErrPrint("Previous group changing request is not finished yet\n");
2933                 return LB_STATUS_ERROR_BUSY;
2934         }
2935
2936         if (!handler->common->is_user) {
2937                 ErrPrint("CA Livebox is not able to change the group\n");
2938                 return LB_STATUS_ERROR_PERMISSION;
2939         }
2940
2941         if (!strcmp(handler->common->cluster, cluster) && !strcmp(handler->common->category, category)) {
2942                 DbgPrint("No changes\n");
2943                 return LB_STATUS_ERROR_ALREADY;
2944         }
2945
2946         packet = packet_create("change_group", "ssss", handler->common->pkgname, handler->common->id, cluster, category);
2947         if (!packet) {
2948                 ErrPrint("Failed to build a param\n");
2949                 return LB_STATUS_ERROR_FAULT;
2950         }
2951
2952         if (!cb) {
2953                 cb = default_group_changed_cb;
2954         }
2955
2956         ret = master_rpc_async_request(handler, packet, 0, set_group_ret_cb, NULL);
2957         if (ret == LB_STATUS_SUCCESS) {
2958                 handler->cbs.group_changed.cb = cb;
2959                 handler->cbs.group_changed.data = data; 
2960                 handler->common->request.group_changed = 1;
2961         }
2962
2963         return ret;
2964 }
2965
2966 EAPI int livebox_get_group(struct livebox *handler, const char **cluster, const char **category)
2967 {
2968         if (!handler) {
2969                 ErrPrint("Handler is NIL\n");
2970                 return LB_STATUS_ERROR_INVALID;
2971         }
2972
2973         if (!cluster || !category || handler->state != CREATE) {
2974                 ErrPrint("Invalid argument\n");
2975                 return LB_STATUS_ERROR_INVALID;
2976         }
2977
2978         if (!handler->common || handler->common->state != CREATE) {
2979                 ErrPrint("Invalid argument\n");
2980                 return LB_STATUS_ERROR_INVALID;
2981         }
2982
2983         if (!handler->common->id) {
2984                 ErrPrint("Invalid argument\n");
2985                 return LB_STATUS_ERROR_INVALID;
2986         }
2987
2988         *cluster = handler->common->cluster;
2989         *category = handler->common->category;
2990         return LB_STATUS_SUCCESS;
2991 }
2992
2993 EAPI int livebox_get_supported_sizes(struct livebox *handler, int *cnt, int *size_list)
2994 {
2995         register int i;
2996         register int j;
2997
2998         if (!handler || !size_list) {
2999                 ErrPrint("Invalid argument, handler(%p), size_list(%p)\n", handler, size_list);
3000                 return LB_STATUS_ERROR_INVALID;
3001         }
3002
3003         if (!cnt || handler->state != CREATE) {
3004                 ErrPrint("Handler is not valid\n");
3005                 return LB_STATUS_ERROR_INVALID;
3006         }
3007
3008         if (!handler->common || handler->common->state != CREATE) {
3009                 ErrPrint("Handler is not valid\n");
3010                 return LB_STATUS_ERROR_INVALID;
3011         }
3012
3013         if (!handler->common->id) {
3014                 ErrPrint("Handler is not valid\n");
3015                 return LB_STATUS_ERROR_INVALID;
3016         }
3017
3018         for (j = i = 0; i < NR_OF_SIZE_LIST; i++) {
3019                 if (handler->common->lb.size_list & (0x01 << i)) {
3020                         if (j == *cnt) {
3021                                 break;
3022                         }
3023
3024                         size_list[j++] = (0x01 << i);
3025                 }
3026         }
3027
3028         *cnt = j;
3029         return LB_STATUS_SUCCESS;
3030 }
3031
3032 EAPI const char *livebox_pkgname(struct livebox *handler)
3033 {
3034         if (!handler) {
3035                 ErrPrint("Handler is NIL\n");
3036                 return NULL;
3037         }
3038
3039         if (handler->state != CREATE) {
3040                 ErrPrint("Handler is not valid\n");
3041                 return NULL;
3042         }
3043
3044         if (!handler->common || handler->common->state != CREATE) {
3045                 ErrPrint("Handler is not valid\n");
3046                 return NULL;
3047         }
3048
3049         return handler->common->pkgname;
3050 }
3051
3052 EAPI double livebox_priority(struct livebox *handler)
3053 {
3054         if (!handler || handler->state != CREATE) {
3055                 ErrPrint("Handler is invalid\n");
3056                 return -1.0f;
3057         }
3058
3059         if (!handler->common || handler->common->state != CREATE) {
3060                 ErrPrint("Handler is invalid\n");
3061                 return -1.0f;
3062         }
3063
3064         if (!handler->common->id) {
3065                 ErrPrint("Handler is not valid (%p)\n", handler);
3066                 return -1.0f;
3067         }
3068
3069         return handler->common->lb.priority;
3070 }
3071
3072 EAPI int livebox_delete_cluster(const char *cluster, ret_cb_t cb, void *data)
3073 {
3074         struct packet *packet;
3075         struct cb_info *cbinfo;
3076         int ret;
3077
3078         packet = packet_create("delete_cluster", "s", cluster);
3079         if (!packet) {
3080                 ErrPrint("Failed to build a param\n");
3081                 return LB_STATUS_ERROR_FAULT;
3082         }
3083
3084         cbinfo = create_cb_info(cb, data);
3085         if (!cbinfo) {
3086                 packet_destroy(packet);
3087                 return LB_STATUS_ERROR_FAULT;
3088         }
3089
3090         ret = master_rpc_async_request(NULL, packet, 0, delete_cluster_cb, cbinfo);
3091         if (ret < 0) {
3092                 destroy_cb_info(cbinfo);
3093         }
3094
3095         return ret;
3096 }
3097
3098 EAPI int livebox_delete_category(const char *cluster, const char *category, ret_cb_t cb, void *data)
3099 {
3100         struct packet *packet;
3101         struct cb_info *cbinfo;
3102         int ret;
3103
3104         packet = packet_create("delete_category", "ss", cluster, category);
3105         if (!packet) {
3106                 ErrPrint("Failed to build a param\n");
3107                 return LB_STATUS_ERROR_FAULT;
3108         }
3109
3110         cbinfo = create_cb_info(cb, data);
3111         if (!cbinfo) {
3112                 packet_destroy(packet);
3113                 return LB_STATUS_ERROR_FAULT;
3114         }
3115
3116         ret = master_rpc_async_request(NULL, packet, 0, delete_category_cb, cbinfo);
3117         if (ret < 0) {
3118                 destroy_cb_info(cbinfo);
3119         }
3120
3121         return ret;
3122 }
3123
3124 EAPI enum livebox_lb_type livebox_lb_type(struct livebox *handler)
3125 {
3126         if (!handler || handler->state != CREATE) {
3127                 ErrPrint("Handler is invalid\n");
3128                 return LB_TYPE_INVALID;
3129         }
3130
3131         if (!handler->common || handler->common->state != CREATE) {
3132                 ErrPrint("Handler is invalid\n");
3133                 return LB_TYPE_INVALID;
3134         }
3135
3136         if (!handler->common->id) {
3137                 ErrPrint("Handler is not valid\n");
3138                 return LB_TYPE_INVALID;
3139         }
3140
3141         switch (handler->common->lb.type) {
3142         case _LB_TYPE_FILE:
3143                 return LB_TYPE_IMAGE;
3144         case _LB_TYPE_BUFFER:
3145         case _LB_TYPE_SCRIPT:
3146                 {
3147                         const char *id;
3148                         id = fb_id(handler->common->lb.fb);
3149                         if (id && !strncasecmp(id, SCHEMA_PIXMAP, strlen(SCHEMA_PIXMAP))) {
3150                                 return LB_TYPE_PIXMAP;
3151                         }
3152                 }
3153                 return LB_TYPE_BUFFER;
3154         case _LB_TYPE_TEXT:
3155                 return LB_TYPE_TEXT;
3156         default:
3157                 break;
3158         }
3159
3160         return LB_TYPE_INVALID;
3161 }
3162
3163 EAPI enum livebox_pd_type livebox_pd_type(struct livebox *handler)
3164 {
3165         if (!handler || handler->state != CREATE) {
3166                 ErrPrint("Handler is invalid\n");
3167                 return PD_TYPE_INVALID;
3168         }
3169
3170         if (!handler->common || handler->common->state != CREATE) {
3171                 ErrPrint("Handler is invalid\n");
3172                 return PD_TYPE_INVALID;
3173         }
3174
3175         if (!handler->common->id) {
3176                 ErrPrint("Handler is not valid\n");
3177                 return PD_TYPE_INVALID;
3178         }
3179
3180         switch (handler->common->pd.type) {
3181         case _PD_TYPE_TEXT:
3182                 return PD_TYPE_TEXT;
3183         case _PD_TYPE_BUFFER:
3184         case _PD_TYPE_SCRIPT:
3185                 {
3186                         const char *id;
3187                         id = fb_id(handler->common->pd.fb);
3188                         if (id && !strncasecmp(id, SCHEMA_PIXMAP, strlen(SCHEMA_PIXMAP))) {
3189                                 return PD_TYPE_PIXMAP;
3190                         }
3191                 }
3192                 return PD_TYPE_BUFFER;
3193         default:
3194                 break;
3195         }
3196
3197         return PD_TYPE_INVALID;
3198 }
3199
3200 EAPI int livebox_set_pd_text_handler(struct livebox *handler, struct livebox_script_operators *ops)
3201 {
3202         if (!handler) {
3203                 ErrPrint("Handler is NIL\n");
3204                 return LB_STATUS_ERROR_INVALID;
3205         }
3206
3207         if (handler->state != CREATE) {
3208                 ErrPrint("Handler is not valid\n");
3209                 return LB_STATUS_ERROR_INVALID;
3210         }
3211
3212         memcpy(&handler->cbs.pd_ops, ops, sizeof(*ops));
3213         return LB_STATUS_SUCCESS;
3214 }
3215
3216 EAPI int livebox_set_text_handler(struct livebox *handler, struct livebox_script_operators *ops)
3217 {
3218         if (!handler) {
3219                 ErrPrint("Handler is NIL\n");
3220                 return LB_STATUS_ERROR_INVALID;
3221         }
3222
3223         if (handler->state != CREATE) {
3224                 ErrPrint("Handler is not valid\n");
3225                 return LB_STATUS_ERROR_INVALID;
3226         }
3227
3228         memcpy(&handler->cbs.lb_ops, ops, sizeof(*ops));
3229         return LB_STATUS_SUCCESS;
3230 }
3231
3232 EAPI int livebox_acquire_lb_pixmap(struct livebox *handler, ret_cb_t cb, void *data)
3233 {
3234         if (!handler || handler->state != CREATE) {
3235                 ErrPrint("Handler is invalid\n");
3236                 return LB_STATUS_ERROR_INVALID;
3237         }
3238
3239         if (!handler->common || handler->common->state != CREATE) {
3240                 ErrPrint("Handler is invalid\n");
3241                 return LB_STATUS_ERROR_INVALID;
3242         }
3243
3244         if (!handler->common->id) {
3245                 ErrPrint("Invalid handle\n");
3246                 return LB_STATUS_ERROR_INVALID;
3247         }
3248
3249         if (handler->common->lb.type != _LB_TYPE_SCRIPT && handler->common->lb.type != _LB_TYPE_BUFFER) {
3250                 ErrPrint("Handler is not valid type\n");
3251                 return LB_STATUS_ERROR_INVALID;
3252         }
3253
3254         return lb_acquire_lb_pixmap(handler, cb, data);
3255 }
3256
3257 EAPI int livebox_release_lb_pixmap(struct livebox *handler, int pixmap)
3258 {
3259         struct packet *packet;
3260
3261         if (!handler || pixmap == 0 || handler->state != CREATE) {
3262                 ErrPrint("Handler is invalid [%d]\n", pixmap);
3263                 return LB_STATUS_ERROR_INVALID;
3264         }
3265
3266         if (!handler->common || handler->common->state != CREATE) {
3267                 ErrPrint("Handler is invalid\n");
3268                 return LB_STATUS_ERROR_INVALID;
3269         }
3270
3271         if (!handler->common->id) {
3272                 ErrPrint("Invalid handle\n");
3273                 return LB_STATUS_ERROR_INVALID;
3274         }
3275
3276         if (handler->common->lb.type != _LB_TYPE_SCRIPT && handler->common->lb.type != _LB_TYPE_BUFFER) {
3277                 ErrPrint("Handler is not valid type\n");
3278                 return LB_STATUS_ERROR_INVALID;
3279         }
3280
3281         packet = packet_create_noack("lb_release_pixmap", "ssi", handler->common->pkgname, handler->common->id, pixmap);
3282         if (!packet) {
3283                 ErrPrint("Failed to build a param\n");
3284                 return LB_STATUS_ERROR_INVALID;
3285         }
3286
3287         return master_rpc_request_only(handler, packet);
3288 }
3289
3290 EAPI int livebox_acquire_pd_pixmap(struct livebox *handler, ret_cb_t cb, void *data)
3291 {
3292         if (!handler || handler->state != CREATE) {
3293                 ErrPrint("Handler is invalid\n");
3294                 return LB_STATUS_ERROR_INVALID;
3295         }
3296
3297         if (!handler->common || handler->common->state != CREATE) {
3298                 ErrPrint("Handler is invalid\n");
3299                 return LB_STATUS_ERROR_INVALID;
3300         }
3301
3302         if (!handler->common->id) {
3303                 ErrPrint("Invalid handle\n");
3304                 return LB_STATUS_ERROR_INVALID;
3305         }
3306
3307         if (handler->common->pd.type != _PD_TYPE_SCRIPT && handler->common->pd.type != _PD_TYPE_BUFFER) {
3308                 ErrPrint("Handler is not valid type\n");
3309                 return LB_STATUS_ERROR_INVALID;
3310         }
3311
3312         return lb_acquire_pd_pixmap(handler, cb, data);
3313 }
3314
3315 EAPI int livebox_pd_pixmap(const struct livebox *handler)
3316 {
3317         const char *id;
3318         int pixmap = 0;
3319
3320         if (!handler || handler->state != CREATE) {
3321                 ErrPrint("Handler is invalid\n");
3322                 return 0;
3323         }
3324
3325         if (!handler->common || handler->common->state != CREATE) {
3326                 ErrPrint("Handler is invalid\n");
3327                 return 0;
3328         }
3329
3330         if (!handler->common->id) {
3331                 ErrPrint("Invalid handler\n");
3332                 return 0;
3333         }
3334
3335         if (handler->common->pd.type != _PD_TYPE_SCRIPT && handler->common->pd.type != _PD_TYPE_BUFFER) {
3336                 ErrPrint("Invalid handler\n");
3337                 return 0;
3338         }
3339
3340         id = fb_id(handler->common->pd.fb);
3341         if (id && sscanf(id, SCHEMA_PIXMAP "%u", (unsigned int *)&pixmap) != 1) {
3342                 ErrPrint("PIXMAP Id is not valid\n");
3343                 return 0;
3344         }
3345
3346         return pixmap;
3347 }
3348
3349 EAPI int livebox_lb_pixmap(const struct livebox *handler)
3350 {
3351         const char *id;
3352         int pixmap = 0;
3353
3354         if (!handler || handler->state != CREATE) {
3355                 ErrPrint("Handler is invalid\n");
3356                 return 0;
3357         }
3358
3359         if (!handler->common || handler->common->state != CREATE) {
3360                 ErrPrint("Handler is invalid\n");
3361                 return 0;
3362         }
3363
3364         if (!handler->common->id) {
3365                 ErrPrint("Invalid handler\n");
3366                 return 0;
3367         }
3368
3369         if (handler->common->lb.type != _LB_TYPE_SCRIPT && handler->common->lb.type != _LB_TYPE_BUFFER) {
3370                 ErrPrint("Invalid handler\n");
3371                 return 0;
3372         }
3373
3374         id = fb_id(handler->common->lb.fb);
3375         if (id && sscanf(id, SCHEMA_PIXMAP "%u", (unsigned int *)&pixmap) != 1) {
3376                 ErrPrint("PIXMAP Id is not valid\n");
3377                 return 0;
3378         }
3379
3380         return pixmap;
3381 }
3382
3383 EAPI int livebox_release_pd_pixmap(struct livebox *handler, int pixmap)
3384 {
3385         struct packet *packet;
3386
3387         if (!handler || pixmap == 0 || handler->state != CREATE) {
3388                 ErrPrint("Handler is invalid [%d]\n", pixmap);
3389                 return LB_STATUS_ERROR_INVALID;
3390         }
3391
3392         if (!handler->common || handler->common->state != CREATE) {
3393                 ErrPrint("Handler is invalid\n");
3394                 return LB_STATUS_ERROR_INVALID;
3395         }
3396
3397         if (!handler->common->id) {
3398                 ErrPrint("Invalid handle\n");
3399                 return LB_STATUS_ERROR_INVALID;
3400         }
3401
3402         if (handler->common->pd.type != _PD_TYPE_SCRIPT && handler->common->pd.type != _PD_TYPE_BUFFER) {
3403                 ErrPrint("Handler is not valid type\n");
3404                 return LB_STATUS_ERROR_INVALID;
3405         }
3406
3407         packet = packet_create_noack("pd_release_pixmap", "ssi", handler->common->pkgname, handler->common->id, pixmap);
3408         if (!packet) {
3409                 ErrPrint("Failed to build a param\n");
3410                 return LB_STATUS_ERROR_FAULT;
3411         }
3412
3413         return master_rpc_request_only(handler, packet);
3414 }
3415
3416 EAPI void *livebox_acquire_fb(struct livebox *handler)
3417 {
3418         if (!handler || handler->state != CREATE) {
3419                 ErrPrint("Handler is invalid\n");
3420                 return NULL;
3421         }
3422
3423         if (!handler->common || handler->common->state != CREATE) {
3424                 ErrPrint("Handler is invalid\n");
3425                 return NULL;
3426         }
3427
3428         if (!handler->common->id) {
3429                 ErrPrint("Invalid handle\n");
3430                 return NULL;
3431         }
3432
3433         if (handler->common->lb.type != _LB_TYPE_SCRIPT && handler->common->lb.type != _LB_TYPE_BUFFER) {
3434                 ErrPrint("Handler is not valid type\n");
3435                 return NULL;
3436         }
3437
3438         return fb_acquire_buffer(handler->common->lb.fb);
3439 }
3440
3441 EAPI int livebox_release_fb(void *buffer)
3442 {
3443         return fb_release_buffer(buffer);
3444 }
3445
3446 EAPI int livebox_fb_refcnt(void *buffer)
3447 {
3448         return fb_refcnt(buffer);
3449 }
3450
3451 EAPI void *livebox_acquire_pdfb(struct livebox *handler)
3452 {
3453         if (!handler || handler->state != CREATE) {
3454                 ErrPrint("Handler is invalid\n");
3455                 return NULL;
3456         }
3457
3458         if (!handler->common || handler->common->state != CREATE) {
3459                 ErrPrint("Handler is invalid\n");
3460                 return NULL;
3461         }
3462
3463         if (!handler->common->id) {
3464                 ErrPrint("Invalid handler\n");
3465                 return NULL;
3466         }
3467
3468         if (handler->common->pd.type != _PD_TYPE_SCRIPT && handler->common->pd.type != _PD_TYPE_BUFFER) {
3469                 ErrPrint("Handler is not valid type\n");
3470                 return NULL;
3471         }
3472
3473         return fb_acquire_buffer(handler->common->pd.fb);
3474 }
3475
3476 EAPI int livebox_release_pdfb(void *buffer)
3477 {
3478         return fb_release_buffer(buffer);
3479 }
3480
3481 EAPI int livebox_pdfb_refcnt(void *buffer)
3482 {
3483         return fb_refcnt(buffer);
3484 }
3485
3486 EAPI int livebox_pdfb_bufsz(struct livebox *handler)
3487 {
3488         if (!handler || handler->state != CREATE) {
3489                 ErrPrint("Handler is invalid\n");
3490                 return LB_STATUS_ERROR_INVALID;
3491         }
3492
3493         if (!handler->common || handler->common->state != CREATE) {
3494                 ErrPrint("Handler is invalid\n");
3495                 return LB_STATUS_ERROR_INVALID;
3496         }
3497
3498         if (!handler->common->id) {
3499                 ErrPrint("Invalid handler\n");
3500                 return LB_STATUS_ERROR_INVALID;
3501         }
3502
3503         return fb_size(handler->common->pd.fb);
3504 }
3505
3506 EAPI int livebox_lbfb_bufsz(struct livebox *handler)
3507 {
3508         if (!handler || handler->state != CREATE) {
3509                 ErrPrint("Handler is invalid\n");
3510                 return LB_STATUS_ERROR_INVALID;
3511         }
3512
3513         if (!handler->common || handler->common->state != CREATE) {
3514                 ErrPrint("Handler is invalid\n");
3515                 return LB_STATUS_ERROR_INVALID;
3516         }
3517
3518         if (!handler->common->id) {
3519                 ErrPrint("Invalid handler\n");
3520                 return LB_STATUS_ERROR_INVALID;
3521         }
3522
3523         return fb_size(handler->common->lb.fb);
3524 }
3525
3526 EAPI int livebox_is_user(struct livebox *handler)
3527 {
3528         if (!handler || handler->state != CREATE) {
3529                 ErrPrint("Handler is invalid\n");
3530                 return LB_STATUS_ERROR_INVALID;
3531         }
3532
3533         if (!handler->common || handler->common->state != CREATE) {
3534                 ErrPrint("Handler is invalid\n");
3535                 return LB_STATUS_ERROR_INVALID;
3536         }
3537
3538         if (!handler->common->id) {
3539                 ErrPrint("Invalid handler\n");
3540                 return LB_STATUS_ERROR_INVALID;
3541         }
3542
3543         return handler->common->is_user;
3544 }
3545
3546 EAPI int livebox_set_pinup(struct livebox *handler, int flag, ret_cb_t cb, void *data)
3547 {
3548         struct packet *packet;
3549         int ret;
3550
3551         if (!handler || handler->state != CREATE) {
3552                 ErrPrint("Handler is invalid\n");
3553                 return LB_STATUS_ERROR_INVALID;
3554         }
3555
3556         if (!handler->common || handler->common->state != CREATE) {
3557                 ErrPrint("Handler is invalid\n");
3558                 return LB_STATUS_ERROR_INVALID;
3559         }
3560
3561         if (!handler->common->id) {
3562                 ErrPrint("Invalid handler\n");
3563                 return LB_STATUS_ERROR_INVALID;
3564         }
3565
3566         if (handler->common->request.pinup) {
3567                 ErrPrint("Previous pinup request is not finished\n");
3568                 return LB_STATUS_ERROR_BUSY;
3569         }
3570
3571         if (handler->common->is_pinned_up == flag) {
3572                 DbgPrint("No changes\n");
3573                 return LB_STATUS_ERROR_ALREADY;
3574         }
3575
3576         packet = packet_create("pinup_changed", "ssi", handler->common->pkgname, handler->common->id, flag);
3577         if (!packet) {
3578                 ErrPrint("Failed to build a param\n");
3579                 return LB_STATUS_ERROR_FAULT;
3580         }
3581
3582         if (!cb) {
3583                 cb = default_pinup_cb;
3584         }
3585
3586         ret = master_rpc_async_request(handler, packet, 0, pinup_done_cb, NULL);
3587         if (ret == LB_STATUS_SUCCESS) {
3588                 handler->cbs.pinup.cb = cb;
3589                 handler->cbs.pinup.data = data;
3590                 handler->common->request.pinup = 1;
3591         }
3592
3593         return ret;
3594 }
3595
3596 EAPI int livebox_is_pinned_up(struct livebox *handler)
3597 {
3598         if (!handler || handler->state != CREATE) {
3599                 ErrPrint("Handler is invalid\n");
3600                 return LB_STATUS_ERROR_INVALID;
3601         }
3602
3603         if (!handler->common || handler->common->state != CREATE) {
3604                 ErrPrint("Handler is invalid\n");
3605                 return LB_STATUS_ERROR_INVALID;
3606         }
3607
3608         if (!handler->common->id) {
3609                 ErrPrint("Invalid handler\n");
3610                 return LB_STATUS_ERROR_INVALID;
3611         }
3612
3613         return handler->common->is_pinned_up;
3614 }
3615
3616 EAPI int livebox_has_pinup(struct livebox *handler)
3617 {
3618         if (!handler || handler->state != CREATE) {
3619                 ErrPrint("Handler is invalid\n");
3620                 return LB_STATUS_ERROR_INVALID;
3621         }
3622
3623         if (!handler->common || handler->common->state != CREATE) {
3624                 ErrPrint("Handler is invalid\n");
3625                 return LB_STATUS_ERROR_INVALID;
3626         }
3627
3628         if (!handler->common->id) {
3629                 ErrPrint("Invalid handler\n");
3630                 return LB_STATUS_ERROR_INVALID;
3631         }
3632
3633         return handler->common->lb.pinup_supported;
3634 }
3635
3636 EAPI int livebox_set_data(struct livebox *handler, void *data)
3637 {
3638         if (!handler) {
3639                 ErrPrint("Handler is NIL\n");
3640                 return LB_STATUS_ERROR_INVALID;
3641         }
3642
3643         if (handler->state != CREATE) {
3644                 ErrPrint("Handler is invalid\n");
3645                 return LB_STATUS_ERROR_INVALID;
3646         }
3647
3648         handler->data = data;
3649         return LB_STATUS_SUCCESS;
3650 }
3651
3652 EAPI void *livebox_get_data(struct livebox *handler)
3653 {
3654         if (!handler) {
3655                 ErrPrint("Handler is NIL\n");
3656                 return NULL;
3657         }
3658
3659         if (handler->state != CREATE) {
3660                 ErrPrint("Handler is invalid\n");
3661                 return NULL;
3662         }
3663
3664         return handler->data;
3665 }
3666
3667 EAPI int livebox_is_exists(const char *pkgname)
3668 {
3669         char *lb;
3670
3671         lb = lb_pkgname(pkgname);
3672         if (lb) {
3673                 free(lb);
3674                 return 1;
3675         }
3676
3677         return 0;
3678 }
3679
3680 EAPI const char *livebox_content(struct livebox *handler)
3681 {
3682         if (!handler || handler->state != CREATE) {
3683                 ErrPrint("Handler is invalid\n");
3684                 return NULL;
3685         }
3686
3687         if (!handler->common || handler->common->state != CREATE) {
3688                 ErrPrint("Invalid handle\n");
3689                 return NULL;
3690         }
3691
3692         return handler->common->content;
3693 }
3694
3695 EAPI const char *livebox_category_title(struct livebox *handler)
3696 {
3697         if (!handler || handler->state != CREATE) {
3698                 ErrPrint("Handler is invalid\n");
3699                 return NULL;
3700         }
3701
3702         if (!handler->common || handler->common->state != CREATE) {
3703                 ErrPrint("Invalid handle\n");
3704                 return NULL;
3705         }
3706
3707         return handler->common->title;
3708 }
3709
3710 EAPI int livebox_emit_text_signal(struct livebox *handler, const char *emission, const char *source, double sx, double sy, double ex, double ey, ret_cb_t cb, void *data)
3711 {
3712         struct packet *packet;
3713         struct cb_info *cbinfo;
3714         int ret;
3715
3716         if (!handler || handler->state != CREATE) {
3717                 ErrPrint("Handler is invalid\n");
3718                 return LB_STATUS_ERROR_INVALID;
3719         }
3720
3721         if (!handler->common || handler->common->state != CREATE) {
3722                 ErrPrint("Handler is invalid\n");
3723                 return LB_STATUS_ERROR_INVALID;
3724         }
3725
3726         if ((handler->common->lb.type != _LB_TYPE_TEXT && handler->common->pd.type != _PD_TYPE_TEXT) || !handler->common->id) {
3727                 ErrPrint("Handler is not valid\n");
3728                 return LB_STATUS_ERROR_INVALID;
3729         }
3730
3731         if (!emission) {
3732                 emission = "";
3733         }
3734
3735         if (!source) {
3736                 source = "";
3737         }
3738
3739         packet = packet_create("text_signal", "ssssdddd",
3740                                 handler->common->pkgname, handler->common->id, emission, source, sx, sy, ex, ey);
3741         if (!packet) {
3742                 ErrPrint("Failed to build a param\n");
3743                 return LB_STATUS_ERROR_FAULT;
3744         }
3745
3746         cbinfo = create_cb_info(cb, data);
3747         if (!cbinfo) {
3748                 packet_destroy(packet);
3749                 return LB_STATUS_ERROR_FAULT;
3750         }
3751
3752         ret = master_rpc_async_request(handler, packet, 0, text_signal_cb, cbinfo);
3753         if (ret < 0) {
3754                 destroy_cb_info(cbinfo);
3755         }
3756
3757         return ret;
3758 }
3759
3760 EAPI int livebox_subscribe_group(const char *cluster, const char *category)
3761 {
3762         struct packet *packet;
3763
3764         /*!
3765          * \todo
3766          * Validate the group info using DB
3767          * If the group info is not valid, do not send this request
3768          */
3769
3770         packet = packet_create_noack("subscribe", "ss", cluster ? cluster : "", category ? category : "");
3771         if (!packet) {
3772                 ErrPrint("Failed to create a packet\n");
3773                 return LB_STATUS_ERROR_FAULT;
3774         }
3775
3776         return master_rpc_request_only(NULL, packet);
3777 }
3778
3779 EAPI int livebox_unsubscribe_group(const char *cluster, const char *category)
3780 {
3781         struct packet *packet;
3782
3783         /*!
3784          * \todo
3785          * Validate the group info using DB
3786          * If the group info is not valid, do not send this request
3787          * AND Check the subscribed or not too
3788          */
3789
3790         packet = packet_create_noack("unsubscribe", "ss", cluster ? cluster : "", category ? category : "");
3791         if (!packet) {
3792                 ErrPrint("Failed to create a packet\n");
3793                 return LB_STATUS_ERROR_FAULT;
3794         }
3795
3796         return master_rpc_request_only(NULL, packet);
3797 }
3798
3799 EAPI int livebox_refresh(struct livebox *handler, int force)
3800 {
3801         struct packet *packet;
3802
3803         if (!handler || handler->state != CREATE) {
3804                 ErrPrint("Handler is invalid\n");
3805                 return LB_STATUS_ERROR_INVALID;
3806         }
3807
3808         if (!handler->common || handler->common->state != CREATE) {
3809                 ErrPrint("Handler is not valid\n");
3810                 return LB_STATUS_ERROR_INVALID;
3811         }
3812
3813         if (!handler->common->id) {
3814                 ErrPrint("Handler is not valid\n");
3815                 return LB_STATUS_ERROR_INVALID;
3816         }
3817
3818         packet = packet_create_noack("update", "ssi", handler->common->pkgname, handler->common->id, force);
3819         if (!packet) {
3820                 ErrPrint("Failed to create a packet\n");
3821                 return LB_STATUS_ERROR_FAULT;
3822         }
3823
3824         return master_rpc_request_only(handler, packet);
3825 }
3826
3827 EAPI int livebox_refresh_group(const char *cluster, const char *category, int force)
3828 {
3829         struct packet *packet;
3830
3831         if (!cluster || !category) {
3832                 ErrPrint("Invalid argument\n");
3833                 return LB_STATUS_ERROR_INVALID;
3834         }
3835
3836         packet = packet_create_noack("refresh_group", "ssi", cluster, category, force);
3837         if (!packet) {
3838                 ErrPrint("Failed to create a packet\n");
3839                 return LB_STATUS_ERROR_FAULT;
3840         }
3841
3842         return master_rpc_request_only(NULL, packet);
3843 }
3844
3845 EAPI int livebox_set_visibility(struct livebox *handler, enum livebox_visible_state state)
3846 {
3847         int old_state;
3848         int ret;
3849
3850         if (!handler || handler->state != CREATE) {
3851                 ErrPrint("Handler is invalid\n");
3852                 return LB_STATUS_ERROR_INVALID;
3853         }
3854
3855         if (!handler->common || handler->common->state != CREATE) {
3856                 ErrPrint("Handler is not valid\n");
3857                 return LB_STATUS_ERROR_INVALID;
3858         }
3859
3860         if (!handler->common->id) {
3861                 ErrPrint("Handler is not valid\n");
3862                 return LB_STATUS_ERROR_INVALID;
3863         }
3864
3865         if (!handler->common->is_user) {
3866                 /* System cluster livebox cannot be changed its visible states */
3867                 if (state == LB_HIDE_WITH_PAUSE) {
3868                         ErrPrint("CA Livebox is not able to change the visibility\n");
3869                         return LB_STATUS_ERROR_PERMISSION;
3870                 }
3871         }
3872
3873         DbgPrint("[%s] Change visiblity to 0x%x\n", handler->common->pkgname, state);
3874
3875         if (handler->visible == state) {
3876                 DbgPrint("%s has no changes\n", handler->common->pkgname);
3877                 return LB_STATUS_ERROR_ALREADY;
3878         }
3879
3880         old_state = handler->visible;
3881         handler->visible = state;
3882
3883         ret = lb_set_visibility(handler, state);
3884         if (ret < 0) {
3885                 handler->visible = old_state;
3886         }
3887
3888         return ret;
3889 }
3890
3891 EAPI enum livebox_visible_state livebox_visibility(struct livebox *handler)
3892 {
3893         if (!handler || handler->state != CREATE) {
3894                 ErrPrint("Handler is invalid\n");
3895                 return LB_VISIBLE_ERROR;
3896         }
3897
3898         if (!handler->common || handler->common->state != CREATE) {
3899                 ErrPrint("Handler is not valid\n");
3900                 return LB_VISIBLE_ERROR;
3901         }
3902
3903         if (!handler->common->id) {
3904                 ErrPrint("Handler is not valid\n");
3905                 return LB_VISIBLE_ERROR;
3906         }
3907
3908         return handler->visible;
3909 }
3910
3911 int lb_set_group(struct livebox_common *common, const char *cluster, const char *category)
3912 {
3913         void *pc = NULL;
3914         void *ps = NULL;
3915
3916         if (cluster) {
3917                 pc = strdup(cluster);
3918                 if (!pc) {
3919                         ErrPrint("Heap: %s (cluster: %s)\n", strerror(errno), cluster);
3920                         return LB_STATUS_ERROR_MEMORY;
3921                 }
3922         }
3923
3924         if (category) {
3925                 ps = strdup(category);
3926                 if (!ps) {
3927                         ErrPrint("Heap: %s (category: %s)\n", strerror(errno), category);
3928                         free(pc);
3929                         return LB_STATUS_ERROR_MEMORY;
3930                 }
3931         }
3932
3933         if (common->cluster) {
3934                 free(common->cluster);
3935         }
3936
3937         if (common->category) {
3938                 free(common->category);
3939         }
3940
3941         common->cluster = pc;
3942         common->category = ps;
3943
3944         return LB_STATUS_SUCCESS;
3945 }
3946
3947 void lb_set_size(struct livebox_common *common, int w, int h)
3948 {
3949         common->lb.width = w;
3950         common->lb.height = h;
3951 }
3952
3953 void lb_set_update_mode(struct livebox_common *common, int active_mode)
3954 {
3955         common->is_active_update = active_mode;
3956 }
3957
3958 void lb_set_pdsize(struct livebox_common *common, int w, int h)
3959 {
3960         common->pd.width = w;
3961         common->pd.height = h;
3962 }
3963
3964 void lb_set_default_pdsize(struct livebox_common *common, int w, int h)
3965 {
3966         common->pd.default_width = w;
3967         common->pd.default_height = h;
3968 }
3969
3970 void lb_invoke_fault_handler(enum livebox_fault_type event, const char *pkgname, const char *file, const char *func)
3971 {
3972         struct dlist *l;
3973         struct dlist *n;
3974         struct fault_info *info;
3975
3976         s_info.fault_state = INFO_STATE_CALLBACK_IN_PROCESSING;
3977
3978         dlist_foreach_safe(s_info.fault_list, l, n, info) {
3979                 if (!info->is_deleted && info->handler(event, pkgname, file, func, info->user_data) == EXIT_FAILURE) {
3980                         info->is_deleted = 1;
3981                 }
3982
3983                 if (info->is_deleted) {
3984                         s_info.fault_list = dlist_remove(s_info.fault_list, l);
3985                         free(info);
3986                 }
3987         }
3988
3989         s_info.fault_state &= ~INFO_STATE_CALLBACK_IN_PROCESSING;
3990 }
3991
3992 void lb_invoke_event_handler(struct livebox *handler, enum livebox_event_type event)
3993 {
3994         struct dlist *l;
3995         struct dlist *n;
3996         struct event_info *info;
3997
3998         if (event == LB_EVENT_LB_UPDATED && handler->common->refcnt > 1) {
3999                 if (handler->visible != LB_SHOW) {
4000                         DbgPrint("Update requested(pending) - %s\n", handler->common->pkgname);
4001                         handler->paused_updating++;
4002                         return;
4003                 } else {
4004                         handler->paused_updating = 0;
4005                 }
4006         }
4007
4008         s_info.event_state = INFO_STATE_CALLBACK_IN_PROCESSING;
4009
4010         dlist_foreach_safe(s_info.event_list, l, n, info) {
4011                 if (!info->is_deleted && info->handler(handler, event, info->user_data) == EXIT_FAILURE) {
4012                         DbgPrint("Event handler returns EXIT_FAILURE\n");
4013                         info->is_deleted = 1;
4014                 }
4015
4016                 if (info->is_deleted) {
4017                         s_info.event_list = dlist_remove(s_info.event_list, l);
4018                         free(info);
4019                 }
4020         }
4021
4022         s_info.event_state &= ~INFO_STATE_CALLBACK_IN_PROCESSING;
4023 }
4024
4025 struct livebox_common *lb_find_common_handle(const char *pkgname, const char *id)
4026 {
4027         struct dlist *l;
4028         struct livebox_common *common;
4029
4030         dlist_foreach(s_info.livebox_common_list, l, common) {
4031                 if (!common->id) {
4032                         continue;
4033                 }
4034
4035                 if (!strcmp(common->pkgname, pkgname) && !strcmp(common->id, id)) {
4036                         return common;
4037                 }
4038         }
4039
4040         return NULL;
4041 }
4042
4043 struct livebox_common *lb_find_common_handle_by_timestamp(double timestamp)
4044 {
4045         struct dlist *l;
4046         struct livebox_common *common;
4047
4048         dlist_foreach(s_info.livebox_common_list, l, common) {
4049                 if (common->timestamp == timestamp) {
4050                         return common;
4051                 }
4052         }
4053
4054         return NULL;
4055 }
4056
4057 struct livebox *lb_new_livebox(const char *pkgname, const char *id, double timestamp, const char *cluster, const char *category)
4058 {
4059         struct livebox *handler;
4060
4061         handler = calloc(1, sizeof(*handler));
4062         if (!handler) {
4063                 ErrPrint("Failed to create a new livebox\n");
4064                 return NULL;
4065         }
4066
4067         handler->common = lb_create_common_handle(handler, pkgname, cluster, category);
4068         if (!handler->common) {
4069                 ErrPrint("Heap: %s\n", strerror(errno));
4070                 free(handler);
4071                 return NULL;
4072         }
4073
4074         lb_common_ref(handler->common, handler);
4075         lb_set_id(handler->common, id);
4076         handler->common->timestamp = timestamp;
4077         handler->common->state = CREATE;
4078         handler->visible = LB_SHOW;
4079         s_info.livebox_list = dlist_append(s_info.livebox_list, handler);
4080
4081         return lb_ref(handler);
4082 }
4083
4084 int lb_delete_all(void)
4085 {
4086         struct dlist *l;
4087         struct dlist *n;
4088         struct livebox *handler;
4089
4090         dlist_foreach_safe(s_info.livebox_list, l, n, handler) {
4091                 lb_invoke_event_handler(handler, LB_EVENT_DELETED);
4092                 lb_unref(handler, 1);
4093         }
4094
4095         return LB_STATUS_SUCCESS;
4096 }
4097
4098 int lb_set_content(struct livebox_common *common, const char *content)
4099 {
4100         char *pc = NULL;
4101
4102         if (content) {
4103                 pc = strdup(content);
4104                 if (!pc) {
4105                         ErrPrint("heap: %s [%s]\n", strerror(errno), content);
4106                         return LB_STATUS_ERROR_MEMORY;
4107                 }
4108         }
4109
4110         free(common->content);
4111         common->content = pc;
4112         return LB_STATUS_SUCCESS;
4113 }
4114
4115 int lb_set_title(struct livebox_common *common, const char *title)
4116 {
4117         char *pt = NULL;
4118
4119         if (title) {
4120                 pt = strdup(title);
4121                 if (!pt) {
4122                         ErrPrint("heap: %s [%s]\n", strerror(errno), title);
4123                         return LB_STATUS_ERROR_MEMORY;
4124                 }
4125         }
4126
4127         free(common->title);
4128         common->title = pt;
4129         return LB_STATUS_SUCCESS;
4130 }
4131
4132 void lb_set_size_list(struct livebox_common *common, int size_list)
4133 {
4134         common->lb.size_list = size_list;
4135 }
4136
4137 void lb_set_auto_launch(struct livebox_common *common, const char *auto_launch)
4138 {
4139         char *pa = NULL;
4140
4141         if (!auto_launch || !strlen(auto_launch)) {
4142                 return;
4143         }
4144
4145         pa = strdup(auto_launch);
4146         if (!pa) {
4147                 ErrPrint("heap: %s, [%s]\n", strerror(errno), auto_launch);
4148                 return;
4149         }
4150
4151         free(common->lb.auto_launch);
4152         common->lb.auto_launch = pa;
4153 }
4154
4155 void lb_set_priority(struct livebox_common *common, double priority)
4156 {
4157         common->lb.priority = priority;
4158 }
4159
4160 void lb_set_id(struct livebox_common *common, const char *id)
4161 {
4162         char *pi = NULL;
4163
4164         if (id) {
4165                 pi = strdup(id);
4166                 if (!pi) {
4167                         ErrPrint("heap: %s [%s]\n", strerror(errno), pi);
4168                         return;
4169                 }
4170         }
4171
4172         free(common->id);
4173         common->id = pi;
4174 }
4175
4176 void lb_set_filename(struct livebox_common *common, const char *filename)
4177 {
4178         if (common->filename) {
4179                 if (common->lb.type == _LB_TYPE_FILE || common->lb.type == _LB_TYPE_TEXT) {
4180                         if (common->filename[0] && unlink(common->filename) < 0) {
4181                                 ErrPrint("unlink: %s (%s)\n", strerror(errno), common->filename);
4182                         }
4183                 }
4184
4185                 free(common->filename);
4186         }
4187
4188         common->filename = strdup(filename);
4189         if (!common->filename) {
4190                 ErrPrint("Heap: %s\n", strerror(errno));
4191         }
4192 }
4193
4194 void lb_set_alt_info(struct livebox_common *common, const char *icon, const char *name)
4195 {
4196         char *_icon = NULL;
4197         char *_name = NULL;
4198
4199         if (icon && strlen(icon)) {
4200                 _icon = strdup(icon);
4201                 if (!_icon) {
4202                         ErrPrint("Heap: %s\n", strerror(errno));
4203                 }
4204         }
4205
4206         if (name && strlen(name)) {
4207                 _name = strdup(name);
4208                 if (!_name) {
4209                         ErrPrint("Heap: %s\n", strerror(errno));
4210                 }
4211         }
4212
4213         free(common->alt.icon);
4214         common->alt.icon = _icon;
4215
4216         free(common->alt.name);
4217         common->alt.name = _name;
4218 }
4219
4220 int lb_set_lb_fb(struct livebox_common *common, const char *filename)
4221 {
4222         struct fb_info *fb;
4223
4224         if (!common) {
4225                 return LB_STATUS_ERROR_INVALID;
4226         }
4227
4228         fb = common->lb.fb;
4229         if (fb && !strcmp(fb_id(fb), filename)) { /*!< BUFFER is not changed, */
4230                 return LB_STATUS_SUCCESS;
4231         }
4232
4233         common->lb.fb = NULL;
4234
4235         if (!filename || filename[0] == '\0') {
4236                 if (fb) {
4237                         fb_destroy(fb);
4238                 }
4239                 return LB_STATUS_SUCCESS;
4240         }
4241
4242         common->lb.fb = fb_create(filename, common->lb.width, common->lb.height);
4243         if (!common->lb.fb) {
4244                 ErrPrint("Faield to create a FB\n");
4245                 if (fb) {
4246                         fb_destroy(fb);
4247                 }
4248                 return LB_STATUS_ERROR_FAULT;
4249         }
4250
4251         if (fb) {
4252                 fb_destroy(fb);
4253         }
4254
4255         return LB_STATUS_SUCCESS;
4256 }
4257
4258 int lb_set_pd_fb(struct livebox_common *common, const char *filename)
4259 {
4260         struct fb_info *fb;
4261
4262         if (!common || common->state != CREATE) {
4263                 return LB_STATUS_ERROR_INVALID;
4264         }
4265
4266         fb = common->pd.fb;
4267         if (fb && !strcmp(fb_id(fb), filename)) {
4268                 /* BUFFER is not changed, just update the content */
4269                 return LB_STATUS_ERROR_EXIST;
4270         }
4271         common->pd.fb = NULL;
4272
4273         if (!filename || filename[0] == '\0') {
4274                 if (fb) {
4275                         fb_destroy(fb);
4276                 }
4277                 return LB_STATUS_SUCCESS;
4278         }
4279
4280         common->pd.fb = fb_create(filename, common->pd.width, common->pd.height);
4281         if (!common->pd.fb) {
4282                 ErrPrint("Failed to create a FB\n");
4283                 if (fb) {
4284                         fb_destroy(fb);
4285                 }
4286                 return LB_STATUS_ERROR_FAULT;
4287         }
4288
4289         if (fb) {
4290                 fb_destroy(fb);
4291         }
4292         return LB_STATUS_SUCCESS;
4293 }
4294
4295 struct fb_info *lb_get_lb_fb(struct livebox_common *common)
4296 {
4297         return common->lb.fb;
4298 }
4299
4300 struct fb_info *lb_get_pd_fb(struct livebox_common *common)
4301 {
4302         return common->pd.fb;
4303 }
4304
4305 void lb_set_user(struct livebox_common *common, int user)
4306 {
4307         common->is_user = user;
4308 }
4309
4310 void lb_set_pinup(struct livebox_common *common, int pinup_supported)
4311 {
4312         common->lb.pinup_supported = pinup_supported;
4313 }
4314
4315 void lb_set_text_lb(struct livebox_common *common)
4316 {
4317         common->lb.type = _LB_TYPE_TEXT;
4318 }
4319
4320 void lb_set_text_pd(struct livebox_common *common)
4321 {
4322         common->pd.type = _PD_TYPE_TEXT;
4323 }
4324
4325 int lb_text_lb(struct livebox_common *common)
4326 {
4327         return common->lb.type == _LB_TYPE_TEXT;
4328 }
4329
4330 int lb_text_pd(struct livebox_common *common)
4331 {
4332         return common->pd.type == _PD_TYPE_TEXT;
4333 }
4334
4335 void lb_set_period(struct livebox_common *common, double period)
4336 {
4337         common->lb.period = period;
4338 }
4339
4340 struct livebox *lb_ref(struct livebox *handler)
4341 {
4342         if (!handler) {
4343                 return NULL;
4344         }
4345
4346         handler->refcnt++;
4347         return handler;
4348 }
4349
4350 struct livebox *lb_unref(struct livebox *handler, int destroy_common)
4351 {
4352         if (!handler) {
4353                 return NULL;
4354         }
4355
4356         handler->refcnt--;
4357         if (handler->refcnt > 0) {
4358                 return handler;
4359         }
4360
4361         if (handler->cbs.created.cb) {
4362                 handler->cbs.created.cb(handler, LB_STATUS_ERROR_FAULT, handler->cbs.created.data);
4363                 handler->cbs.created.cb = NULL;
4364                 handler->cbs.created.data = NULL;
4365         }
4366
4367         if (handler->cbs.deleted.cb) {
4368                 handler->cbs.deleted.cb(handler, LB_STATUS_ERROR_FAULT, handler->cbs.deleted.data);
4369                 handler->cbs.deleted.cb = NULL;
4370                 handler->cbs.deleted.data = NULL;
4371         }
4372
4373         if (handler->cbs.pinup.cb) {
4374                 handler->cbs.pinup.cb(handler, LB_STATUS_ERROR_FAULT, handler->cbs.pinup.data);
4375                 handler->cbs.pinup.cb = NULL;
4376                 handler->cbs.pinup.data = NULL;
4377         }
4378
4379         if (handler->cbs.group_changed.cb) {
4380                 handler->cbs.group_changed.cb(handler, LB_STATUS_ERROR_FAULT, handler->cbs.group_changed.data);
4381                 handler->cbs.group_changed.cb = NULL;
4382                 handler->cbs.group_changed.data = NULL;
4383         }
4384
4385         if (handler->cbs.period_changed.cb) {
4386                 handler->cbs.period_changed.cb(handler, LB_STATUS_ERROR_FAULT, handler->cbs.period_changed.data);
4387                 handler->cbs.period_changed.cb = NULL;
4388                 handler->cbs.period_changed.data = NULL;
4389         }
4390
4391         if (handler->cbs.size_changed.cb) {
4392                 handler->cbs.size_changed.cb(handler, LB_STATUS_ERROR_FAULT, handler->cbs.size_changed.data);
4393                 handler->cbs.size_changed.cb = NULL;
4394                 handler->cbs.size_changed.data = NULL;
4395         }
4396
4397         if (handler->cbs.pd_created.cb) {
4398                 handler->cbs.pd_created.cb(handler, LB_STATUS_ERROR_FAULT, handler->cbs.pd_created.data);
4399                 handler->cbs.pd_created.cb = NULL;
4400                 handler->cbs.pd_created.data = NULL;
4401         }
4402
4403         if (handler->cbs.pd_destroyed.cb) {
4404                 handler->cbs.pd_destroyed.cb(handler, LB_STATUS_ERROR_FAULT, handler->cbs.pd_destroyed.data);
4405                 handler->cbs.pd_destroyed.cb = NULL;
4406                 handler->cbs.pd_destroyed.data = NULL;
4407         }
4408
4409         if (handler->cbs.update_mode.cb) {
4410                 handler->cbs.update_mode.cb(handler, LB_STATUS_ERROR_FAULT, handler->cbs.update_mode.data);
4411                 handler->cbs.update_mode.cb = NULL;
4412                 handler->cbs.update_mode.data = NULL;
4413         }
4414
4415         if (handler->cbs.access_event.cb) {
4416                 handler->cbs.access_event.cb(handler, LB_ACCESS_STATUS_ERROR, handler->cbs.access_event.data);
4417                 handler->cbs.access_event.cb = NULL;
4418                 handler->cbs.access_event.data = NULL;
4419         }
4420
4421         if (handler->cbs.key_event.cb) {
4422                 handler->cbs.key_event.cb(handler, LB_KEY_STATUS_ERROR, handler->cbs.key_event.data);
4423                 handler->cbs.key_event.cb = NULL;
4424                 handler->cbs.key_event.data = NULL;
4425         }
4426
4427         dlist_remove_data(s_info.livebox_list, handler);
4428
4429         handler->state = DESTROYED;
4430         if (lb_common_unref(handler->common, handler) == 0) {
4431                 if (destroy_common) {
4432                         /*!
4433                          * \note
4434                          * Lock file should be deleted after all callbacks are processed.
4435                          */
4436                         lb_destroy_lock_file(handler->common, 0);
4437                         lb_destroy_common_handle(handler->common);
4438                 }
4439         }
4440         free(handler);
4441         DbgPrint("Handler is released\n");
4442         return NULL;
4443 }
4444
4445 int lb_send_delete(struct livebox *handler, int type, ret_cb_t cb, void *data)
4446 {
4447         struct packet *packet;
4448         struct cb_info *cbinfo;
4449         int ret;
4450
4451         if (handler->common->request.deleted) {
4452                 ErrPrint("Already in-progress\n");
4453                 if (cb) {
4454                         cb(handler, LB_STATUS_SUCCESS, data);
4455                 }
4456                 return LB_STATUS_ERROR_BUSY;
4457         }
4458
4459         if (!cb) {
4460                 cb = default_delete_cb;
4461         }
4462
4463         packet = packet_create("delete", "ssid", handler->common->pkgname, handler->common->id, type, handler->common->timestamp);
4464         if (!packet) {
4465                 ErrPrint("Failed to build a param\n");
4466                 if (cb) {
4467                         cb(handler, LB_STATUS_ERROR_FAULT, data);
4468                 }
4469
4470                 return LB_STATUS_ERROR_FAULT;
4471         }
4472
4473         cbinfo = create_cb_info(cb, data);
4474         if (!cbinfo) {
4475                 packet_destroy(packet);
4476                 ErrPrint("Failed to create cbinfo\n");
4477                 if (cb) {
4478                         cb(handler, LB_STATUS_ERROR_FAULT, data);
4479                 }
4480
4481                 return LB_STATUS_ERROR_FAULT;
4482         }
4483
4484         ret = master_rpc_async_request(handler, packet, 0, del_ret_cb, cbinfo);
4485         if (ret < 0) {
4486                 /*!
4487                  * Packet is destroyed by master_rpc_async_request.
4488                  */
4489                 destroy_cb_info(cbinfo);
4490
4491                 if (cb) {
4492                         cb(handler, LB_STATUS_ERROR_FAULT, data);
4493                 }
4494         } else {
4495                 handler->common->request.deleted = 1;
4496         }
4497
4498         return ret;
4499 }
4500
4501 EAPI int livebox_client_paused(void)
4502 {
4503         struct packet *packet;
4504
4505         packet = packet_create_noack("client_paused", "d", util_timestamp());
4506         if (!packet) {
4507                 ErrPrint("Failed to create a pause packet\n");
4508                 return LB_STATUS_ERROR_FAULT;
4509         }
4510
4511         return master_rpc_request_only(NULL, packet);
4512 }
4513
4514 EAPI int livebox_client_resumed(void)
4515 {
4516         struct packet *packet;
4517
4518         packet = packet_create_noack("client_resumed", "d", util_timestamp());
4519         if (!packet) {
4520                 ErrPrint("Failed to create a resume packet\n");
4521                 return LB_STATUS_ERROR_FAULT;
4522         }
4523
4524         return master_rpc_request_only(NULL, packet);
4525 }
4526
4527 EAPI int livebox_sync_lb_fb(struct livebox *handler)
4528 {
4529         if (!handler || handler->state != CREATE) {
4530                 ErrPrint("Invalid handle\n");
4531                 return LB_STATUS_ERROR_INVALID;
4532         }
4533
4534         if (!handler->common || handler->common->state != CREATE) {
4535                 ErrPrint("Invalid handle\n");
4536                 return LB_STATUS_ERROR_INVALID;
4537         }
4538
4539         if (!handler->common->id) {
4540                 return LB_STATUS_ERROR_INVALID;
4541         }
4542
4543         return lb_sync_lb_fb(handler->common);
4544 }
4545
4546 int lb_sync_lb_fb(struct livebox_common *common)
4547 {
4548         int ret;
4549
4550         if (fb_type(lb_get_lb_fb(common)) == BUFFER_TYPE_FILE && common->lb.lock_fd >= 0) {
4551                 (void)do_fb_lock(common->lb.lock_fd);
4552                 ret = fb_sync(lb_get_lb_fb(common));
4553                 (void)do_fb_unlock(common->lb.lock_fd);
4554         } else {
4555                 ret = fb_sync(lb_get_lb_fb(common));
4556         }
4557
4558         return ret;
4559 }
4560
4561 int lb_sync_pd_fb(struct livebox_common *common)
4562 {
4563         int ret;
4564
4565         if (fb_type(lb_get_pd_fb(common)) == BUFFER_TYPE_FILE && common->pd.lock_fd >= 0) {
4566                 (void)do_fb_lock(common->pd.lock_fd);
4567                 ret = fb_sync(lb_get_pd_fb(common));
4568                 (void)do_fb_unlock(common->pd.lock_fd);
4569         } else {
4570                 ret = fb_sync(lb_get_pd_fb(common));
4571         }
4572
4573         return ret;
4574 }
4575
4576 EAPI int livebox_sync_pd_fb(struct livebox *handler)
4577 {
4578         if (!handler || handler->state != CREATE) {
4579                 ErrPrint("Invalid handle\n");
4580                 return LB_STATUS_ERROR_INVALID;
4581         }
4582
4583         if (!handler->common || handler->common->state != CREATE) {
4584                 ErrPrint("Invalid handle\n");
4585                 return LB_STATUS_ERROR_INVALID;
4586         }
4587
4588         if (!handler->common->id) {
4589                 ErrPrint("Invalid handle\n");
4590                 return LB_STATUS_ERROR_INVALID;
4591         }
4592
4593         return lb_sync_pd_fb(handler->common);
4594 }
4595
4596 EAPI const char *livebox_alt_icon(struct livebox *handler)
4597 {
4598         if (!handler || handler->state != CREATE) {
4599                 ErrPrint("Handler is not valid[%p]\n", handler);
4600                 return NULL;
4601         }
4602
4603         if (!handler->common || handler->common->state != CREATE) {
4604                 ErrPrint("Handler is not valid\n");
4605                 return NULL;
4606         }
4607
4608         return handler->common->alt.icon;
4609 }
4610
4611 EAPI const char *livebox_alt_name(struct livebox *handler)
4612 {
4613         if (!handler || handler->state != CREATE) {
4614                 ErrPrint("Handler is not valid[%p]\n", handler);
4615                 return NULL;
4616         }
4617
4618         if (!handler->common || handler->common->state != CREATE) {
4619                 ErrPrint("Handler is not valid\n");
4620                 return NULL;
4621         }
4622
4623         return handler->common->alt.name;
4624 }
4625
4626 EAPI int livebox_acquire_fb_lock(struct livebox *handler, int is_pd)
4627 {
4628         int ret = LB_STATUS_SUCCESS;
4629         int fd;
4630
4631         if (!handler || handler->state != CREATE) {
4632                 ErrPrint("Handler is not valid[%p]\n", handler);
4633                 return LB_STATUS_ERROR_INVALID;
4634         }
4635
4636         if (!handler->common || handler->common->state != CREATE) {
4637                 ErrPrint("Handler is not valid\n");
4638                 return LB_STATUS_ERROR_INVALID;
4639         }
4640
4641         if (!handler->common->id) {
4642                 ErrPrint("Handler is not valid[%p]\n", handler);
4643                 return LB_STATUS_ERROR_INVALID;
4644         }
4645
4646         if (is_pd) {
4647                 if (!handler->common->pd.lock || handler->common->pd.lock_fd < 0) {
4648                         DbgPrint("Lock: %s (%d)\n", handler->common->pd.lock, handler->common->pd.lock_fd);
4649                         return LB_STATUS_ERROR_INVALID;
4650                 }
4651
4652                 if (fb_type(lb_get_pd_fb(handler->common)) == BUFFER_TYPE_FILE) {
4653                         return LB_STATUS_SUCCESS;
4654                 }
4655
4656                 fd = handler->common->pd.lock_fd;
4657         } else {
4658                 if (!handler->common->lb.lock || handler->common->lb.lock_fd < 0) {
4659                         DbgPrint("Lock: %s (%d)\n", handler->common->lb.lock, handler->common->lb.lock_fd);
4660                         return LB_STATUS_ERROR_INVALID;
4661                 }
4662
4663                 if (fb_type(lb_get_lb_fb(handler->common)) == BUFFER_TYPE_FILE) {
4664                         return LB_STATUS_SUCCESS;
4665                 }
4666
4667                 fd = handler->common->lb.lock_fd;
4668         }
4669
4670         ret = do_fb_lock(fd);
4671
4672         return ret == 0 ? LB_STATUS_SUCCESS : LB_STATUS_ERROR_FAULT;
4673 }
4674
4675 EAPI int livebox_release_fb_lock(struct livebox *handler, int is_pd)
4676 {
4677         int ret = LB_STATUS_SUCCESS;
4678         int fd;
4679
4680         if (!handler || handler->state != CREATE) {
4681                 ErrPrint("Invalid handle\n");
4682                 return LB_STATUS_ERROR_INVALID;
4683         }
4684
4685         if (!handler->common || handler->common->state != CREATE) {
4686                 ErrPrint("Invalid handle\n");
4687                 return LB_STATUS_ERROR_INVALID;
4688         }
4689
4690         if (!handler->common->id) {
4691                 ErrPrint("Handler is not valid[%p]\n", handler);
4692                 return LB_STATUS_ERROR_INVALID;
4693         }
4694
4695         if (is_pd) {
4696                 if (!handler->common->pd.lock || handler->common->pd.lock_fd < 0) {
4697                         DbgPrint("Unlock: %s (%d)\n", handler->common->pd.lock, handler->common->pd.lock_fd);
4698                         return LB_STATUS_ERROR_INVALID;
4699                 }
4700
4701                 if (fb_type(lb_get_pd_fb(handler->common)) == BUFFER_TYPE_FILE) {
4702                         return LB_STATUS_SUCCESS;
4703                 }
4704
4705                 fd = handler->common->pd.lock_fd;
4706         } else {
4707                 if (!handler->common->lb.lock || handler->common->lb.lock_fd < 0) {
4708                         DbgPrint("Unlock: %s (%d)\n", handler->common->lb.lock, handler->common->lb.lock_fd);
4709                         return LB_STATUS_ERROR_INVALID;
4710                 }
4711
4712                 if (fb_type(lb_get_lb_fb(handler->common)) == BUFFER_TYPE_FILE) {
4713                         return LB_STATUS_SUCCESS;
4714                 }
4715
4716                 fd = handler->common->lb.lock_fd;
4717         }
4718
4719         ret = do_fb_unlock(fd);
4720
4721         return ret == 0 ? LB_STATUS_SUCCESS : LB_STATUS_ERROR_FAULT;
4722 }
4723
4724 EAPI int livebox_set_option(enum livebox_option_type option, int state)
4725 {
4726         int ret = LB_STATUS_SUCCESS;
4727
4728         switch (option) {
4729         case LB_OPTION_MANUAL_SYNC:
4730                 conf_set_manual_sync(state);
4731                 break;
4732         case LB_OPTION_FRAME_DROP_FOR_RESIZE:
4733                 conf_set_frame_drop_for_resizing(state);
4734                 break;
4735         case LB_OPTION_SHARED_CONTENT:
4736                 conf_set_shared_content(state);
4737                 break;
4738         default:
4739                 ret = LB_STATUS_ERROR_INVALID;
4740                 break;
4741         }
4742
4743         return ret;
4744 }
4745
4746 EAPI int livebox_option(enum livebox_option_type option)
4747 {
4748         int ret;
4749
4750         switch (option) {
4751         case LB_OPTION_MANUAL_SYNC:
4752                 ret = conf_manual_sync();
4753                 break;
4754         case LB_OPTION_FRAME_DROP_FOR_RESIZE:
4755                 ret = conf_frame_drop_for_resizing();
4756                 break;
4757         case LB_OPTION_SHARED_CONTENT:
4758                 ret = conf_shared_content();
4759                 break;
4760         default:
4761                 ret = LB_STATUS_ERROR_INVALID;
4762                 break;
4763         }
4764
4765         return ret;
4766 }
4767
4768 /* End of a file */