[REFACTOR] add functions start_app_launch_timer stop_app_launch_timer
[platform/core/system/swap-manager.git] / daemon / daemon.c
index c684269..325abff 100644 (file)
@@ -1,35 +1,39 @@
 /*
-*  DA manager
-*
-* Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved.
-*
-* Contact: 
-*
-* Jaewon Lim <jaewon81.lim@samsung.com>
-* Woojin Jung <woojin2.jung@samsung.com>
-* Juyoung Kim <j0.kim@samsung.com>
-* 
+ *  DA manager
+ *
+ * Copyright (c) 2000 - 2013 Samsung Electronics Co., Ltd. All rights reserved.
+ *
+ * Contact:
+ *
+ * Jaewon Lim <jaewon81.lim@samsung.com>
+ * Woojin Jung <woojin2.jung@samsung.com>
+ * Juyoung Kim <j0.kim@samsung.com>
+ * Cherepanov Vitaliy <v.cherepanov@samsung.com>
+ * Nikita Kalyazin    <n.kalyazin@samsung.com>
+ *
  * Licensed under the Apache License, Version 2.0 (the "License");
-* you may not use this file except in compliance with the License.
-* You may obtain a copy of the License at
-*
-* http://www.apache.org/licenses/LICENSE-2.0
-*
-* Unless required by applicable law or agreed to in writing, software
-* distributed under the License is distributed on an "AS IS" BASIS,
-* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-* See the License for the specific language governing permissions and
-* limitations under the License.
-*
-* Contributors:
-* - S-Core Co., Ltd
-*
-*/ 
-
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ * Contributors:
+ * - S-Core Co., Ltd
+ * - Samsung RnD Institute Russia
+ *
+ */
+#define __STDC_FORMAT_MACROS
 #include <stdio.h>
 #include <stdlib.h>                    // for realpath
 #include <string.h>                    // for strtok, strcpy, strncpy
 #include <limits.h>                    // for realpath
+#include <inttypes.h>
 
 #include <errno.h>                     // for errno
 #include <sys/types.h>         // for accept, mkdir, opendir, readdir
@@ -39,6 +43,9 @@
 #include <sys/epoll.h>         // for epoll apis
 #include <sys/timerfd.h>       // for timerfd
 #include <unistd.h>                    // for access, sleep
+#include <stdbool.h>
+
+#include <ctype.h>
 
 #ifndef LOCALTEST
 #include <attr/xattr.h>                // for fsetxattr
 #include "sys_stat.h"
 #include "utils.h"
 #include "da_protocol.h"
+#include "da_data.h"
+#include "debug.h"
+#include "process_info.h"
+
 #define DA_WORK_DIR                            "/home/developer/sdk_tools/da/"
 #define DA_READELF_PATH                        "/home/developer/sdk_tools/da/readelf"
 #define SCREENSHOT_DIR                 "/tmp/da"
 
 #define EPOLL_SIZE                             10
-#define MAX_CONNECT_SIZE               12
-#define MAX_APP_LAUNCH_TIME            6
+#define MAX_APP_LAUNCH_TIME            60
+#define MAX_CONNECT_TIMEOUT_TIME       5*60
 
 #define MAX_DEVICE                             10
 #define MAX_FILENAME                   128
@@ -188,7 +199,8 @@ void _device_write(input_dev *dev, struct input_event* in_ev)
                if(dev[i].fd >= 0)
                {
                        write(dev[i].fd, in_ev, sizeof(struct input_event));
-                       LOGI("write(%d, %d, %d)\n",dev[i].fd, in_ev, sizeof(struct input_event));
+                       LOGI("write(%d, %d, %d)\n",
+                                       dev[i].fd, (int)in_ev, sizeof(struct input_event));
                }
        }
 }
@@ -236,152 +248,257 @@ static void setEmptyTargetSlot(int index)
        }
 }
 
-// ======================================================================================
-// send functions to host
-// ======================================================================================
+// =============================================================================
+// start and terminate control functions
+// =============================================================================
 
-int pseudoSendDataToHost(struct msg_data_t* log)
+//start application launch timer function
+static int start_app_launch_timer()
 {
+       int res = 0;
+       struct epoll_event ev;
 
-       printBuf(log, MSG_DATA_HDR_LEN + log->len);
-/*     LOGI("try send to <%d><%s>\n", dev->fd, dev->fileName); */
-
-       write_to_buf(log);
-
-       return 0;
-}
-
-int sendDataToHost(msg_t* log)
-{
-       if (manager.host.data_socket != -1)
+       manager.app_launch_timerfd = timerfd_create(CLOCK_REALTIME, TFD_CLOEXEC);
+       if(manager.app_launch_timerfd > 0)
        {
-               char logstr[DA_MSG_MAX];
-               int loglen;
-
-               if(log->length != 0)
-                       loglen = sprintf(logstr, "%d|%d|%s\n", log->type, log->length + 1, log->data);
+               struct itimerspec ctime;
+               ctime.it_value.tv_sec = MAX_APP_LAUNCH_TIME;
+               ctime.it_value.tv_nsec = 0;
+               ctime.it_interval.tv_sec = 0;
+               ctime.it_interval.tv_nsec = 0;
+               if (timerfd_settime(manager.app_launch_timerfd, 0, &ctime, NULL) < 0)
+               {
+                       LOGE("fail to set app launch timer\n");
+                       close(manager.app_launch_timerfd);
+                       manager.app_launch_timerfd = -1;
+                       res = -1;
+               }
                else
-                       loglen = sprintf(logstr, "%d|%d|\n", log->type, log->length + 1);
-
-//             loglen = sprintf(logstr, "%d|%s\n", log->type, log->data);
-
-               pthread_mutex_lock(&(manager.host.data_socket_mutex));
-               send(manager.host.data_socket, logstr, loglen, MSG_NOSIGNAL);
-               pthread_mutex_unlock(&(manager.host.data_socket_mutex));
-               return 0;
+               {
+                       // add event fd to epoll list
+                       ev.events = EPOLLIN;
+                       ev.data.fd = manager.app_launch_timerfd;
+                       if (epoll_ctl(manager.efd, EPOLL_CTL_ADD,
+                                               manager.app_launch_timerfd, &ev) < 0)
+                       {
+                               // fail to add event fd
+                               LOGE("fail to add app launch timer fd to epoll list\n");
+                               close(manager.app_launch_timerfd);
+                               manager.app_launch_timerfd = -1;
+                               res = -2;
+                       } else {
+                               LOGI("application launch time started\n");
+                       }
+               }
+       } else {
+               LOGE("cannot create launch timer\n");
+               res = -3;
        }
-       else
-               return 1;
-}
 
-// msgstr can be NULL
-static int sendACKStrToHost(enum HostMessageType resp, char* msgstr)
-{
-       if (manager.host.control_socket != -1)
-       {
-               char logstr[DA_MSG_MAX];
-               int loglen;
-
-               if(msgstr != NULL)
-                       loglen = sprintf(logstr, "%d|%d|%s", (int)resp, strlen(msgstr), msgstr);
-               else
-                       loglen = sprintf(logstr, "%d|0|", (int)resp);
-
-               send(manager.host.control_socket, logstr, loglen, MSG_NOSIGNAL);
-               return 0;
-       }
-       else
-               return 1;
+       return res;
 }
 
-
-
-static int sendACKCodeToHost(enum HostMessageType resp, int msgcode)
+//stop application launch timer
+static int stop_app_launch_timer()
 {
-       // FIXME:
-       //disabled string protocol
+       epoll_ctl(manager.efd, EPOLL_CTL_DEL,manager.app_launch_timerfd, NULL);
+       close(manager.app_launch_timerfd);
+       manager.app_launch_timerfd = -1;
        return 0;
-       if (manager.host.control_socket != -1)
-       {
-               char codestr[16];
-               char logstr[DA_MSG_MAX];
-               int loglen, codelen;
-
-               codelen = sprintf(codestr, "%d", msgcode);
-               loglen = sprintf(logstr, "%d|%d|%s", (int)resp, codelen, codestr);
-
-               send(manager.host.control_socket, logstr, loglen, MSG_NOSIGNAL);
-               return 0;
-       }
-       else
-               return 1;
 }
 
-// ========================================================================================
-// start and terminate control functions
-// ========================================================================================
-
-int startProfiling(long launchflag)
+static int exec_app(const struct app_info_t *app_info)
 {
-       const struct app_info_t *app_info = &prof_session.app_info;
+       int res = 0;
+       static struct epoll_event ev;
 
-       // remove previous screen capture files
-       remove_indir(SCREENSHOT_DIR);
-       mkdir(SCREENSHOT_DIR, 0777);
-#ifndef LOCALTEST
-       smack_lsetlabel(SCREENSHOT_DIR, "*", SMACK_LABEL_ACCESS);
-#endif
-       manager.config_flag = launchflag;
-
-       if (samplingStart() < 0)
-               return -1;
 
        switch (app_info->app_type) {
        case APP_TYPE_TIZEN:
+               kill_app(app_info->exe_path);
                if (exec_app_tizen(app_info->app_id, app_info->exe_path)) {
                        LOGE("Cannot exec tizen app %s\n", app_info->app_id);
-                       samplingStop();
-                       return -1;
+                       res = -1;
                }
                break;
        case APP_TYPE_RUNNING:
                // TODO: nothing, it's running
+               LOGI("already started\n");
+               write_process_info(atoi(app_info->app_id), 0);
                break;
        case APP_TYPE_COMMON:
+               kill_app(app_info->exe_path);
                if (exec_app_common(app_info->exe_path)) {
                        LOGE("Cannot exec common app %s\n", app_info->exe_path);
-                       samplingStop();
-                       return -1;
+                       res = -1;
                }
                break;
        default:
                LOGE("Unknown app type %d\n", app_info->app_type);
-               samplingStop();
-               return -1;
+               res = -1;
                break;
        }
 
-       return 0;
+       if (res == 0 && app_info->app_type != APP_TYPE_RUNNING)
+               if (start_app_launch_timer()<0)
+                       res = -1;
+
+       LOGI("ret=%d\n", res);
+       return res;
 }
 
-// terminate single target
-// just send stop message to target process
-static void terminate_target(int index)
+int launch_timer_start()
 {
-       ssize_t sendlen;
-       msg_t sendlog;
-       sendlog.type = MSG_STOP;
-       sendlog.length = 0;
+       static struct epoll_event ev;
+       int res = 0;
 
-       if(manager.target[index].socket != -1)
+       manager.connect_timeout_timerfd = timerfd_create(CLOCK_REALTIME, TFD_CLOEXEC);
+       if(manager.connect_timeout_timerfd > 0)
        {
-               // result of sending to disconnected socket is not expected
-               sendlen = send(manager.target[index].socket, &sendlog, sizeof(sendlog.type) + sizeof(sendlog.length), MSG_NOSIGNAL);
-               if(sendlen != -1)
+               struct itimerspec ctime;
+               ctime.it_value.tv_sec = MAX_CONNECT_TIMEOUT_TIME;
+               ctime.it_value.tv_nsec = 0;
+               ctime.it_interval.tv_sec = 0;
+               ctime.it_interval.tv_nsec = 0;
+               if (timerfd_settime(manager.connect_timeout_timerfd, 0, &ctime, NULL) < 0)
                {
-                       LOGI("TERMINATE send exit msg (socket %d) by terminate_target()\n", manager.target[index].socket);
+                       LOGE("fail to set connect timeout timer\n");
+                       close(manager.connect_timeout_timerfd);
+                       manager.connect_timeout_timerfd = -1;
                }
+               else
+               {
+                       // add event fd to epoll list
+                       ev.events = EPOLLIN;
+                       ev.data.fd = manager.connect_timeout_timerfd;
+                       if (epoll_ctl(manager.efd, EPOLL_CTL_ADD,
+                                               manager.connect_timeout_timerfd, &ev) < 0)
+                       {
+                               // fail to add event fd
+                               LOGE("fail to add app connection timeout timer fd to epoll list\n");
+                               close(manager.connect_timeout_timerfd);
+                               manager.connect_timeout_timerfd = -1;
+                       } else {
+                               LOGI("connection timeout timer started\n");
+                       }
+               }
+       } else {
+               LOGE("cannot create connection timeout timer\n");
        }
+
+       LOGI("ret=%d\n", res);
+       return res;
+}
+
+static void epoll_add_input_events();
+static void epoll_del_input_events();
+
+int start_profiling()
+{
+       const struct app_info_t *app_info = &prof_session.app_info;
+       int res = 0;
+
+       // remove previous screen capture files
+       remove_indir(SCREENSHOT_DIR);
+       mkdir(SCREENSHOT_DIR, 0777);
+#ifndef LOCALTEST
+       smack_lsetlabel(SCREENSHOT_DIR, "*", SMACK_LABEL_ACCESS);
+#endif
+
+       if (IS_OPT_SET(FL_CPU | FL_MEMORY)) {
+               if (samplingStart() < 0) {
+                       LOGE("Cannot start sampling\n");
+                       res = -1;
+                       goto exit;
+               }
+       }
+
+       if (IS_OPT_SET(FL_RECORDING))
+               epoll_add_input_events();
+
+       if (exec_app(app_info)) {
+               LOGE("Cannot exec app\n");
+               res = -1;
+               goto recording_stop;
+       }
+
+       goto exit;
+
+recording_stop:
+       if (IS_OPT_SET(FL_RECORDING))
+               epoll_del_input_events();
+       if (IS_OPT_SET(FL_CPU | FL_MEMORY))
+               samplingStop();
+
+exit:
+       LOGI("return %d\n", res);
+       return res;
+}
+
+void stop_profiling(void)
+{
+       if (IS_OPT_SET(FL_RECORDING))
+               epoll_del_input_events();
+       if (IS_OPT_SET(FL_CPU | FL_MEMORY))
+               samplingStop();
+}
+
+static void reconfigure_recording(struct conf_t conf)
+{
+       uint64_t old_features = prof_session.conf.use_features0;
+       uint64_t new_features = conf.use_features0;
+       uint64_t to_enable = (new_features ^ old_features) & new_features;
+       uint64_t to_disable = (new_features ^ old_features) & old_features;
+
+       if (IS_OPT_SET_IN(FL_RECORDING, to_disable)) {
+               epoll_del_input_events();
+               prof_session.conf.use_features0 &= ~FL_RECORDING;
+       }
+
+       if (IS_OPT_SET_IN(FL_RECORDING, to_enable)) {
+               epoll_add_input_events();
+               prof_session.conf.use_features0 |= FL_RECORDING;
+       }
+
+}
+
+static int reconfigure_cpu_and_memory(struct conf_t conf)
+{
+       uint64_t old_features = prof_session.conf.use_features0;
+       uint64_t new_features = conf.use_features0;
+       uint64_t to_enable = (new_features ^ old_features) & new_features;
+       uint64_t to_disable = (new_features ^ old_features) & old_features;
+
+       prof_session.conf.system_trace_period = conf.system_trace_period;
+
+       if (IS_OPT_SET(FL_CPU | FL_MEMORY))
+               samplingStop();
+
+       if (IS_OPT_SET_IN(FL_CPU | FL_MEMORY, to_disable)) {
+               prof_session.conf.use_features0 &= ~(FL_CPU | FL_MEMORY);
+               return 0;
+       }
+
+       if (IS_OPT_SET_IN(FL_CPU | FL_MEMORY, to_enable)) {
+               if (samplingStart() < 0) {
+                       LOGE("Cannot start sampling\n");
+                       return -1;
+               }
+               prof_session.conf.use_features0 |= (FL_CPU | FL_MEMORY);
+       }
+
+       return 0;
+}
+
+int reconfigure(struct conf_t conf)
+{
+       reconfigure_recording(conf);
+       if (reconfigure_cpu_and_memory(conf)) {
+               LOGE("Cannot reconf cpu and memory\n");
+               return -1;
+       }
+
+       return 0;
 }
 
 // just send stop message to all target process
@@ -389,7 +506,7 @@ static void terminate_all_target()
 {
        int i;
        ssize_t sendlen;
-       msg_t sendlog;
+       msg_target_t sendlog;
 
        sendlog.type = MSG_STOP;
        sendlog.length = 0;
@@ -398,10 +515,13 @@ static void terminate_all_target()
        {
                if(manager.target[i].socket != -1)
                {
-                       sendlen = send(manager.target[i].socket, &sendlog, sizeof(sendlog.type) + sizeof(sendlog.length), MSG_NOSIGNAL);
+                       sendlen = send(manager.target[i].socket, &sendlog,
+                                                       sizeof(sendlog.type) + sizeof(sendlog.length),
+                                                       MSG_NOSIGNAL);
                        if(sendlen != -1)
                        {
-                               LOGI("TERMINATE send exit msg (socket %d) by terminate_all_target()\n", manager.target[i].socket);
+                               LOGI("TERMINATE send exit msg (socket %d) "
+                                               "by terminate_all_target()\n", manager.target[i].socket);
                        }
                }
        }
@@ -412,7 +532,6 @@ void terminate_all()
 {
        int i;
        terminate_all_target();
-       samplingStop();
 
        // wait for all other thread exit
        for(i = 0; i < MAX_TARGET_COUNT; i++)
@@ -425,306 +544,22 @@ void terminate_all()
 }
 
 // terminate all profiling by critical error
-static void terminate_error(char* errstr, int sendtohost)
-{
-       msg_t log;
-
-       LOGE("TERMINATE ERROR: %s\n", errstr);
-       if(sendtohost)
-       {
-               log.type = MSG_ERROR;
-               log.length = sprintf(log.data, "%s", errstr);
-               sendDataToHost(&log);
-       }
-
-       terminate_all();
-}
-
-// ===========================================================================================
-// message parsing and handling functions
-// ===========================================================================================
-
-static int parseDeviceMessage(msg_t* log)
+// TODO: don't send data to host
+static void terminate_error(char* errstr, int send_to_host)
 {
-       char eventType[MAX_FILENAME];
-       struct input_event in_ev;
-       int i, index;
-
-       if(log == NULL)
-               return -1;
-
-       eventType[0] = '\0';
-       in_ev.type = 0;
-       in_ev.code = 0;
-       in_ev.value = 0;
-
-       index = 0;
-       for(i = 0; i < log->length; i++)
-       {
-               if(log->data[i] == '\n')
-                       break;
-
-               if(log->data[i] == '`') // meet separate
-               {
-                       i++;
-                       index++;
-                       continue;
-               }
-
-               if(index == 0)          // parse eventType
-               {
-                       eventType[i] = log->data[i];
-                       eventType[i+1] = '\0';
-               }
-               else if(index == 1)     // parse in_ev.type
-               {
-                       in_ev.type = in_ev.type * 10 + (log->data[i] - '0');
-               }
-               else if(index == 2)     // parse in_ev.code
-               {
-                       in_ev.code = in_ev.code * 10 + (log->data[i] - '0');
-               }
-               else if(index == 3)     // parse in_ev.value
-               {
-                       in_ev.value = in_ev.value * 10 + (log->data[i] - '0');
+       LOGE("termination all with err '%s'\n", errstr);
+       struct msg_data_t *msg = NULL;
+       if (send_to_host != 0){
+               msg = gen_message_error(errstr);
+               if (msg) {
+                       write_to_buf(msg);
+                       free_msg_data(msg);
+               } else {
+                       LOGI("cannot generate error message\n");
                }
        }
-
-       if(index != 3)
-               return -1;      // parse error
-
-       if(0 == strncmp(eventType, STR_TOUCH, strlen(STR_TOUCH)))
-       {
-               _device_write(g_touch_dev, &in_ev);
-       }
-       else if(0 == strncmp(eventType, STR_KEY, strlen(STR_KEY)))
-       {
-               _device_write(g_key_dev, &in_ev);
-       }
-
-       return 0;
-}
-
-// return 0 if normal case
-// return plus value if non critical error occur
-// return minus value if critical error occur
-static int _hostMessageHandler(int efd,struct msg_t* log)
-{
-/*     int ret = 0; */
-       
-/*     long flag = 0; */
-/*     char *barloc, *tmploc; */
-/*     char execPath[PATH_MAX]; */
-
-/*     if (log == NULL) */
-/*             return 1; */
-
-/*     switch (log->type) */
-/*     { */
-/*     case MSG_REPLAY: */
-/*             sendACKStrToHost(MSG_OK, NULL); */
-/*             parseDeviceMessage(log); */
-/*             break; */
-/*     case MSG_VERSION: */
-/*             if(strcmp(PROTOCOL_VERSION, log->data) != 0) */
-/*             { */
-/*                     sendACKCodeToHost(MSG_NOTOK, ERR_WRONG_PROTOCOL_VERSION); */
-/*             } */
-/*             else */
-/*             { */
-/*                     sendACKStrToHost(MSG_OK, NULL); */
-/*             } */
-/*             break; */
-/*     case MSG_START: */
-/*             LOGI("MSG_START handling : %s\n", log->data); */
-/*             if(log->length == 0) */
-/*             { */
-/*                     sendACKCodeToHost(MSG_NOTOK, ERR_WRONG_MESSAGE_DATA); */
-/*                     return -1;              // wrong message format */
-/*             } */
-
-/*             // parsing for host start status */
-/*             tmploc  = log->data; */
-/*             barloc = strchr(tmploc, '|'); */
-/*             if(barloc == NULL) */
-/*             { */
-/*                     sendACKCodeToHost(MSG_NOTOK, ERR_WRONG_MESSAGE_FORMAT); */
-/*                     return -1;              // wrong message format */
-/*             } */
-
-/*             // parsing for target launch option flag */
-/*             tmploc = barloc + 1; */
-/*             barloc = strchr(tmploc, '|'); */
-/*             if(barloc != NULL) */
-/*             { */
-/*                     while(tmploc < barloc) */
-/*                     { */
-/*                             flag = (flag * 10) + (*tmploc - '0'); */
-/*                             tmploc++; */
-/*                     } */
-/*             } */
-/*             else */
-/*             { */
-/*                     sendACKCodeToHost(MSG_NOTOK, ERR_WRONG_MESSAGE_FORMAT); */
-/*                     return -1;      // wrong message format */
-/*             } */
-/*             LOGI("launch flag : %lx\n", flag); */
-
-/*             // parsing for application package name */
-/*             tmploc = barloc + 1; */
-/*             strcpy(manager.appPath, tmploc); */
-
-/*             get_executable(manager.appPath, execPath, PATH_MAX); // get exact app executable file name */
-/*             LOGI("executable app path %s\n", manager.appPath); */
-
-/* #ifdef RUN_APP_LOADER */
-/*             kill_app(manager.appPath); */
-/* #else */
-/*             kill_app(execPath); */
-/* #endif */
-
-/*             { */
-/*                     char command[PATH_MAX]; */
-/*                     struct epoll_event ev; */
-
-/*                     //save app install path */
-/*                     mkdir(DA_WORK_DIR, 0775); */
-/*                     sprintf(command, */
-/*                                     "%s -Wwi %s | grep DW_AT_comp_dir > %s", DA_READELF_PATH, */
-/*                                     execPath, DA_INSTALL_PATH); */
-/*                     LOGI("appInstallCommand %s\n", command); */
-/*                     system(command); */
-
-/*                     sprintf(command, */
-/*                                     "%s -h %s | grep Type | cut -d\" \" -f33 > %s", DA_READELF_PATH, */
-/*                                     execPath, DA_BUILD_OPTION); */
-/*                     LOGI("appInstallCommand %s\n", command); */
-/*                     system(command); */
-
-/*                     if(startProfiling(flag) < 0) */
-/*                     { */
-/*                             sendACKCodeToHost(MSG_NOTOK, ERR_CANNOT_START_PROFILING); */
-/*                             return -1; */
-/*                     } */
-
-/*                     manager.app_launch_timerfd = timerfd_create(CLOCK_REALTIME, TFD_CLOEXEC); */
-/*                     if(manager.app_launch_timerfd > 0) */
-/*                     { */
-/*                             struct itimerspec ctime; */
-/*                             ctime.it_value.tv_sec = MAX_APP_LAUNCH_TIME; */
-/*                             ctime.it_value.tv_nsec = 0; */
-/*                             ctime.it_interval.tv_sec = 0; */
-/*                             ctime.it_interval.tv_nsec = 0; */
-/*                             if(0 > timerfd_settime(manager.app_launch_timerfd, 0, &ctime, NULL)) */
-/*                             { */
-/*                                     LOGE("fail to set app launch timer\n"); */
-/*                                     close(manager.app_launch_timerfd); */
-/*                                     manager.app_launch_timerfd = -1; */
-/*                             } */
-/*                             else */
-/*                             { */
-/*                                     // add event fd to epoll list */
-/*                                     ev.events = EPOLLIN; */
-/*                                     ev.data.fd = manager.app_launch_timerfd; */
-/*                                     if(epoll_ctl(efd, EPOLL_CTL_ADD, manager.app_launch_timerfd, &ev) < 0) */
-/*                                     { */
-/*                                             // fail to add event fd */
-/*                                             LOGE("fail to add app launch timer fd to epoll list\n"); */
-/*                                             close(manager.app_launch_timerfd); */
-/*                                             manager.app_launch_timerfd = -1; */
-/*                                     } */
-/*                             } */
-/*                     } */
-/*             } */
-/*             sendACKStrToHost(MSG_OK, NULL); */
-/*             break; */
-/*     case MSG_STOP: */
-/*             LOGI("MSG_STOP handling\n"); */
-/*             sendACKStrToHost(MSG_OK, NULL); */
-/*             terminate_all(); */
-/*             break; */
-/*     case MSG_OPTION: */
-/*             if(log->length > 0) */
-/*             { */
-/*                     int i; */
-/*                     msg_t sendlog; */
-/*                     manager.config_flag = atoi(log->data); */
-/*                     sendACKStrToHost(MSG_OK, NULL); */
-
-/*                     LOGI("MSG_OPTION : str(%s), flag(%x)\n", log->data, manager.config_flag); */
-
-/*                     sendlog.type = MSG_OPTION; */
-/*                     sendlog.length = sprintf(sendlog.data, "%u", manager.config_flag); */
-
-/*                     for(i = 0; i < MAX_TARGET_COUNT; i++) */
-/*                     { */
-/*                             if(manager.target[i].socket != -1) */
-/*                             { */
-/*                                     send(manager.target[i].socket, &sendlog, sizeof(sendlog.type) + sizeof(sendlog.length) + sendlog.length, MSG_NOSIGNAL); */
-/*                             } */
-/*                     } */
-/*             } */
-/*             else */
-/*             { */
-/*                     sendACKCodeToHost(MSG_NOTOK, ERR_WRONG_MESSAGE_DATA); */
-/*                     ret = 1; */
-/*             } */
-/*             break; */
-/*     case MSG_ISALIVE: */
-/*             sendACKStrToHost(MSG_OK, NULL); */
-/*             break; */
-/*     default: */
-/*             LOGW("Unknown msg\n"); */
-/*             sendACKCodeToHost(MSG_NOTOK, ERR_WRONG_MESSAGE_TYPE); */
-/*             ret = 1; */
-/*             break; */
-/*     } */
-/*     return ret; */
-}
-
-// ========================================================================================
-// socket and event_fd handling functions
-// ========================================================================================
-
-// return 0 if normal case
-// return plus value if non critical error occur
-// return minus value if critical error occur
- /*
-static int deviceEventHandler(input_dev* dev, int input_type)
-{
-       int ret = 0;
-       struct input_event in_ev;
-       msg_t log;
-
-       if(input_type == INPUT_ID_TOUCH)
-       {
-               //touch read
-               read(dev->fd, &in_ev, sizeof(struct input_event));
-               log.type = MSG_RECORD;
-               log.length = sprintf(log.data, "%s`,%s`,%ld`,%ld`,%hu`,%hu`,%u",
-                               STR_TOUCH, dev->fileName, in_ev.time.tv_sec,
-                               in_ev.time.tv_usec, in_ev.type, in_ev.code, in_ev.value);
-               sendDataToHost(&log);
-       }
-       else if(input_type == INPUT_ID_KEY)
-       {
-               //key read
-               read(dev->fd, &in_ev, sizeof(struct input_event));
-               log.type = MSG_RECORD;
-               log.length = sprintf(log.data, "%s`,%s`,%ld`,%ld`,%hu`,%hu`,%u",
-                               STR_KEY, dev->fileName, in_ev.time.tv_sec,
-                               in_ev.time.tv_usec, in_ev.type, in_ev.code, in_ev.value);
-               sendDataToHost(&log);
-       }
-       else
-       {
-               LOGW("unknown input_type\n");
-               ret = 1;
-       }
-
-       return ret;
+       terminate_all();
 }
-*/
 
 #define MAX_EVENTS_NUM 10
 static int deviceEventHandler(input_dev* dev, int input_type)
@@ -738,24 +573,25 @@ static int deviceEventHandler(input_dev* dev, int input_type)
        if(input_type == INPUT_ID_TOUCH || input_type == INPUT_ID_KEY)
        {
                do {
-//                     LOGI(">read %s events\n,", input_type==INPUT_ID_KEY?STR_KEY:STR_TOUCH);
                        size = read(dev->fd, &in_ev[count], sizeof(*in_ev) );
-//                     LOGI("<read %s events : size = %d\n,", input_type==INPUT_ID_KEY?STR_KEY:STR_TOUCH,size);
                        if (size >0)
                                count++;
                } while (count < MAX_EVENTS_NUM && size > 0);
 
-               if(count != 0){
-                       LOGI("readed %d %s events\n", count, input_type==INPUT_ID_KEY?STR_KEY:STR_TOUCH);
+               if (count) {
+                       LOGI("read %d %s events\n",
+                            count,
+                            input_type == INPUT_ID_KEY ? STR_KEY : STR_TOUCH);
                        log = gen_message_event(in_ev, count, input_type);
-                       pseudoSendDataToHost(log);
-                       reset_data_msg(log);
+                       printBuf((char *)log, MSG_DATA_HDR_LEN + log->len);
+                       write_to_buf(log);
+                       free_msg_data(log);
                }
        }
        else
        {
                LOGW("unknown input_type\n");
-               ret = 1;
+               ret = 1; // it is not error
        }
        return ret;
 }
@@ -768,18 +604,37 @@ static int targetEventHandler(int epollfd, int index, uint64_t msg)
 {
        if(msg & EVENT_PID)
        {
+               if (index == 0) { // main application
+
+                       if ( is_same_app_process(prof_session.app_info.exe_path,
+                                               manager.target[index].pid) == 0 ) {
+                               LOGE("is same error: '%s' is not %d\n",
+                                               prof_session.app_info.exe_path,
+                                               manager.target[index].pid);
+                               return -1;
+                       }
+
+                       if (start_replay() != 0) {
+                               LOGE("Cannot start replay thread\n");
+                               return -1;
+                       }
+               }
                manager.target[index].initial_log = 1;
        }
 
        if(msg & EVENT_STOP || msg & EVENT_ERROR)
        {
                LOGI("target close, socket(%d), pid(%d) : (remaining %d target)\n",
-                               manager.target[index].socket, manager.target[index].pid, manager.target_count - 1);
-
-               terminate_target(index);
+                    manager.target[index].socket,
+                    manager.target[index].pid,
+                    manager.target_count - 1);
+               if (index == 0) { // main application
+                       stop_replay();
+               }
                epoll_ctl(epollfd, EPOLL_CTL_DEL, manager.target[index].event_fd, NULL);
                setEmptyTargetSlot(index);
-               if (0 == __sync_sub_and_fetch(&manager.target_count, 1)) // all target client are closed
+               // all target client are closed
+               if (0 == __sync_sub_and_fetch(&manager.target_count, 1))
                        return -11;
        }
 
@@ -791,7 +646,7 @@ static int targetEventHandler(int epollfd, int index, uint64_t msg)
 // return minus value if critical error occur
 static int targetServerHandler(int efd)
 {
-       msg_t log;
+       msg_target_t log;
        struct epoll_event ev;
 
        int index = getEmptyTargetSlot();
@@ -801,7 +656,8 @@ static int targetServerHandler(int efd)
                return 1;
        }
 
-       manager.target[index].socket = accept(manager.target_server_socket, NULL, NULL);
+       manager.target[index].socket =
+               accept(manager.target_server_socket, NULL, NULL);
 
        if(manager.target[index].socket >= 0)   // accept succeed
        {
@@ -813,15 +669,19 @@ static int targetServerHandler(int efd)
 
                // send config message to target process
                log.type = MSG_OPTION;
-               log.length = sprintf(log.data, "%u", manager.config_flag);
-               send(manager.target[index].socket, &log, sizeof(log.type) + sizeof(log.length) + log.length, MSG_NOSIGNAL);
+               log.length = sprintf(log.data, "%lu",
+                                    (unsigned long int) prof_session.conf.use_features0);
+               send(manager.target[index].socket, &log,
+                    sizeof(log.type) + sizeof(log.length) + log.length,
+                    MSG_NOSIGNAL);
 
                // make event fd
                manager.target[index].event_fd = eventfd(0, EFD_NONBLOCK);
                if(manager.target[index].event_fd == -1)
                {
                        // fail to make event fd
-                       LOGE("fail to make event fd for socket (%d)\n", manager.target[index].socket);
+                       LOGE("fail to make event fd for socket (%d)\n",
+                                       manager.target[index].socket);
                        goto TARGET_CONNECT_FAIL;
                }
 
@@ -831,7 +691,8 @@ static int targetServerHandler(int efd)
                if(epoll_ctl(efd, EPOLL_CTL_ADD, manager.target[index].event_fd, &ev) < 0)
                {
                        // fail to add event fd
-                       LOGE("fail to add event fd to epoll list for socket (%d)\n", manager.target[index].socket);
+                       LOGE("fail to add event fd to epoll list for socket (%d)\n",
+                                       manager.target[index].socket);
                        goto TARGET_CONNECT_FAIL;
                }
 
@@ -839,16 +700,17 @@ static int targetServerHandler(int efd)
                if(makeRecvThread(index) != 0)
                {
                        // fail to make recv thread
-                       LOGE("fail to make recv thread for socket (%d)\n", manager.target[index].socket);
+                       LOGE("fail to make recv thread for socket (%d)\n",
+                                       manager.target[index].socket);
                        epoll_ctl(efd, EPOLL_CTL_DEL, manager.target[index].event_fd, NULL);
                        goto TARGET_CONNECT_FAIL;
                }
 
                if(manager.app_launch_timerfd >= 0)
                {
-                       epoll_ctl(efd, EPOLL_CTL_DEL, manager.app_launch_timerfd, NULL);
-                       close(manager.app_launch_timerfd);
-                       manager.app_launch_timerfd = -1;
+                       LOGI("release launch timer\n");
+                       if (stop_app_launch_timer()<0)
+                               LOGE("cannot stop app launch timer\n");
                }
 
                LOGI("target connected = %d(running %d target)\n",
@@ -867,8 +729,9 @@ TARGET_CONNECT_FAIL:
        {
                return -1;
        }
-       else    // if this connection is not main connection then ignore process by error
+       else
        {
+               // if this connection is not main connection then ignore process by error
                setEmptyTargetSlot(index);
                return 1;
        }
@@ -922,41 +785,7 @@ static int hostServerHandler(int efd)
        }
 }
 
-#ifdef DEB_PRINTBUF
-//TODO del it or move to debug section
-void printBuf (char * buf, int len)
-{
-
-       int i,j;
-       char local_buf[3*16 + 2*16 + 1];
-       char * p1, * p2;
-       LOGI("BUFFER:\n");
-       for ( i = 0; i < len/16 + 1; i++)
-       {
-               memset(local_buf, ' ', 5*16);
-               p1 = local_buf;
-               p2 = local_buf + 3*17;
-               for ( j = 0; j < 16; j++)
-                       if (i*16+j < len )
-                       {
-                               sprintf(p1, "%02X ",(unsigned char) *buf);
-                               p1+=3;
-                               if (isprint( *buf)){
-                                       sprintf(p2, "%c ",(int)*buf);
-                               }else{
-                                       sprintf(p2,". ");
-                               }
-                               p2+=2;
-                               buf++;
-                       }
-               *p1 = ' ';
-               *p2 = '\0';
-               LOGI("%s\n",local_buf);
-       }
-}
-#else
 
-#endif
 // return 0 if normal case
 // return plus value if non critical error occur
 // return minus value if critical error occur
@@ -964,114 +793,158 @@ void printBuf (char * buf, int len)
 
 static int controlSocketHandler(int efd)
 {
-       ssize_t recvLen;
-       char recvBuf[DA_MSG_MAX];
-       msg_t log;
+       ssize_t recv_len;
+       struct msg_t msg_head;
+       struct msg_t *msg;
+       int res = 0;
 
-       // host log format xxx|length|str
-       recvLen = recv(manager.host.control_socket, recvBuf, DA_MSG_MAX, 0);
-
-       if (recvLen > 0)
+       if(manager.connect_timeout_timerfd >= 0)
        {
-               recvBuf[recvLen] = '\0';
-               printBuf(recvBuf,recvLen);
-               LOGI("host sent control msg str(%s)\n", recvBuf);
-               if(parseHostMessage(&log, recvBuf) < 0)
-               {
-                       // error to parse host message
-                       sendACKCodeToHost(MSG_NOTOK, ERR_WRONG_MESSAGE_FORMAT);
-                       return 1;
+               LOGI("release connect timeout timer\n");
+               epoll_ctl(efd, EPOLL_CTL_DEL, manager.connect_timeout_timerfd, NULL);
+               close(manager.connect_timeout_timerfd);
+               manager.connect_timeout_timerfd = -1;
+       }
+
+       // Receive header
+       recv_len = recv(manager.host.control_socket,
+                      &msg_head,
+                      MSG_CMD_HDR_LEN, 0);
+       // error or close request from host
+       if (recv_len == -1 || recv_len == 0)
+               return -11;
+       else {
+               msg = malloc(MSG_CMD_HDR_LEN + msg_head.len);
+               if (!msg) {
+                       LOGE("Cannot alloc msg\n");
+                       sendACKToHost(msg_head.id, ERR_WRONG_MESSAGE_FORMAT, 0, 0);
+                       return -1;
+               }
+               msg->id = msg_head.id;
+               msg->len = msg_head.len;
+               if (msg->len > 0) {
+                       // Receive payload (if exists)
+                       recv_len = recv(manager.host.control_socket,
+                                       msg->payload,
+                                       msg->len, MSG_WAITALL);
+                       if (recv_len == -1)
+                               return -11;
                }
+               res = host_message_handler(msg);
+               free(msg);
+       }
+
+       return res;
+}
+
+static void epoll_add_input_events()
+{
+       struct epoll_event ev;
+       int i;
 
-               // host msg command handling
-               return hostMessageHandle(&log);
+       // add device fds to epoll event pool
+       ev.events = EPOLLIN;
+       for (i = 0; g_key_dev[i].fd != ARRAY_END; i++) {
+               if (g_key_dev[i].fd >= 0) {
+                       ev.data.fd = g_key_dev[i].fd;
+                       if (epoll_ctl(manager.efd,
+                                     EPOLL_CTL_ADD,
+                                     g_key_dev[i].fd, &ev) < 0)
+                               LOGE("keyboard device file epoll_ctl error\n");
+               }
        }
-       else    // close request from HOST
-       {
-               return -11;
+
+       ev.events = EPOLLIN;
+       for (i = 0; g_touch_dev[i].fd != ARRAY_END; i++) {
+               if (g_touch_dev[i].fd >= 0) {
+                       ev.data.fd = g_touch_dev[i].fd;
+                       if (epoll_ctl(manager.efd,
+                                     EPOLL_CTL_ADD,
+                                     g_touch_dev[i].fd, &ev) < 0)
+                               LOGE("touch device file epoll_ctl error\n");
+               }
        }
 }
 
-// return 0 for normal case
-int daemonLoop()
+static void epoll_del_input_events()
 {
-       int                     ret = 0;                                // return value
-       int                     i, k;
-       ssize_t         recvLen;
+       int i;
 
-       struct epoll_event ev, *events;
-       int efd;                // epoll fd
-       int numevent;   // number of occured events
+       // remove device fds from epoll event pool
+       for (i = 0; g_key_dev[i].fd != ARRAY_END; i++)
+               if (g_key_dev[i].fd >= 0)
+                       if (epoll_ctl(manager.efd,
+                                     EPOLL_CTL_DEL,
+                                     g_key_dev[i].fd, NULL) < 0)
+                               LOGE("keyboard device file epoll_ctl error\n");
 
-       _get_fds(g_key_dev, INPUT_ID_KEY);
-       _get_fds(g_touch_dev, INPUT_ID_TOUCH);
+       for (i = 0; g_touch_dev[i].fd != ARRAY_END; i++)
+               if (g_touch_dev[i].fd >= 0)
+                       if (epoll_ctl(manager.efd,
+                                     EPOLL_CTL_DEL,
+                                     g_touch_dev[i].fd, NULL) < 0)
+                               LOGE("touch device file epoll_ctl error\n");
+}
+static bool initialize_epoll_events(void)
+{
+       struct epoll_event ev;
 
-       // initialize epoll event pool
-       events = (struct epoll_event*) malloc(sizeof(struct epoll_event) * EPOLL_SIZE);
-       if(events == NULL)
-       {
-               LOGE("Out of memory when allocate epoll event pool\n");
-               ret = -1;
-               goto END_RETURN;
-       }
-       if((efd = epoll_create(MAX_CONNECT_SIZE)) < 0)
-       {
-               LOGE("epoll creation error\n");
-               ret = -1;
-               goto END_EVENT;
+       if ((manager.efd = epoll_create1(0)) < 0) {
+         LOGE("epoll creation error\n");
+         return false;
        }
 
        // add server sockets to epoll event pool
        ev.events = EPOLLIN;
        ev.data.fd = manager.host_server_socket;
-       if(epoll_ctl(efd, EPOLL_CTL_ADD, manager.host_server_socket, &ev) < 0)
+       if (epoll_ctl(manager.efd, EPOLL_CTL_ADD,
+                    manager.host_server_socket, &ev) < 0)
        {
                LOGE("Host server socket epoll_ctl error\n");
-               ret = -1;
-               goto END_EFD;
+               return false;
        }
        ev.events = EPOLLIN;
        ev.data.fd = manager.target_server_socket;
-       if(epoll_ctl(efd, EPOLL_CTL_ADD, manager.target_server_socket, &ev) < 0)
+       if (epoll_ctl(manager.efd, EPOLL_CTL_ADD,
+                     manager.target_server_socket, &ev) < 0)
        {
                LOGE("Target server socket epoll_ctl error\n");
-               ret = -1;
-               goto END_EFD;
+               return false;
        }
+       return true;
+}
 
-       // add device fds to epoll event pool
-       ev.events = EPOLLIN;
-       for(i = 0; g_key_dev[i].fd != ARRAY_END; i++)
-       {
-               if(g_key_dev[i].fd >= 0)
-               {
-                       ev.data.fd = g_key_dev[i].fd;
-                       if(epoll_ctl(efd, EPOLL_CTL_ADD, g_key_dev[i].fd, &ev) < 0)
-                       {
-                               LOGE("keyboard device file epoll_ctl error\n");
-                       }
-               }
-       }
+// return 0 for normal case
+int daemonLoop()
+{
+       int return_value = 0;
+       struct epoll_event *events = malloc(EPOLL_SIZE * sizeof(*events));
 
-       ev.events = EPOLLIN;
-       for(i = 0; g_touch_dev[i].fd != ARRAY_END; i++)
-       {
-               if(g_touch_dev[i].fd >= 0)
-               {
-                       ev.data.fd = g_touch_dev[i].fd;
-                       if(epoll_ctl(efd, EPOLL_CTL_ADD, g_touch_dev[i].fd, &ev) < 0)
-                       {
-                               LOGE("touch device file epoll_ctl error\n");
-                       }
-               }
+       _get_fds(g_key_dev, INPUT_ID_KEY);
+       _get_fds(g_touch_dev, INPUT_ID_TOUCH);
+
+       if (!events) {
+               LOGE("Out of memory when allocate epoll event pool\n");
+               return_value = -1;
+               goto END_EVENT;
+       }
+       if (!initialize_epoll_events()) {
+               return_value = -1;
+               goto END_EFD;
        }
 
+       if (launch_timer_start() < 0) {
+               LOGE("Launch timer start failed\n");
+               return_value = -1;
+               goto END_EFD;
+       }
        // handler loop
-       while (1)
-       {
-               numevent = epoll_wait(efd, events, EPOLL_SIZE, -1);
-               if(numevent <= 0)
-               {
+       while (1) {
+               int i, k;
+               ssize_t recvLen;
+               // number of occured events
+               int numevent = epoll_wait(manager.efd, events, EPOLL_SIZE, -1);
+               if (numevent <= 0) {
                        LOGE("Failed to epoll_wait : num of event(%d), errno(%d)\n", numevent, errno);
                        continue;
                }
@@ -1088,16 +961,15 @@ int daemonLoop()
                                        recvLen = read(manager.target[k].event_fd, &u, sizeof(uint64_t));
                                        if(recvLen != sizeof(uint64_t))
                                        {
-                                               // maybe closed, but ignoring is more safe then removing fd from epoll list
+                                               // maybe closed, but ignoring is more safe then
+                                               // removing fd from epoll list
                                        }
                                        else
                                        {
-                                               if(-11 == targetEventHandler(efd, k, u))
+                                               if(-11 == targetEventHandler(manager.efd, k, u))
                                                {
                                                        LOGI("all target process is closed\n");
-                                                       terminate_all();
-                                                       ret = 0;
-                                                       goto END_EFD;
+                                                       continue;
                                                }
                                        }
                                        break;
@@ -1115,9 +987,9 @@ int daemonLoop()
                                {
                                        if(deviceEventHandler(&g_touch_dev[k], INPUT_ID_TOUCH) < 0)
                                        {
-                                               terminate_error("Internal DA framework error, Please re-run the profiling.", 1);
-                                               ret = -1;
-                                               goto END_EFD;
+                                               LOGE("Internal DA framework error, "
+                                                        "Please re-run the profiling (touch dev)\n");
+                                               continue;
                                        }
                                        break;
                                }
@@ -1133,9 +1005,9 @@ int daemonLoop()
                                {
                                        if(deviceEventHandler(&g_key_dev[k], INPUT_ID_KEY) < 0)
                                        {
-                                               terminate_error("Internal DA framework error, Please re-run the profiling.", 1);
-                                               ret = -1;
-                                               goto END_EFD;
+                                               LOGE("Internal DA framework error, "
+                                                        "Please re-run the profiling (key dev)\n");
+                                               continue;
                                        }
                                        break;
                                }
@@ -1145,67 +1017,82 @@ int daemonLoop()
                                continue;
 
                        // connect request from target
-                       if(events[i].data.fd == manager.target_server_socket)
+                       if (events[i].data.fd == manager.target_server_socket)
                        {
-                               if(targetServerHandler(efd) < 0)        // critical error
+                               if (targetServerHandler(manager.efd) < 0)       // critical error
                                {
-                                       terminate_error("Internal DA framework error, Please re-run the profiling.", 1);
-                                       ret = -1;
-                                       goto END_EFD;
+                                       terminate_error("Internal DA framework error, "
+                                                                       "Please re-run the profiling (targetServerHandler)\n", 1);
+                                       continue;
                                }
                        }
                        // connect request from host
-                       else if(events[i].data.fd == manager.host_server_socket)
+                       else if (events[i].data.fd == manager.host_server_socket)
                        {
-                               int result = hostServerHandler(efd);
-                               if(result < 0)
+                               int result = hostServerHandler(manager.efd);
+                               if (result < 0)
                                {
-                                       terminate_error("Internal DA framework error, Please re-run the profiling.", 1);
-                                       ret = -1;
-                                       goto END_EFD;
+                                       LOGE("Internal DA framework error (hostServerHandler)\n");
+                                       continue;
                                }
                        }
                        // control message from host
-                       else if(events[i].data.fd == manager.host.control_socket)
+                       else if (events[i].data.fd == manager.host.control_socket)
                        {
-                               int result = controlSocketHandler(efd);
-                               if(result == -11)       // socket close
+                               int result = controlSocketHandler(manager.efd);
+                               if (result == -11)      // socket close
                                {
-                                       // close target and host socket and quit
-                                       LOGI("host close = %d\n", manager.host.control_socket);
-                                       terminate_all();
-                                       ret = 0;
+                                       //if the host disconnected.
+                                       //In all other cases daemon must report an error and continue the loop
+                                       //close connect_timeoutt and host socket and quit
+                                       LOGI("Connection closed. Termination. (%d)\n",
+                                            manager.host.control_socket);
+                                       return_value = 0;
                                        goto END_EFD;
                                }
-                               else if(result < 0)
+                               else if (result < 0)
                                {
-                                       terminate_error("Internal DA framework error, Please re-run the profiling.", 1);
-                                       ret = -1;
+                                       terminate_error("Internal DA framework error, "
+                                                       "Please re-run the profiling.", 1);
+                                       return_value = -1;
                                        goto END_EFD;
                                }
                        }
-                       else if(events[i].data.fd == manager.host.data_socket)
+                       else if (events[i].data.fd == manager.host.data_socket)
                        {
                                char recvBuf[32];
                                recvLen = recv(manager.host.data_socket, recvBuf, 32, MSG_DONTWAIT);
-                               if(recvLen == 0)
+                               if (recvLen == 0)
                                {       // close data socket
-                                       epoll_ctl(efd, EPOLL_CTL_DEL, manager.host.data_socket, NULL);
+                                       epoll_ctl(manager.efd, EPOLL_CTL_DEL,
+                                                 manager.host.data_socket,
+                                                 NULL);
                                        close(manager.host.data_socket);
                                        manager.host.data_socket = -1;
+                                       // TODO: finish transfer thread
                                }
-       
-                               LOGW("host message from data socket %d\n", recvLen);
+
+                               LOGI("host message from data socket %d\n", recvLen);
                        }
                        // check for application launch timerfd
-                       else if(events[i].data.fd == manager.app_launch_timerfd)
+                       else if (events[i].data.fd == manager.app_launch_timerfd)
                        {
                                // send to host timeout error message for launching application
-                               terminate_error("Failed to launch application", 1);
-                               epoll_ctl(efd, EPOLL_CTL_DEL, manager.app_launch_timerfd, NULL);
-                               close(manager.app_launch_timerfd);
-                               manager.app_launch_timerfd = -1;
-                               ret = -1;
+                               LOGE("Failed to launch application\n");
+                               if (stop_app_launch_timer()<0)
+                                       LOGE("cannot stop app launch timer\n");
+                               continue;
+                       }
+                       // check for connection timeout timerfd
+                       else if (events[i].data.fd == manager.connect_timeout_timerfd)
+                       {
+                               // send to host timeout error message for launching application
+                               terminate_error("no incoming connections", 1);
+                               epoll_ctl(manager.efd, EPOLL_CTL_DEL,
+                                         manager.connect_timeout_timerfd, NULL);
+                               close(manager.connect_timeout_timerfd);
+                               manager.connect_timeout_timerfd = -1;
+                               LOGE("No connection in %d sec. shutdown.\n",MAX_CONNECT_TIMEOUT_TIME);
                                goto END_EFD;
                        }
                        // unknown socket
@@ -1218,9 +1105,9 @@ int daemonLoop()
        }
 
 END_EFD:
-       close(efd);
+       LOGI("close efd\n");
+       close(manager.efd);
 END_EVENT:
        free(events);
-END_RETURN:
-       return ret;
+       return return_value;
 }