Add core abi capability
[sdk/target/sdbd.git] / src / sdb.c
old mode 100644 (file)
new mode 100755 (executable)
index e282ced..7b33f8a
--- a/src/sdb.c
+++ b/src/sdb.c
@@ -14,7 +14,8 @@
  * limitations under the License.
  */
 
-#define  TRACE_TAG   TRACE_SDB
+//#define  TRACE_TAG   TRACE_SDB
+#define LOG_TAG "SDBD_TRACE_SDB"
 
 #include <stdio.h>
 #include <stdlib.h>
 #include <tzplatform_config.h>
 #include <pthread.h>
 #include <dlfcn.h>
+#include <sys/smack.h>
 
 #include "sysdeps.h"
 #include "log.h"
 #include "sdb.h"
 #include "strutils.h"
-#if !SDB_HOST
 #include "commandline_sdbd.h"
-#endif
 #include "utils.h"
 #include "sdktools.h"
 #include "plugin.h"
 #include "sdbd_plugin.h"
+#include "sdb_systemd.h"
 
-#if !SDB_HOST
-#include <linux/prctl.h>
-#define SDB_PIDPATH "/tmp/.sdbd.pid"
+#ifdef SUPPORT_ENCRYPT
+#include "plugin_encrypt.h"
 #endif
+
+#include <linux/prctl.h>
 #include <system_info.h>
 #include <vconf.h>
 #include <glib.h>
 
 #define PROC_CMDLINE_PATH "/proc/cmdline"
 #define USB_SERIAL_PATH "/sys/class/usb_mode/usb0/iSerial"
+#define APPID2PID_PATH  "/usr/bin/appid2pid"
 
 #include <sys/ioctl.h>
 #include <net/if.h>
@@ -66,7 +69,12 @@ SDB_MUTEX_DEFINE(zone_check_lock);
 SDB_MUTEX_DEFINE( D_lock );
 #endif
 
+#define SDB_LOGCONF_PATH "/tmp/.sdbdlog.conf"
+
 int HOST = 0;
+int exit_cleanup_required = 0;
+
+// sdk user
 uid_t g_sdk_user_id;
 gid_t g_sdk_group_id;
 char* g_sdk_home_dir = NULL;
@@ -75,6 +83,12 @@ pcap g_capabilities;
 int rootshell_mode; // 0: sdk user, 1: root
 int booting_done; // 0: platform booting is in progess 1: platform booting is done
 
+// root user
+uid_t g_root_user_id;
+gid_t g_root_group_id;
+char* g_root_home_dir = NULL;
+char* g_root_home_dir_env = NULL;
+
 struct group_info
 {
     const char *name;
@@ -87,14 +101,16 @@ struct group_info g_default_groups[] = {
     {"log", -1},
     {NULL, -1}
 };
+
 #define SDB_DEFAULT_GROUPS_CNT  ((sizeof(g_default_groups)/sizeof(g_default_groups[0]))-1)
+#define BUF_SIZE 4096
 
 int is_init_sdk_userinfo = 0;
 int is_pwlocked = 0;    // 0 if unlocked, 1 otherwise
 
-#if !SDB_HOST
+int recovery_mode = 0;
+
 SdbdCommandlineArgs sdbd_commandline_args;
-#endif
 
 static int is_support_usbproto();
 static int is_support_sockproto();
@@ -108,9 +124,6 @@ void (*usb_kick)(usb_handle *h) = NULL;
 
 int g_is_emulator = -1;
 int is_emulator(void) {
-#if SDB_HOST
-    return 0;
-#else
     if (g_is_emulator >= 0) {
         return g_is_emulator;
     } else {
@@ -118,7 +131,64 @@ int is_emulator(void) {
     }
 
     return sdbd_commandline_args.emulator.host != NULL;
-#endif
+}
+
+int is_appid2pid_supported(void) {
+
+    if (access(APPID2PID_PATH, F_OK) == 0) {
+        /* It is necessary to confirm that it is possible
+         * to run "appid2pid" in the sdk user/group privileges. */
+        struct stat st;
+        if (stat(APPID2PID_PATH, &st) == 0) {
+            D("appid2pid uid=%d, gid=%d, mode=0x%x.\n", st.st_uid, st.st_gid, st.st_mode);
+            if ( (st.st_uid == STATIC_SDK_USER_ID && st.st_mode & S_IXUSR)
+                || (st.st_gid == STATIC_SDK_GROUP_ID && st.st_mode & S_IXGRP)
+                || (st.st_mode & S_IXOTH) ) {
+                D("appid2pid is supported.\n");
+                return 1;
+            }
+        }
+    } else {
+        D("failed to access appid2pid file: %d\n", errno);
+    }
+
+    D("appid2pid is NOT supported.\n");
+    return 0;
+}
+
+int is_netcoredbg_supported(void) {
+
+    FILE *fp = fopen(NETCOREDBG_LOCATION, "r");
+    if (fp) {
+        size_t len;
+        ssize_t num;
+        char *line = NULL;
+
+        while ((num = getline(&line, &len, fp)) != -1) {
+            if (strstr(line, "NETCOREDBG") != NULL) {
+                snprintf(g_capabilities.netcoredbg_support, sizeof(g_capabilities.netcoredbg_support),
+                         "%s", ENABLED);
+                free(line);
+                fclose(fp);
+                return 1;
+            }
+            free(line);
+            line = NULL;
+        }
+        fclose(fp);
+    }
+    return 0;
+}
+
+const char* get_platfrom_architecture(void) {
+    void* void_pointer;
+    D("void pointer size:  %zu", sizeof(void_pointer));
+    // in 32 bit sizeof void* is 4 and in 64 bit its 8
+    if((int)(sizeof(void_pointer)) == 4)
+        return BIT32;
+    if((int)(sizeof(void_pointer)) == 8)
+        return BIT64;
+    return UNKNOWN;
 }
 
 int is_container_enabled(void) {
@@ -126,7 +196,7 @@ int is_container_enabled(void) {
     int ret;
     ret = system_info_get_platform_bool("tizen.org/feature/container", &value);
     if (ret != SYSTEM_INFO_ERROR_NONE) {
-        D("failed to get container information: %d\n", errno);
+        E("failed to get container information: %d\n", errno);
         return 0;
     } else {
         D("tizen container: %d\n", value);
@@ -137,12 +207,6 @@ int is_container_enabled(void) {
     }
 }
 
-void handle_sig_term(int sig) {
-#ifdef SDB_PIDPATH
-    if (access(SDB_PIDPATH, F_OK) == 0)
-        sdb_unlink(SDB_PIDPATH);
-#endif
-}
 
 static const char *sdb_device_banner = "device";
 
@@ -168,9 +232,47 @@ void fatal_errno(const char *fmt, ...)
     exit(-1);
 }
 
+static char* get_sdb_log_conf(const char* key)
+{
+    int fd;
+    char line[256] = {0,};
+    char value[256] = {0,};
+
+    if (access(SDB_LOGCONF_PATH, F_OK)) {
+        return NULL;
+    }
+
+    fd = unix_open(SDB_LOGCONF_PATH, O_RDONLY);
+    if (fd < 0) {
+        E("failed to open '%s' file: %d\n", SDB_LOGCONF_PATH, errno);
+        return NULL;
+    }
+
+    if (read_line(fd, line, sizeof(line)) > 0) {
+        char* start = strstr(line, key);
+        if (start != NULL) {
+            // move one more character to remove '=',
+            // including the length of the key string
+            start = start + strlen(key) + 1;
+            char* end = strstr(start, " ");
+            if (end != NULL) {
+                strncpy(value, start, end - start);
+            } else {
+                strncpy(value, start, sizeof(value) - 1);
+                value[sizeof(value) - 1] = '\0';
+            }
+        } else {
+            sdb_close(fd);
+            return NULL;
+        }
+    }
+    sdb_close(fd);
+    return strdup(value);
+}
+
 static int is_enable_sdbd_log()
 {
-    return (!strncmp(g_capabilities.log_enable, PLUGIN_RET_ENABLED, strlen(PLUGIN_RET_ENABLED)));
+    return (!strncmp(g_capabilities.log_enable, PLUGIN_RET_ENABLED, strlen(PLUGIN_RET_ENABLED)+1));
 }
 
 int   sdb_trace_mask;
@@ -182,7 +284,8 @@ int   sdb_trace_mask;
  */
 void  sdb_trace_init(void)
 {
-    const char*  p = getenv("SDB_TRACE");
+    char*  ptr = get_sdb_log_conf("SDB_TRACE");
+    const char*  p;
     const char*  q;
 
     static const struct {
@@ -207,11 +310,13 @@ void  sdb_trace_init(void)
         { NULL, 0 }
     };
 
-    if (p == NULL) {
+    if (ptr == NULL) {
         if (is_enable_sdbd_log())
             p = "all";
         else
             return;
+    } else {
+        p = ptr;
     }
 
     /* use a comma/column/semi-colum/space separated list */
@@ -233,6 +338,7 @@ void  sdb_trace_init(void)
                 int  flag = tags[tagn].flag;
                 if (flag == 0) {
                     sdb_trace_mask = ~0;
+                    free(ptr);
                     return;
                 }
                 sdb_trace_mask |= (1 << flag);
@@ -243,9 +349,9 @@ void  sdb_trace_init(void)
         if (*p)
             p++;
     }
+    free(ptr);
 }
 
-#if !SDB_HOST
 /*
  * Implements SDB tracing inside the emulator.
  */
@@ -270,46 +376,25 @@ void  sdb_trace_init(void)
 /* A handle to sdb-debug qemud service in the emulator. */
 int   sdb_debug_qemu = -1;
 
-/* Initializes connection with the sdb-debug qemud service in the emulator. */
-#if 0 /* doen't support in Tizen */
-static int sdb_qemu_trace_init(void)
-{
-    char con_name[32];
-
-    if (sdb_debug_qemu >= 0) {
-        return 0;
-    }
-
-    /* sdb debugging QEMUD service connection request. */
-    snprintf(con_name, sizeof(con_name), "qemud:sdb-debug");
-    sdb_debug_qemu = qemu_pipe_open(con_name);
-    return (sdb_debug_qemu >= 0) ? 0 : -1;
-}
-
-void sdb_qemu_trace(const char* fmt, ...)
-{
-    va_list args;
-    va_start(args, fmt);
-    char msg[1024];
-
-    if (sdb_debug_qemu >= 0) {
-        vsnprintf(msg, sizeof(msg), fmt, args);
-        sdb_write(sdb_debug_qemu, msg, strlen(msg));
-    }
-}
-#endif
-#endif  /* !SDB_HOST */
-
 apacket *get_apacket(void)
 {
     apacket *p = malloc(sizeof(apacket));
-    if(p == 0) fatal("failed to allocate an apacket");
+    if(p == 0) {
+        // free only being done to resolve SVACE issue.
+        free(p) ;
+        fatal("failed to allocate an apacket");
+    }
     memset(p, 0, sizeof(apacket) - MAX_PAYLOAD);
     return p;
 }
 
 void put_apacket(apacket *p)
 {
+    int result = access((const char *) p, F_OK);
+    if ((result == -1) && (errno == EFAULT)) {
+        E("Invalid apacket = [0x%p]", p);
+        fatal("Invalid apacket = [0x%p]", p);
+    }
     if (p != NULL) {
         free(p);
         p = NULL;
@@ -318,12 +403,12 @@ void put_apacket(apacket *p)
 
 void handle_online(void)
 {
-    D("sdb: online\n");
+    I("sdb: online\n");
 }
 
 void handle_offline(atransport *t)
 {
-    D("sdb: offline\n");
+    I("sdb: offline\n");
     //Close the associated usb
     run_transport_disconnects(t);
 }
@@ -368,9 +453,153 @@ void print_packet(const char *label, apacket *p)
 }
 #endif
 
+#ifdef SUPPORT_ENCRYPT
+/*
+desc. : 암호화 실패 메시지 전송
+parameter : [in] apacket* p : sdbd로 들어온 메시지
+            [in] atransport *t : 현재 연결에 대한 atransport
+            [in] unsigned failed_value : 실패 값
+*/
+void send_encr_fail(apacket* p, atransport *t, unsigned failed_value){
+    apacket* enc_p;
+    enc_p = get_apacket();
+    enc_p->msg.command = A_ENCR; // 암호화 메시지
+    enc_p->msg.arg0 = failed_value; // 실패값
+    enc_p->msg.arg1 = p->msg.arg1;
+    send_packet(enc_p, t);
+    //put_apacket(enc_p);
+}
+
+/*
+desc. : 암호화 메시지 핸들링
+parameter : [in] apacket* p : sdbd로 들어온 메시지
+            [in/out] atransport *t : 현재 연결에 대한 atransport
+ret : 0 : 정상적으로 메시지 전송
+      -1: 메시지 전송 실패
+*/
+int handle_encr_packet(apacket* p, atransport *t){
+    static int sessionID = 0;
+    int retVal = 0;
+    apacket* enc_p = NULL;
+
+    if(p->msg.arg0 == ENCR_SET_ON_REQ){ // hello 메시지인 경우
+        t->sessionID = sessionID;
+        if((retVal = security_init(t->sessionID, NULL)) == 1){ // 암호화 handshaking을 위한 init
+            if(security_parse_server_hello(t->sessionID, p) == 1){ // hello 메시지 파싱
+                I("security_parse_server_hello success\n");
+                enc_p = get_apacket();
+                if(security_gen_client_hello(t->sessionID, enc_p) == 1){ // hello 메시지 생성
+                    I("security_gen_client_hello success\n");
+                    enc_p->msg.command = A_ENCR;
+                    enc_p->msg.arg0 = ENCR_SET_ON_REQ;
+                    enc_p->msg.arg1 = p->msg.arg1;
+                    sessionID++;
+                    send_packet(enc_p, t);
+                }
+                else { // hello 메시지 생성 실패
+                    E("security_gen_client_hello error\n");
+                    send_encr_fail(p, t, ENCR_ON_FAIL); // 암호화 on 실패 메시지 전송
+                    t->encryption = ENCR_OFF; // 암호화 모드는 off
+                    security_deinit(t->sessionID);
+                    return -1;
+                }
+            }
+            else{ // hello 메시지 파싱 실패
+                E("security_parse_server_hello error\n");
+                send_encr_fail(p, t, ENCR_ON_FAIL);
+                t->encryption = ENCR_OFF;
+                security_deinit(t->sessionID);
+
+                return -1;
+            }
+        } else { // init 실패
+            E("security_init error\n");
+            send_encr_fail(p, t, ENCR_ON_FAIL);
+            t->encryption = ENCR_OFF;
+            if (retVal == 0)
+            {
+                security_deinit(t->sessionID);
+            }
+            //here!! do security_deinit(), but when plugin pointer is null -> not deinit
+            return -1;
+        }
+    }
+    else if(p->msg.arg0 == ENCR_SET_ON_OK){ // ack 메시지인 경우
+        if(security_parse_server_ack(t->sessionID, p) == 1){    // ack 메시지 파싱
+            enc_p = get_apacket();
+            if(security_gen_client_ack(t->sessionID, enc_p) == 1){ // ack 메시지 생성
+                I("security_gen_client_ack success\n");
+                enc_p->msg.command = A_ENCR;
+                enc_p->msg.arg0 = ENCR_SET_ON_OK;
+                enc_p->msg.arg1 = p->msg.arg1;
+                t->encryption = ENCR_ON;
+                send_packet(enc_p, t);
+            }
+            else { // ack 메시지 생성에 실패한 경우
+                E("security_gen_client_ack error\n");
+                send_encr_fail(p, t, ENCR_ON_FAIL);
+                t->encryption = ENCR_OFF;
+                security_deinit(t->sessionID);
+                return -1;
+            }
+        }
+        else { // ack 메시지 파싱에 실패한 경우
+            E("security_parse_server_ack error\n");
+            send_encr_fail(p, t, ENCR_ON_FAIL);
+            t->encryption = ENCR_OFF;
+            security_deinit(t->sessionID);
+            return -1;
+        }
+    }
+    else if(p->msg.arg0 == ENCR_SET_OFF){ // 암호화 모드 off 요청 메시지
+        if(t->encryption == ENCR_ON && security_deinit(t->sessionID) == 1){ // 현재 암호화 모드가 on 상태인 경우
+            enc_p = get_apacket();
+            t->encryption = ENCR_OFF; // 현재 연결에 대한 암호화 모드 off
+            enc_p->msg.command = A_ENCR;
+            enc_p->msg.arg0 = ENCR_SET_OFF;
+            enc_p->msg.arg1 = p->msg.arg1;
+            send_packet(enc_p, t);
+        }
+        else { // 암호화 모드 off에 실패한 경우
+            E("security_deinit error\n");
+            send_encr_fail(p, t, ENCR_OFF_FAIL); // 암호화 모드 off 실패 메시지 전송
+            return -1;
+        }
+    }
+    else if(p->msg.arg0 == ENCR_GET){ // 암호화 모드의 상태 요청 메시지인 경우
+        enc_p = get_apacket();
+        enc_p->msg.command = A_ENCR;
+        enc_p->msg.arg0 = ENCR_GET; // 암호화 모드 status get메시지
+        enc_p->msg.arg1 = p->msg.arg1;
+        if(t->encryption == ENCR_ON){ // 암호화 모드가 on인 경우
+            enc_p->msg.data_length = 13;
+            strncpy((char*)enc_p->data, "encryption:on", enc_p->msg.data_length + 1); // encryption:on 메시지 전송
+        } else if(t->encryption == ENCR_OFF){ // 암호화 모드가 off인 경우
+            enc_p->msg.data_length = 14;
+            strncpy((char*)enc_p->data, "encryption:off", enc_p->msg.data_length + 1); // encryption:off 메시지 전송
+        }
+        send_packet(enc_p, t);
+    }
+    else if (p->msg.arg0 == ENCR_ON_FAIL) // 암호화 모드를 on 하는 도중 실패한 경우 받는 메시지
+    {
+        t->encryption = ENCR_OFF; // 암호화 모드를 다시 off
+        E("encryption on failed\n");
+    }
+    else if (p->msg.arg0 == ENCR_OFF_FAIL) // 암호화 모드를 off하는 도중 실패한 경우 받는 메시지
+    {
+        //t->encryption = ENCR_ON;
+        E("encryption off failed\n");
+    }
+    //put_apacket(enc_p);
+    return 0;
+
+}
+#endif
+
+
 static void send_ready(unsigned local, unsigned remote, atransport *t)
 {
-    D("Calling send_ready \n");
+    I("Calling send_ready \n");
     apacket *p = get_apacket();
     p->msg.command = A_OKAY;
     p->msg.arg0 = local;
@@ -380,7 +609,7 @@ static void send_ready(unsigned local, unsigned remote, atransport *t)
 
 static void send_close(unsigned local, unsigned remote, atransport *t)
 {
-    D("Calling send_close \n");
+    I("Calling send_close \n");
     apacket *p = get_apacket();
     p->msg.command = A_CLSE;
     p->msg.arg0 = local;
@@ -390,12 +619,15 @@ static void send_close(unsigned local, unsigned remote, atransport *t)
 
 static void send_connect(atransport *t)
 {
-    D("Calling send_connect \n");
+    I("Calling send_connect \n");
     apacket *cp = get_apacket();
     cp->msg.command = A_CNXN;
     cp->msg.arg0 = A_VERSION;
+#ifdef SUPPORT_ENCRYPT
+   cp->msg.arg1 = MAX_PAYLOAD - 100; // connection 시, sdb server의 패킷 크기를 암호화 오버로드 만큼 줄임
+#else
     cp->msg.arg1 = MAX_PAYLOAD;
-
+#endif
     char device_name[256]={0,};
     int r = 0;
     int status = 0;
@@ -415,20 +647,20 @@ static void send_connect(atransport *t)
         snprintf((char*) cp->data, sizeof cp->data, "%s::%s::%d", sdb_device_banner, device_name, status);
     }
 
-    D("CNXN data:%s\n", (char*)cp->data);
+    if (extcmd != NULL) {
+        char extbuf[BUF_SIZE] = {0,};
+        snprintf(extbuf, sizeof extbuf, "::%s", extcmd);
+        strncat((char*) cp->data, extbuf, sizeof(cp->data) - strlen((const char*)cp->data)- 1);
+    }
     cp->msg.data_length = strlen((char*) cp->data) + 1;
+    D("CNXN data: %s\n", (char*)cp->data);
 
     send_packet(cp, t);
-#if SDB_HOST
-        /* XXX why sleep here? */
-    // allow the device some time to respond to the connect message
-    sdb_sleep_ms(1000);
-#endif
 }
 
 void send_device_status()
 {
-    D("broadcast device status\n");
+    I("broadcast device status\n");
     apacket* cp = get_apacket();
     cp->msg.command = A_STAT;
     cp->msg.arg0 = is_pwlocked;
@@ -472,7 +704,7 @@ static int get_str_cmdline(char *src, char *dest, char str[], int str_size) {
     int len = e-s-strlen(dest);
 
     if (len >= str_size) {
-        D("buffer size(%d) should be bigger than %d\n", str_size, len+1);
+        E("buffer size(%d) should be bigger than %d\n", str_size, len+1);
         return -1;
     }
 
@@ -506,7 +738,7 @@ int get_device_name(char str[], int str_size) {
     char *value = NULL;
     int r = system_info_get_platform_string("http://tizen.org/system/model_name", &value);
     if (r != SYSTEM_INFO_ERROR_NONE) {
-        D("fail to get system model:%d\n", errno);
+        E("fail to get system model:%d\n", errno);
         return -1;
     } else {
         s_strncpy(str, value, str_size);
@@ -538,13 +770,13 @@ static int get_cmdline_value(char *split, char str[], int str_size) {
     int fd = unix_open(PROC_CMDLINE_PATH, O_RDONLY);
 
     if (fd < 0) {
-        D("fail to read /proc/cmdline\n");
+        E("fail to read /proc/cmdline\n");
         return -1;
     }
     if(read_line(fd, cmdline, sizeof(cmdline))) {
         D("qemu cmd: %s\n", cmdline);
         if (get_str_cmdline(cmdline, split, str, str_size) < 1) {
-            D("could not get the (%s) value from cmdline\n", split);
+            E("could not get the (%s) value from cmdline\n", split);
             sdb_close(fd);
             return -1;
         }
@@ -564,19 +796,19 @@ int get_emulator_guestip(char str[], int str_size) {
 
     s = socket(AF_INET, SOCK_DGRAM, 0);
     if(s < 0) {
-        D("socket error\n");
+        E("socket error\n");
         return -1;
     }
 
     snprintf(ifr.ifr_name, sizeof(ifr.ifr_name), "%s", GUEST_IP_INTERFACE);
     if(ioctl(s, SIOCGIFHWADDR, &ifr) < 0) {
-        D("ioctl hwaddr error\n");
+        E("ioctl hwaddr error\n");
         sdb_close(s);
         return -1;
     }
 
     if(ioctl(s, SIOCGIFADDR, &ifr) < 0) {
-        D("ioctl addr error\n");
+        E("ioctl addr error\n");
         sdb_close(s);
         return -1;
     }
@@ -613,28 +845,28 @@ void parse_banner(char *banner, atransport *t)
     }
 
     if(!strcmp(type, "bootloader")){
-        D("setting connection_state to CS_BOOTLOADER\n");
+        I("setting connection_state to CS_BOOTLOADER\n");
         t->connection_state = CS_BOOTLOADER;
         update_transports();
         return;
     }
 
     if(!strcmp(type, "device")) {
-        D("setting connection_state to CS_DEVICE\n");
+        I("setting connection_state to CS_DEVICE\n");
         t->connection_state = CS_DEVICE;
         update_transports();
         return;
     }
 
     if(!strcmp(type, "recovery")) {
-        D("setting connection_state to CS_RECOVERY\n");
+        I("setting connection_state to CS_RECOVERY\n");
         t->connection_state = CS_RECOVERY;
         update_transports();
         return;
     }
 
     if(!strcmp(type, "sideload")) {
-        D("setting connection_state to CS_SIDELOAD\n");
+        I("setting connection_state to CS_SIDELOAD\n");
         t->connection_state = CS_SIDELOAD;
         update_transports();
         return;
@@ -643,6 +875,18 @@ void parse_banner(char *banner, atransport *t)
     t->connection_state = CS_HOST;
 }
 
+static void update_version(atransport *t, int version, size_t payload)
+{
+#ifdef SUPPORT_ENCRYPT
+    size_t max_payload = MAX_PAYLOAD - 100;
+#else
+    size_t max_payload = MAX_PAYLOAD;
+#endif
+    t->protocol_version = min(version, A_VERSION);
+    t->max_payload = min(payload, max_payload);
+    D("update transport version. version=%x, max_payload=%zu\n", t->protocol_version, t->max_payload);
+}
+
 void handle_packet(apacket *p, atransport *t)
 {
     // Verify pointer p
@@ -653,10 +897,10 @@ void handle_packet(apacket *p, atransport *t)
 
     asocket *s;
 
-    D("handle_packet() %c%c%c%c\n", ((char*) (&(p->msg.command)))[0],
-                ((char*) (&(p->msg.command)))[1],
-                ((char*) (&(p->msg.command)))[2],
-                ((char*) (&(p->msg.command)))[3]);
+//    D("handle_packet() %c%c%c%c\n", ((char*) (&(p->msg.command)))[0],
+//                ((char*) (&(p->msg.command)))[1],
+//                ((char*) (&(p->msg.command)))[2],
+//                ((char*) (&(p->msg.command)))[3]);
 
     print_packet("recv", p);
 
@@ -678,6 +922,7 @@ void handle_packet(apacket *p, atransport *t)
             t->connection_state = CS_OFFLINE;
             handle_offline(t);
         }
+        update_version(t, p->msg.arg0, p->msg.arg1);
         parse_banner((char*) p->data, t);
         handle_online();
         if(!HOST) send_connect(t);
@@ -686,7 +931,7 @@ void handle_packet(apacket *p, atransport *t)
     case A_OPEN: /* OPEN(local-id, 0, "destination") */
         if (request_lock_state_to_plugin(LOCKTYPE_PASSWORD) == 1 && t->connection_state == CS_PWLOCK) {
             // in case of already locked before get A_CNXN
-            D("open failed due to password locked before get A_CNXN:%d\n", t->connection_state);
+            E("open failed due to password locked before get A_CNXN:%d\n", t->connection_state);
             send_close(0, p->msg.arg0, t);
         } else {
             if(t->connection_state != CS_OFFLINE) {
@@ -732,13 +977,20 @@ void handle_packet(apacket *p, atransport *t)
                 p->len = p->msg.data_length;
 
                 if(s->enqueue(s, p) == 0) {
-                    D("Enqueue the socket\n");
+                    I("Enqueue the socket\n");
                     send_ready(s->id, rid, t);
                 }
                 return;
             }
         }
         break;
+#ifdef SUPPORT_ENCRYPT
+    case A_ENCR: // 암호화 메시지인 경우
+        if(t->connection_state != CS_OFFLINE) {
+            handle_encr_packet(p, t);
+        }
+        break;
+#endif
 
     default:
         printf("handle_packet: what is %08x?!\n", p->msg.command);
@@ -755,6 +1007,7 @@ alistener listener_list = {
 static void ss_listener_event_func(int _fd, unsigned ev, void *_l)
 {
     asocket *s;
+    int ret = -1;
 
     if(ev & FDE_READ) {
         struct sockaddr addr;
@@ -765,7 +1018,10 @@ static void ss_listener_event_func(int _fd, unsigned ev, void *_l)
         fd = sdb_socket_accept(_fd, &addr, &alen);
         if(fd < 0) return;
 
-        sdb_socket_setbufsize(fd, CHUNK_SIZE);
+        ret = sdb_socket_setbufsize(fd, CHUNK_SIZE);
+        if (ret == -1) {
+            D("sdbd: sdb_socket_setbufsize failed (%d)\n", ret);
+        }
 
         s = create_local_socket(fd);
         if(s) {
@@ -924,7 +1180,7 @@ static int install_listener(const char *local_name, const char *connect_to, atra
     }
 
     if (close_on_exec(l->fd) < 0) {
-        D("fail to close fd exec:%d\n",l->fd);
+        E("fail to close fd exec:%d\n",l->fd);
     }
     if(!strcmp(l->connect_to, "*smartsocket*")) {
         fdevent_install(&l->fde, l->fd, ss_listener_event_func, l);
@@ -951,14 +1207,6 @@ nomem:
     return 0;
 }
 
-#ifdef HAVE_WIN32_PROC
-static BOOL WINAPI ctrlc_handler(DWORD type)
-{
-    exit(STATUS_CONTROL_C_EXIT);
-    return TRUE;
-}
-#endif
-
 static void sdb_cleanup(void)
 {
     clear_sdbd_commandline_args(&sdbd_commandline_args);
@@ -973,87 +1221,41 @@ static void sdb_cleanup(void)
     unload_sdbd_plugin();
 }
 
-void start_logging(void)
+static void sdb_service_cleanup(void)
 {
-#ifdef HAVE_WIN32_PROC
-    char    temp[ MAX_PATH ];
-    FILE*   fnul;
-    FILE*   flog;
-
-    GetTempPath( sizeof(temp) - 8, temp );
-    strcat( temp, "sdb.log" );
-
-    /* Win32 specific redirections */
-    fnul = fopen( "NUL", "rt" );
-    if (fnul != NULL)
-        stdin[0] = fnul[0];
-
-    flog = fopen( temp, "at" );
-    if (flog == NULL)
-        flog = fnul;
-
-    setvbuf( flog, NULL, _IONBF, 0 );
-
-    stdout[0] = flog[0];
-    stderr[0] = flog[0];
-    fprintf(stderr,"--- sdb starting (pid %d) ---\n", getpid());
-#else
-    int fd;
-
-    fd = unix_open("/dev/null", O_RDONLY);
-    if (fd < 0) {
-        // hopefully not gonna happen
-        return;
-    }
-    dup2(fd, 0);
-    sdb_close(fd);
-
-    fd = unix_open("/tmp/sdb.log", O_WRONLY | O_CREAT | O_APPEND, 0640);
-    if(fd < 0) {
-        fd = unix_open("/dev/null", O_WRONLY);
-        if (fd < 0) {
-            // hopefully not gonna happen
-            return;
-        }
+    if (exit_cleanup_required)
+    {
+        unload_sdbd_service_plugin();
     }
-    dup2(fd, 1);
-    dup2(fd, 2);
-    sdb_close(fd);
-    fprintf(stderr,"--- sdb starting (pid %d) ---\n", getpid());
-#endif
 }
 
-#if !SDB_HOST
 
 void start_device_log(void)
 {
     int fd;
-    char    path[PATH_MAX] = {0, };
+    char    path[2*PATH_MAX] = {0, };
     char    path_folder[PATH_MAX] = {0, };
     char    path_file[PATH_MAX] = {0, };
     struct tm now;
     time_t t;
-//    char value[PROPERTY_VALUE_MAX];
-    const char* p_trace = getenv("SDB_TRACE");
-    const char* p_path = getenv("SDBD_LOG_PATH");
+
     // read the trace mask from persistent property persist.sdb.trace_mask
     // give up if the property is not set or cannot be parsed
-#if 0 /* tizen specific */
-    property_get("persist.sdb.trace_mask", value, "");
-    if (sscanf(value, "%x", &sdb_trace_mask) != 1)
-        return;
-#endif
-
+    char* p_trace = get_sdb_log_conf("SDB_TRACE");
     if ((p_trace == NULL ) && !is_enable_sdbd_log()) {
         return;
+    } else {
+        free(p_trace);
     }
-
-    if (p_path)
+    char* p_path = get_sdb_log_conf("SDBD_LOG_PATH");
+    if (p_path) {
         snprintf(path_folder, sizeof(path_folder), "%s", p_path);
-    else if (g_capabilities.log_path[0] != '\0')
+        free(p_path);
+    } else if (g_capabilities.log_path[0] != '\0') {
         snprintf(path_folder, sizeof(path_folder), "%s", g_capabilities.log_path);
-    else
+    } else {
         return;
+    }
 
     tzset();
     time(&t);
@@ -1085,174 +1287,6 @@ void start_device_log(void)
     sdb_close(fd);
 }
 
-int daemonize(void) {
-
-    // set file creation mask to 0
-    umask(0);
-
-    switch (fork()) {
-    case -1:
-        return -1;
-    case 0:
-        break;
-    default:
-        _exit(0);
-    }
-#ifdef SDB_PIDPATH
-    FILE *f = fopen(SDB_PIDPATH, "w");
-
-    if (f != NULL) {
-        fprintf(f, "%d\n", getpid());
-        fclose(f);
-    }
-#endif
-    if (setsid() == -1)
-        return -1;
-
-    if (chdir("/") < 0)
-        D("sdbd: unable to change working directory to /\n");
-
-    return 0;
-}
-#endif
-
-#if SDB_HOST
-int launch_server(int server_port)
-{
-#ifdef HAVE_WIN32_PROC
-    /* we need to start the server in the background                    */
-    /* we create a PIPE that will be used to wait for the server's "OK" */
-    /* message since the pipe handles must be inheritable, we use a     */
-    /* security attribute                                               */
-    HANDLE                pipe_read, pipe_write;
-    SECURITY_ATTRIBUTES   sa;
-    STARTUPINFO           startup;
-    PROCESS_INFORMATION   pinfo;
-    char                  program_path[ MAX_PATH ];
-    int                   ret;
-
-    sa.nLength = sizeof(sa);
-    sa.lpSecurityDescriptor = NULL;
-    sa.bInheritHandle = TRUE;
-
-    /* create pipe, and ensure its read handle isn't inheritable */
-    ret = CreatePipe( &pipe_read, &pipe_write, &sa, 0 );
-    if (!ret) {
-        fprintf(stderr, "CreatePipe() failure, error %ld\n", GetLastError() );
-        return -1;
-    }
-
-    SetHandleInformation( pipe_read, HANDLE_FLAG_INHERIT, 0 );
-
-    ZeroMemory( &startup, sizeof(startup) );
-    startup.cb = sizeof(startup);
-    startup.hStdInput  = GetStdHandle( STD_INPUT_HANDLE );
-    startup.hStdOutput = pipe_write;
-    startup.hStdError  = GetStdHandle( STD_ERROR_HANDLE );
-    startup.dwFlags    = STARTF_USESTDHANDLES;
-
-    ZeroMemory( &pinfo, sizeof(pinfo) );
-
-    /* get path of current program */
-    GetModuleFileName( NULL, program_path, sizeof(program_path) );
-
-    ret = CreateProcess(
-            program_path,                              /* program path  */
-            "sdb fork-server server",
-                                    /* the fork-server argument will set the
-                                       debug = 2 in the child           */
-            NULL,                   /* process handle is not inheritable */
-            NULL,                    /* thread handle is not inheritable */
-            TRUE,                          /* yes, inherit some handles */
-            DETACHED_PROCESS, /* the new process doesn't have a console */
-            NULL,                     /* use parent's environment block */
-            NULL,                    /* use parent's starting directory */
-            &startup,                 /* startup info, i.e. std handles */
-            &pinfo );
-
-    CloseHandle( pipe_write );
-
-    if (!ret) {
-        fprintf(stderr, "CreateProcess failure, error %ld\n", GetLastError() );
-        CloseHandle( pipe_read );
-        return -1;
-    }
-
-    CloseHandle( pinfo.hProcess );
-    CloseHandle( pinfo.hThread );
-
-    /* wait for the "OK\n" message */
-    {
-        char  temp[3];
-        DWORD  count;
-
-        ret = ReadFile( pipe_read, temp, 3, &count, NULL );
-        CloseHandle( pipe_read );
-        if ( !ret ) {
-            fprintf(stderr, "could not read ok from SDB Server, error = %ld\n", GetLastError() );
-            return -1;
-        }
-        if (count != 3 || temp[0] != 'O' || temp[1] != 'K' || temp[2] != '\n') {
-            fprintf(stderr, "SDB server didn't ACK\n" );
-            return -1;
-        }
-    }
-#elif defined(HAVE_FORKEXEC)
-    char    path[PATH_MAX];
-    int     fd[2];
-
-    // set up a pipe so the child can tell us when it is ready.
-    // fd[0] will be parent's end, and fd[1] will get mapped to stderr in the child.
-    if (pipe(fd)) {
-        fprintf(stderr, "pipe failed in launch_server, errno: %d\n", errno);
-        return -1;
-    }
-    get_my_path(path, PATH_MAX);
-    pid_t pid = fork();
-    if(pid < 0) return -1;
-
-    if (pid == 0) {
-        // child side of the fork
-
-        // redirect stderr to the pipe
-        // we use stderr instead of stdout due to stdout's buffering behavior.
-        sdb_close(fd[0]);
-        dup2(fd[1], STDERR_FILENO);
-        sdb_close(fd[1]);
-
-        // child process
-        int result = execl(path, "sdb", "fork-server", "server", NULL);
-        // this should not return
-        fprintf(stderr, "OOPS! execl returned %d, errno: %d\n", result, errno);
-    } else  {
-        // parent side of the fork
-
-        char  temp[3];
-
-        temp[0] = 'A'; temp[1] = 'B'; temp[2] = 'C';
-        // wait for the "OK\n" message
-        sdb_close(fd[1]);
-        int ret = sdb_read(fd[0], temp, 3);
-        int saved_errno = errno;
-        sdb_close(fd[0]);
-        if (ret < 0) {
-            fprintf(stderr, "could not read ok from SDB Server, errno = %d\n", saved_errno);
-            return -1;
-        }
-        if (ret != 3 || temp[0] != 'O' || temp[1] != 'K' || temp[2] != '\n') {
-            fprintf(stderr, "SDB server didn't ACK\n" );
-            return -1;
-        }
-
-        setsid();
-    }
-#else
-#error "cannot implement background server start on this platform"
-#endif
-    return 0;
-}
-#endif
-
 /* Constructs a local name of form tcp:port.
  * target_str points to the target string, it's content will be overwritten.
  * target_size is the capacity of the target string.
@@ -1263,7 +1297,6 @@ void build_local_name(char* target_str, size_t target_size, int server_port)
   snprintf(target_str, target_size, "tcp:%d", server_port);
 }
 
-#if !SDB_HOST
 static void init_drop_privileges() {
 #ifdef _DROP_PRIVILEGE
     rootshell_mode = 0;
@@ -1273,143 +1306,154 @@ static void init_drop_privileges() {
 }
 
 int should_drop_privileges() {
-    if (rootshell_mode == 1) { // if root, then don't drop
-        return 0;
-    }
-    return 1;
+    return !rootshell_mode; // if root, then don't drop
 }
 
-#include <dbus/dbus.h>
-#include <dbus/dbus-glib.h>
-#include <dbus/dbus-glib-lowlevel.h>
+#include <gio/gio.h>
 
+#define BOOTING_DONE_PATH      "/org/tizen/system"
 #define BOOTING_DONE_SIGNAL    "BootingDone"
-#define DEVICED_CORE_INTERFACE "org.tizen.system.deviced.core"
-#define SDBD_BOOT_INFO_FILE "/tmp/sdbd_boot_info"
-
-static DBusHandlerResult __sdbd_dbus_signal_filter(DBusConnection *conn,
-               DBusMessage *message, void *user_data) {
-       D("got dbus message\n");
-       const char *interface;
-
-       DBusError error;
-       dbus_error_init(&error);
-
-       interface = dbus_message_get_interface(message);
-       if (interface == NULL) {
-               D("reject by security issue - no interface\n");
-               return DBUS_HANDLER_RESULT_NOT_YET_HANDLED;
-       }
-
-       if (dbus_message_is_signal(message, DEVICED_CORE_INTERFACE,
-                       BOOTING_DONE_SIGNAL)) {
-               booting_done = 1;
-               if (access(SDBD_BOOT_INFO_FILE, F_OK) == 0) {
-                       D("booting is done before\n");
+#define BOOTING_DONE_INTERFACE "org.tizen.system.Booting"
+#define SDBD_BOOT_INFO_FILE    "/tmp/sdbd_boot_info"
+
+static GMainLoop *g_mainloop;
+
+static void booting_done_signal_subscriber(GDBusConnection *connection,
+    const gchar *sender, const gchar *path, const gchar *interface,
+    const gchar *signal, GVariant *parameters, gpointer user_data)
+{
+    if (g_strcmp0(signal, BOOTING_DONE_SIGNAL) != 0) {
+        D("received signal(%s) does not match the desired signal(%s)\n",
+          signal, BOOTING_DONE_SIGNAL);
+        return;
+    }
+
+    D("received the \"%s\" signal\n", signal);
+
+    booting_done = 1;
+    if (access(SDBD_BOOT_INFO_FILE, F_OK) == 0) {
+        I("booting is already done\n");
+    } else {
+        FILE *info_file = fopen(SDBD_BOOT_INFO_FILE, "w");
+        if (info_file != NULL) {
+               char* tmppath = realpath(SDBD_BOOT_INFO_FILE, NULL);
+               if (tmppath != NULL) {
+                        if (strcmp(SDBD_BOOT_INFO_FILE, tmppath) == 0) {
+                               fprintf(info_file, "%d", 1);
+                               I("booting is done\n");
+                        } else {
+                               D("Path has symbolic link, security risk \n");
+                               free(tmppath);
+                               return;
+                        }
+                       free(tmppath);
                } else {
-                       FILE *f = fopen(SDBD_BOOT_INFO_FILE, "w");
-                       if (f != NULL) {
-                               fprintf(f, "%d", 1);
-                               fclose(f);
-                       }
+                       D("Getting realpath failed\n");
                }
-               D("booting is done\n");
-       }
+               fclose(info_file);
+        }
+    }
 
-       D("handled dbus message\n");
-       return DBUS_HANDLER_RESULT_HANDLED;
+    I("handled the booting done signal\n");
+    g_main_loop_quit(g_mainloop);
 }
 
-static void *bootdone_cb(void *x) {
-       int MAX_LOCAL_BUFSZ = 128;
-       DBusError error;
-       DBusConnection *bus;
-       char rule[MAX_LOCAL_BUFSZ];
-       GMainLoop *mainloop;
-
-/* g_type_init() is deprecated for glib version 2.35.0 or greater, */
-#if !GLIB_CHECK_VERSION(2,35,0)
-       g_type_init();
-#endif
+static void *bootdone_cb(void *args)
+{
+    GError *error = NULL;
+    GDBusConnection *connection = NULL;
+    guint id;
+
+    connection = g_bus_get_sync(G_BUS_TYPE_SYSTEM, NULL, &error);
+    if (connection == NULL) {
+        if (error != NULL) {
+            E("failed to connect to the system bus: %s\n", error->message);
+            g_error_free(error);
+        } else {
+            E("failed to connect to the system bus\n");
+        }
+        return NULL;
+    }
 
-       dbus_error_init(&error);
-       bus = dbus_bus_get(DBUS_BUS_SYSTEM, &error);
-       if (!bus) {
-               D("Failed to connect to the D-BUS daemon: %s", error.message);
-               dbus_error_free(&error);
-               return NULL;
-       }
-       dbus_connection_setup_with_g_main(bus, NULL);
+    g_mainloop = g_main_loop_new(NULL, false);
+    if (g_mainloop == NULL) {
+        E("failed to create a g_main_loop\n");
+        goto bootdone_out;
+    }
 
-       snprintf(rule, MAX_LOCAL_BUFSZ, "type='signal',interface='%s'",
-                       DEVICED_CORE_INTERFACE);
-       /* listening to messages */
-       dbus_bus_add_match(bus, rule, &error);
-       if (dbus_error_is_set(&error)) {
-               D("Fail to rule set: %s", error.message);
-               dbus_error_free(&error);
-               return NULL;
-       }
+    id = g_dbus_connection_signal_subscribe(connection,
+        NULL, BOOTING_DONE_INTERFACE, BOOTING_DONE_SIGNAL,
+        BOOTING_DONE_PATH, NULL, G_DBUS_SIGNAL_FLAGS_NONE,
+        booting_done_signal_subscriber, NULL, NULL);
+    if (id == 0) {
+        E("failed to subscribe to the booting done signal\n");
+        goto bootdone_out;
+    }
 
-       if (dbus_connection_add_filter(bus, __sdbd_dbus_signal_filter, NULL, NULL)
-                       == FALSE)
-               return NULL;
+    I("wait for the booting done signal\n");
+    g_main_loop_run(g_mainloop);
 
-       D("booting signal initialized\n");
-       mainloop = g_main_loop_new(NULL, FALSE);
-       g_main_loop_run(mainloop);
+    g_dbus_connection_signal_unsubscribe(connection, id);
 
-       D("dbus loop exited");
+bootdone_out:
+    if (g_mainloop != NULL) {
+        g_main_loop_unref(g_mainloop);
+    }
+    if (connection != NULL) {
+        g_object_unref(connection);
+    }
+    I("exit the bootdone_cb thread\n");
 
-       return NULL;
+    return NULL;
 }
 
-void register_bootdone_cb() {
-       D("registerd bootdone callback\n");
-
-       sdb_thread_t t;
-       if (sdb_thread_create(&t, bootdone_cb, NULL)) {
-               D("cannot create service thread\n");
-               return;
-       }
+void register_bootdone_cb()
+{
+    sdb_thread_t t;
+    if (sdb_thread_create(&t, bootdone_cb, NULL)) {
+        E("can not create a service thread to check the booting done\n");
+        return;
+    }
+    I("created the bootdone_cb thread\n");
 }
 
-static int sdbd_set_groups() {
+static int sdbd_set_groups(const char *name, int gid, struct group_info default_groups[], int default_groups_size) {
     gid_t *group_ids = NULL;
     int ngroups = 0;
     int i, j = 0;
     int group_match = 0;
     int added_group_cnt = 0;
 
-    getgrouplist(SDK_USER_NAME, g_sdk_group_id, NULL, &ngroups);
-    D("group list : ngroups = %d\n", ngroups);
-    group_ids = malloc((ngroups + SDB_DEFAULT_GROUPS_CNT) * sizeof(gid_t));
+    if (getgrouplist(name, gid, NULL, &ngroups) == -1) {
+        D("group list : ngroups = %d\n", ngroups);
+    }
+    group_ids = malloc((ngroups + default_groups_size) * sizeof(gid_t));
     if (group_ids == NULL) {
-        D("failed to allocate group_ids(%d)\n", (ngroups + SDB_DEFAULT_GROUPS_CNT) * sizeof(gid_t));
+        E("failed to allocate group_ids(%zu)\n", (ngroups + default_groups_size) * sizeof(gid_t));
         return -1;
     }
-    if (getgrouplist(SDK_USER_NAME, g_sdk_group_id, group_ids, &ngroups) == -1) {
-        D("failed to getgrouplist(), ngroups = %d\n", ngroups);
+    if (getgrouplist(name, gid, group_ids, &ngroups) == -1) {
+        E("failed to getgrouplist(), ngroups = %d\n", ngroups);
         free(group_ids);
         return -1;
     }
-
-    for (i = 0; g_default_groups[i].name != NULL; i++) {
-        for (j = 0; j < ngroups; j++) {
-            if (group_ids[j] == g_default_groups[i].gid) {
-                group_match = 1;
-                break;
+    if(default_groups_size >= 1) {
+        for (i = 0; default_groups[i].name != NULL; i++) {
+            for (j = 0; j < ngroups; j++) {
+                if (group_ids[j] == default_groups[i].gid) {
+                    group_match = 1;
+                    break;
+                }
             }
+            if (group_match == 0 && default_groups[i].gid != -1) {
+                group_ids[ngroups + added_group_cnt] = default_groups[i].gid;
+                added_group_cnt ++;
+            }
+            group_match = 0;
         }
-        if (group_match == 0 && g_default_groups[i].gid != -1) {
-            group_ids[ngroups + added_group_cnt] = g_default_groups[i].gid;
-            added_group_cnt ++;
-        }
-        group_match = 0;
     }
-
     if (setgroups(ngroups+added_group_cnt, group_ids) != 0) {
-        D("failed to setgroups().\n");
+        E("failed to setgroups().\n");
         free(group_ids);
         return -1;
     }
@@ -1425,10 +1469,10 @@ static int sdbd_get_user_pwd(const char* user_name, struct passwd* pwd, char* bu
     ret = getpwnam_r(user_name, pwd, buf, bufsize, &result);
     if (result == NULL) {
         if (ret == 0) {
-            D("Not found passwd : username(%s)\n", user_name);
+            E("Not found passwd : username(%s)\n", user_name);
         } else {
             errno = ret;
-            D("failed to getpwnam_r\n");
+            E("failed to getpwnam_r\n");
         }
         return -1;
     }
@@ -1443,10 +1487,10 @@ static int sdbd_get_group(const char* group_name, struct group* grp, char* buf,
     ret = getgrnam_r(group_name, grp, buf, bufsize, &result);
     if (result == NULL) {
         if (ret == 0) {
-            D("Not found group : groupname(%s)\n", group_name);
+            E("Not found group : groupname(%s)\n", group_name);
         } else {
             errno = ret;
-            D("failed to getgrnam_r\n");
+            E("failed to getgrnam_r\n");
         }
         return -1;
     }
@@ -1454,29 +1498,44 @@ static int sdbd_get_group(const char* group_name, struct group* grp, char* buf,
     return 0;
 }
 
-int set_sdk_user_privileges() {
+int set_sdk_user_privileges(int is_drop_capability_after_fork) {
     if (!is_init_sdk_userinfo) {
-        D("failed to init sdk user information.\n");
+        E("failed to init sdk user information.\n");
         return -1;
     }
 
-    if (sdbd_set_groups() < 0) {
-        D("set groups failed (errno: %d)\n", errno);
+    /*
+    * If a process switches its real, effective, or saved uids from at least one being 0 to all being non-zero,
+    * then both the permitted and effective capabilities are cleared.
+    */
+    if(is_drop_capability_after_fork) {
+
+        if (setuid(g_root_user_id) != 0) {
+            E("set root user id failed (errno: %d)\n", errno);
+            return -1;
+        }
+    }
+
+    if (sdbd_set_groups(SDK_USER_NAME, g_sdk_group_id, g_default_groups, SDB_DEFAULT_GROUPS_CNT) < 0) {
+        E("set groups failed (errno: %d)\n", errno);
         return -1;
     }
 
     if (setgid(g_sdk_group_id) != 0) {
-        D("set group id failed (errno: %d)\n", errno);
+        E("set group id failed (errno: %d)\n", errno);
         return -1;
     }
 
     if (setuid(g_sdk_user_id) != 0) {
-        D("set user id failed (errno: %d)\n", errno);
+        E("set user id failed (errno: %d)\n", errno);
         return -1;
+//        if(is_drop_capability_after_fork) {
+//            return -1;
+//        }
     }
 
     if (chdir(g_sdk_home_dir) < 0) {
-        D("unable to change working directory to %s\n", g_sdk_home_dir);
+        E("unable to change working directory to %s\n", g_sdk_home_dir);
     }
 
     // TODO: use pam later
@@ -1487,6 +1546,32 @@ int set_sdk_user_privileges() {
     return 0;
 }
 
+int set_root_privileges() {
+
+    if (sdbd_set_groups(ROOT_USER_NAME, g_root_group_id, NULL, 0) < 0) {
+        E("set root groups failed (errno: %d)\n", errno);
+    }
+
+    if (setgid(g_root_group_id) != 0) {
+        E("set root group id failed (errno: %d)\n", errno);
+    }
+
+    if (setuid(g_root_user_id) != 0) {
+        E("set root user id failed (errno: %d)\n", errno);
+    }
+
+    if (chdir(g_root_home_dir) < 0) {
+        E("unable to change root working directory to %s\n", g_sdk_home_dir);
+    }
+
+    // TODO: use pam later
+    if (g_root_home_dir_env) {
+        putenv(g_root_home_dir_env);
+    }
+
+    return 0;
+}
+
 #define SDB_PW_GR_DEFAULT_SIZE  (16*1024)
 static long get_passwd_bufsize() {
     long bufsize = 0;
@@ -1519,7 +1604,7 @@ static int init_sdb_default_groups() {
     bufsize = get_group_bufsize();
     buf = malloc(bufsize);
     if (buf == NULL) {
-        D("failed to allocate gruop buf(%ld)\n", bufsize);
+        E("failed to allocate gruop buf(%ld)\n", bufsize);
         return -1;
     }
 
@@ -1528,7 +1613,7 @@ static int init_sdb_default_groups() {
         if (sdbd_get_group(g_default_groups[i].name, &grp, buf, bufsize) == 0) {
             g_default_groups[i].gid = grp.gr_gid;
         } else {
-            D("failed get group info.(errno: %d)\n", errno);
+            E("failed get group info.(errno: %d)\n", errno);
         }
     }
 
@@ -1536,12 +1621,53 @@ static int init_sdb_default_groups() {
     return 0;
 }
 
-static void set_static_userinfo() {
+static void set_static_root_userinfo() {
+    g_root_user_id = STATIC_ROOT_USER_ID;
+    g_root_group_id = STATIC_ROOT_GROUP_ID;
+    g_root_home_dir = STATIC_ROOT_HOME_DIR;
+}
+
+static void set_static_sdk_userinfo() {
     g_sdk_user_id = STATIC_SDK_USER_ID;
     g_sdk_group_id = STATIC_SDK_GROUP_ID;
     g_sdk_home_dir = STATIC_SDK_HOME_DIR;
 }
 
+static int init_root_userinfo() {
+    struct passwd pwd;
+    char *buf = NULL;
+    long bufsize = 0;
+
+    bufsize = get_passwd_bufsize();
+    buf = malloc(bufsize);
+    if (buf == NULL) {
+        E("failed to allocate passwd buf(%ld)\n", bufsize);
+        set_static_root_userinfo();
+    } else {
+        if (sdbd_get_user_pwd(ROOT_USER_NAME, &pwd, buf, bufsize) < 0) {
+            E("failed to get root user passwd info.(errno: %d)\n", errno);
+            set_static_root_userinfo();
+        } else {
+            D("username=%s, uid=%d, gid=%d, dir=%s\n", pwd.pw_name, pwd.pw_uid, pwd.pw_gid, pwd.pw_dir);
+
+            g_root_user_id = pwd.pw_uid;
+            g_root_group_id = pwd.pw_gid;
+            g_root_home_dir = strdup(pwd.pw_dir);
+        }
+        free(buf);
+    }
+
+    int env_size = strlen("HOME=") + strlen(g_root_home_dir) + 1;
+    g_root_home_dir_env = malloc(env_size);
+    if(g_root_home_dir_env == NULL) {
+        E("failed to allocate for home dir env string\n");
+    } else {
+        snprintf(g_root_home_dir_env, env_size, "HOME=%s", g_root_home_dir);
+    }
+
+    return 0;
+}
+
 static int init_sdk_userinfo() {
     struct passwd pwd;
     char *buf = NULL;
@@ -1552,18 +1678,18 @@ static int init_sdk_userinfo() {
     }
 
     if (init_sdb_default_groups() < 0) {
-        D("failed to initialize default groups.\n");
+        E("failed to initialize default groups.\n");
     }
 
     bufsize = get_passwd_bufsize();
     buf = malloc(bufsize);
     if (buf == NULL) {
-        D("failed to allocate passwd buf(%ld)\n", bufsize);
-        set_static_userinfo();
+        E("failed to allocate passwd buf(%ld)\n", bufsize);
+        set_static_sdk_userinfo();
     } else {
         if (sdbd_get_user_pwd(SDK_USER_NAME, &pwd, buf, bufsize) < 0) {
-            D("get user passwd info.(errno: %d)\n", errno);
-            set_static_userinfo();
+            E("get user passwd info.(errno: %d)\n", errno);
+            set_static_sdk_userinfo();
         } else {
             D("username=%s, uid=%d, gid=%d, dir=%s\n", pwd.pw_name, pwd.pw_uid, pwd.pw_gid, pwd.pw_dir);
 
@@ -1577,7 +1703,7 @@ static int init_sdk_userinfo() {
     int env_size = strlen("HOME=") + strlen(g_sdk_home_dir) + 1;
     g_sdk_home_dir_env = malloc(env_size);
     if(g_sdk_home_dir_env == NULL) {
-        D("failed to allocate for home dir env string\n");
+        E("failed to allocate for home dir env string\n");
     } else {
         snprintf(g_sdk_home_dir_env, env_size, "HOME=%s", g_sdk_home_dir);
     }
@@ -1586,36 +1712,44 @@ static int init_sdk_userinfo() {
     return 0;
 }
 
-static void init_sdk_requirements() {
-    struct stat st;
+#if 0
+static int safe_system(char *cmd, char *argv[], char *envp[]) {
+    pid_t pid;
+    int status;
 
-    // set env variable for temporary
-    // TODO: should use pam instead later!!
-    if (!getenv("TERM")) {
-        putenv("TERM=linux");
+    pid = fork();
+    switch (pid) {
+        case -1:
+            return -1;
+        case 0:
+            execve(cmd, argv, envp);
+            E("- exec '%s' failed: (errno:%d) -\n", cmd, errno);
+            exit(-1);
+        default:
+            for (;;) {
+                pid_t p = waitpid(pid, &status, 0);
+                if (p == pid) {
+                    break;
+                }
+            }
     }
+    return 0;
+}
+#endif
 
-    if (!getenv("HOME")) {
-        putenv("HOME=/root");
-    }
+static void init_sdk_requirements() {
+    // set env variable for temporary
+    // TODO: should use pam instead later!!
+    putenv("TERM=linux");
+    putenv("HOME=/root");
 
     init_sdk_userinfo();
-
-    if (g_sdk_home_dir != NULL && stat(g_sdk_home_dir, &st) == 0) {
-        if (st.st_uid != g_sdk_user_id || st.st_gid != g_sdk_group_id) {
-            char cmd[128];
-            snprintf(cmd, sizeof(cmd), "chown %s:%s %s -R", SDK_USER_NAME, SDK_USER_NAME, g_sdk_home_dir);
-            if (system(cmd) < 0) {
-                D("failed to change ownership to sdk user to %s\n", g_sdk_home_dir);
-            }
-        }
-    }
+    init_root_userinfo();
 
     if (is_emulator()) {
         register_bootdone_cb();
     }
 }
-#endif /* !SDB_HOST */
 
 static void init_capabilities(void) {
     int ret = -1;
@@ -1623,16 +1757,42 @@ static void init_capabilities(void) {
 
     memset(&g_capabilities, 0, sizeof(g_capabilities));
 
+    // architecture support
+    char* arch = get_platfrom_architecture();
+    snprintf(g_capabilities.architecture, sizeof(g_capabilities.architecture),
+             "%s", arch);
+
     // CPU Architecture of model
     ret = system_info_get_platform_string("http://tizen.org/feature/platform.core.cpu.arch", &value);
     if (ret != SYSTEM_INFO_ERROR_NONE) {
         snprintf(g_capabilities.cpu_arch, sizeof(g_capabilities.cpu_arch),
                     "%s", UNKNOWN);
-        D("fail to get the CPU architecture of model:%d\n", errno);
+        E("fail to get the CPU architecture of model:%d\n", errno);
     } else {
-        snprintf(g_capabilities.cpu_arch, sizeof(g_capabilities.cpu_arch),
-                    "%s", value);
         if (value != NULL) {
+            // check for armv8 and 32 bit architecture, for it make the cpu arch as armv7l
+            if(!strncmp(value,"armv8",sizeof("armv8")+1) && !strncmp(arch,"32",sizeof("32")+1))
+            {
+                D("Changing cpu arch in capability from %s to %s for %s bit\n",value,"armv7l",arch);
+                snprintf(g_capabilities.cpu_arch, sizeof(g_capabilities.cpu_arch),
+                                    "%s", "armv7l");
+            } else {
+                snprintf(g_capabilities.cpu_arch, sizeof(g_capabilities.cpu_arch),
+                                    "%s", value);
+            }
+            free(value);
+        }
+    }
+
+    // Core ABI (That value can be a "arm_32", "arm_64", "riscv_32", "riscv_64", "x86", "x86_64")
+    ret = system_info_get_platform_string("http://tizen.org/feature/platform.core.abi", &value);
+    if (ret != SYSTEM_INFO_ERROR_NONE) {
+        snprintf(g_capabilities.core_abi, sizeof(g_capabilities.core_abi),
+                    "%s", UNKNOWN);
+        E("fail to get the core abi:%d\n", errno);
+    } else {
+        if (value != NULL) {
+            snprintf(g_capabilities.core_abi, sizeof(g_capabilities.core_abi), "%s", value);            
             free(value);
         }
     }
@@ -1641,7 +1801,7 @@ static void init_capabilities(void) {
     // Secure protocol support
     if(!request_capability_to_plugin(CAPABILITY_SECURE, g_capabilities.secure_protocol,
                             sizeof(g_capabilities.secure_protocol))) {
-        D("failed to request. (%d:%d) \n", PLUGIN_SYNC_CMD_CAPABILITY, CAPABILITY_SECURE);
+        E("failed to request. (%d:%d) \n", PLUGIN_SYNC_CMD_CAPABILITY, CAPABILITY_SECURE);
         snprintf(g_capabilities.secure_protocol, sizeof(g_capabilities.secure_protocol),
                     "%s", DISABLED);
     }
@@ -1650,7 +1810,7 @@ static void init_capabilities(void) {
     // Interactive shell support
     if(!request_capability_to_plugin(CAPABILITY_INTER_SHELL, g_capabilities.intershell_support,
                             sizeof(g_capabilities.intershell_support))) {
-        D("failed to request. (%d:%d) \n", PLUGIN_SYNC_CMD_CAPABILITY, CAPABILITY_INTER_SHELL);
+        E("failed to request. (%d:%d) \n", PLUGIN_SYNC_CMD_CAPABILITY, CAPABILITY_INTER_SHELL);
         snprintf(g_capabilities.intershell_support, sizeof(g_capabilities.intershell_support),
                     "%s", DISABLED);
     }
@@ -1659,7 +1819,7 @@ static void init_capabilities(void) {
     // File push/pull support
     if(!request_capability_to_plugin(CAPABILITY_FILESYNC, g_capabilities.filesync_support,
                             sizeof(g_capabilities.filesync_support))) {
-        D("failed to request. (%d:%d) \n", PLUGIN_SYNC_CMD_CAPABILITY, CAPABILITY_FILESYNC);
+        E("failed to request. (%d:%d) \n", PLUGIN_SYNC_CMD_CAPABILITY, CAPABILITY_FILESYNC);
         snprintf(g_capabilities.filesync_support, sizeof(g_capabilities.filesync_support),
                     "%s", DISABLED);
     }
@@ -1668,7 +1828,7 @@ static void init_capabilities(void) {
     // USB protocol support
     if(!request_capability_to_plugin(CAPABILITY_USB_PROTOCOL, g_capabilities.usbproto_support,
                             sizeof(g_capabilities.usbproto_support))) {
-        D("failed to request. (%d:%d) \n", PLUGIN_SYNC_CMD_CAPABILITY, CAPABILITY_USB_PROTOCOL);
+        E("failed to request. (%d:%d) \n", PLUGIN_SYNC_CMD_CAPABILITY, CAPABILITY_USB_PROTOCOL);
         snprintf(g_capabilities.usbproto_support, sizeof(g_capabilities.usbproto_support),
                     "%s", DISABLED);
     }
@@ -1677,21 +1837,33 @@ static void init_capabilities(void) {
     // Socket protocol support
     if(!request_capability_to_plugin(CAPABILITY_SOCK_PROTOCOL, g_capabilities.sockproto_support,
                             sizeof(g_capabilities.sockproto_support))) {
-        D("failed to request. (%d:%d) \n", PLUGIN_SYNC_CMD_CAPABILITY, CAPABILITY_SOCK_PROTOCOL);
+        E("failed to request. (%d:%d) \n", PLUGIN_SYNC_CMD_CAPABILITY, CAPABILITY_SOCK_PROTOCOL);
         snprintf(g_capabilities.sockproto_support, sizeof(g_capabilities.sockproto_support),
                     "%s", DISABLED);
     }
 
+    // Sdbd root permission
+    snprintf(g_capabilities.root_permission, sizeof(g_capabilities.root_permission),
+                "%s", DISABLED);
 
     // Root command support
     if(!request_capability_to_plugin(CAPABILITY_ROOT_ONOFF, g_capabilities.rootonoff_support,
                             sizeof(g_capabilities.rootonoff_support))) {
-        D("failed to request. (%d:%d) \n", PLUGIN_SYNC_CMD_CAPABILITY, CAPABILITY_ROOT_ONOFF);
+        E("failed to request. (%d:%d) \n", PLUGIN_SYNC_CMD_CAPABILITY, CAPABILITY_ROOT_ONOFF);
         snprintf(g_capabilities.rootonoff_support, sizeof(g_capabilities.rootonoff_support),
                     "%s", DISABLED);
     }
 
 
+    // Encryption support
+    if(!request_capability_to_plugin(CAPABILITY_ENCRYPTION, g_capabilities.encryption_support,
+                            sizeof(g_capabilities.encryption_support))) {
+        E("failed to request. (%d:%d) \n", PLUGIN_SYNC_CMD_CAPABILITY, CAPABILITY_ENCRYPTION);
+        snprintf(g_capabilities.encryption_support, sizeof(g_capabilities.encryption_support),
+                    "%s", DISABLED);
+    }
+
+
     // Zone support
     ret = is_container_enabled();
     snprintf(g_capabilities.zone_support, sizeof(g_capabilities.zone_support),
@@ -1716,7 +1888,7 @@ static void init_capabilities(void) {
 
     // SDK Tool path
     if (SDK_TOOL_PATH == NULL) {
-        D("fail to get SDK tool path.\n");
+        E("fail to get SDK tool path.\n");
         snprintf(g_capabilities.sdk_toolpath, sizeof(g_capabilities.sdk_toolpath),
                     "%s", UNKNOWN);
     } else {
@@ -1729,7 +1901,7 @@ static void init_capabilities(void) {
     if (ret != SYSTEM_INFO_ERROR_NONE) {
         snprintf(g_capabilities.profile_name, sizeof(g_capabilities.profile_name),
                     "%s", UNKNOWN);
-        D("fail to get profile name:%d\n", errno);
+        E("fail to get profile name:%d\n", errno);
     } else {
         snprintf(g_capabilities.profile_name, sizeof(g_capabilities.profile_name),
                     "%s", value);
@@ -1744,7 +1916,7 @@ static void init_capabilities(void) {
     if (ret != SYSTEM_INFO_ERROR_NONE) {
         snprintf(g_capabilities.vendor_name, sizeof(g_capabilities.vendor_name),
                     "%s", UNKNOWN);
-        D("fail to get the Vendor name:%d\n", errno);
+        E("fail to get the Vendor name:%d\n", errno);
     } else {
         snprintf(g_capabilities.vendor_name, sizeof(g_capabilities.vendor_name),
                     "%s", value);
@@ -1755,21 +1927,35 @@ static void init_capabilities(void) {
 
 
     // Target name of the launch possible
-    if(!request_plugin_cmd(SDBD_CMD_PLUGIN_CAP, SDBD_CAP_TYPE_CANLAUNCH,
-                            g_capabilities.can_launch,
+    if(!request_capability_to_plugin(CAPABILITY_CAN_LAUNCH, g_capabilities.can_launch,
                             sizeof(g_capabilities.can_launch))) {
-        D("failed to request. (%s:%s) \n", SDBD_CMD_PLUGIN_CAP, SDBD_CAP_TYPE_CANLAUNCH);
+        E("failed to request. (%d:%d) \n", PLUGIN_SYNC_CMD_CAPABILITY, CAPABILITY_CAN_LAUNCH);
         snprintf(g_capabilities.can_launch, sizeof(g_capabilities.can_launch),
                     "%s", UNKNOWN);
     }
 
 
+    // Device name
+    value = vconf_get_str(VCONFKEY_SETAPPL_DEVICE_NAME_STR);
+    if(value) {
+        snprintf(g_capabilities.device_name, sizeof(g_capabilities.device_name),
+                "%s", value);
+        if (value != NULL) {
+            free(value);
+        }
+    } else {
+        snprintf(g_capabilities.device_name, sizeof(g_capabilities.device_name),
+                "%s", UNKNOWN);
+        E("fail to get the Device name:%d\n", errno);
+    }
+
+
     // Platform version
     ret = system_info_get_platform_string("http://tizen.org/feature/platform.version", &value);
     if (ret != SYSTEM_INFO_ERROR_NONE) {
         snprintf(g_capabilities.platform_version, sizeof(g_capabilities.platform_version),
                     "%s", UNKNOWN);
-        D("fail to get platform version:%d\n", errno);
+        E("fail to get platform version:%d\n", errno);
     } else {
         snprintf(g_capabilities.platform_version, sizeof(g_capabilities.platform_version),
                     "%s", value);
@@ -1782,7 +1968,7 @@ static void init_capabilities(void) {
     // Product version
     if(!request_capability_to_plugin(CAPABILITY_PRODUCT_VER, g_capabilities.product_version,
                             sizeof(g_capabilities.product_version))) {
-        D("failed to request. (%d:%d) \n", PLUGIN_SYNC_CMD_CAPABILITY, CAPABILITY_PRODUCT_VER);
+        E("failed to request. (%d:%d) \n", PLUGIN_SYNC_CMD_CAPABILITY, CAPABILITY_PRODUCT_VER);
         snprintf(g_capabilities.product_version, sizeof(g_capabilities.product_version),
                     "%s", UNKNOWN);
     }
@@ -1796,7 +1982,7 @@ static void init_capabilities(void) {
     // Sdbd plugin version
     if(!request_capability_to_plugin(CAPABILITY_PLUGIN_VER, g_capabilities.sdbd_plugin_version,
                             sizeof(g_capabilities.sdbd_plugin_version))) {
-        D("failed to request. (%d:%d) \n", PLUGIN_SYNC_CMD_CAPABILITY, CAPABILITY_PLUGIN_VER);
+        E("failed to request. (%d:%d) \n", PLUGIN_SYNC_CMD_CAPABILITY, CAPABILITY_PLUGIN_VER);
         snprintf(g_capabilities.sdbd_plugin_version, sizeof(g_capabilities.sdbd_plugin_version),
                     "%s", UNKNOWN);
     }
@@ -1805,7 +1991,7 @@ static void init_capabilities(void) {
     // sdbd log enable
     if(!request_capability_to_plugin(CAPABILITY_LOG_ENABLE, g_capabilities.log_enable,
                                sizeof(g_capabilities.log_enable))) {
-           D("failed to request. (%d:%d) \n", PLUGIN_SYNC_CMD_CAPABILITY, CAPABILITY_LOG_ENABLE);
+           E("failed to request. (%d:%d) \n", PLUGIN_SYNC_CMD_CAPABILITY, CAPABILITY_LOG_ENABLE);
            snprintf(g_capabilities.log_enable, sizeof(g_capabilities.log_enable),
                        "%s", DISABLED);
     }
@@ -1813,7 +1999,7 @@ static void init_capabilities(void) {
     // sdbd log path
     if(!request_capability_to_plugin(CAPABILITY_LOG_PATH, g_capabilities.log_path,
                                sizeof(g_capabilities.log_path))) {
-           D("failed to request. (%d:%d) \n", PLUGIN_SYNC_CMD_CAPABILITY, CAPABILITY_LOG_PATH);
+           E("failed to request. (%d:%d) \n", PLUGIN_SYNC_CMD_CAPABILITY, CAPABILITY_LOG_PATH);
            snprintf(g_capabilities.log_path, sizeof(g_capabilities.log_path),
                        "%s", UNKNOWN);
     }
@@ -1821,11 +2007,29 @@ static void init_capabilities(void) {
     // Application command support
     if(!request_capability_to_plugin(CAPABILITY_APPCMD, g_capabilities.appcmd_support,
                                sizeof(g_capabilities.appcmd_support))) {
-           D("failed to request. (%d:%d) \n", PLUGIN_SYNC_CMD_CAPABILITY, CAPABILITY_APPCMD);
+           E("failed to request. (%d:%d) \n", PLUGIN_SYNC_CMD_CAPABILITY, CAPABILITY_APPCMD);
            snprintf(g_capabilities.appcmd_support, sizeof(g_capabilities.appcmd_support),
                        "%s", UNKNOWN);
     }
 
+    // appid2pid support
+    ret = is_appid2pid_supported();
+    snprintf(g_capabilities.appid2pid_support, sizeof(g_capabilities.appid2pid_support),
+                "%s", ret == 1 ? ENABLED : DISABLED);
+
+    // pkgcmd debug mode support
+    if(!request_capability_to_plugin(CAPABILITY_DEBUGMODE, g_capabilities.pkgcmd_debugmode,
+                sizeof(g_capabilities.pkgcmd_debugmode))) {
+        E("failed to request. (%d:%d) \n", PLUGIN_SYNC_CMD_CAPABILITY, CAPABILITY_DEBUGMODE);
+        snprintf(g_capabilities.pkgcmd_debugmode, sizeof(g_capabilities.pkgcmd_debugmode),
+                "%s", ENABLED);
+    }
+
+    // netcore debugger support
+    ret = is_netcoredbg_supported();
+    snprintf(g_capabilities.netcoredbg_support, sizeof(g_capabilities.netcoredbg_support),
+             "%s", ret == 1 ? ENABLED : DISABLED);
+
     // Capability version
     snprintf(g_capabilities.sdbd_cap_version, sizeof(g_capabilities.sdbd_cap_version),
                 "%d.%d", SDBD_CAP_VERSION_MAJOR, SDBD_CAP_VERSION_MINOR);
@@ -1833,12 +2037,12 @@ static void init_capabilities(void) {
 
 static int is_support_usbproto()
 {
-    return (!strncmp(g_capabilities.usbproto_support, PLUGIN_RET_ENABLED, strlen(PLUGIN_RET_ENABLED)));
+    return (!strncmp(g_capabilities.usbproto_support, PLUGIN_RET_ENABLED, strlen(PLUGIN_RET_ENABLED)+1));
 }
 
 static int is_support_sockproto()
 {
-    return (!strncmp(g_capabilities.sockproto_support, PLUGIN_RET_ENABLED, strlen(PLUGIN_RET_ENABLED)));
+    return (!strncmp(g_capabilities.sockproto_support, PLUGIN_RET_ENABLED, strlen(PLUGIN_RET_ENABLED)+1));
 }
 
 #define EMULATOR_MODEL_NAME     "Emulator"
@@ -1850,16 +2054,16 @@ static void check_emulator_or_device()
     // Get the model name from model_config.xml
     ret = get_device_name(model_name, sizeof model_name);
     if (ret == 0) {
-        if(!strncmp(model_name, EMULATOR_MODEL_NAME, sizeof(EMULATOR_MODEL_NAME))){
+        if(!strncmp(model_name, EMULATOR_MODEL_NAME, strlen("Emulator")+1)){
             g_is_emulator = 1;
-            D("This target type is Emulator\n");
+            I("This target type is Emulator\n");
         } else {
             g_is_emulator = 0;
-            D("This target type is Device\n");
+            I("This target type is Device\n");
         }
     } else {
         g_is_emulator = -1;
-        D("failed to get the model name.\n");
+        E("failed to get the model name.\n");
     }
 }
 
@@ -1878,52 +2082,36 @@ static void fork_child_handler(void)
     sdb_mutex_unlock(&D_lock);
 }
 
-int sdb_main(int is_daemon, int server_port)
+int sdb_main(int server_port)
 {
-#if !SDB_HOST
     check_emulator_or_device();
 
     load_sdbd_plugin();
 
     init_capabilities();
 
-    sdb_trace_init();
-    start_device_log();
+    //sdb_trace_init();
+    //start_device_log();
 
     init_drop_privileges();
     init_sdk_requirements();
     if (!request_validity_to_plugin(PLUGIN_SYNC_CMD_VERIFY_LAUNCH, NULL)) {
-        D("sdbd should be launched in develop mode.\n");
+        E("sdbd should be launched in develop mode.\n");
         return -1;
     }
 
     umask(000);
 
     pthread_atfork(fork_prepare_handler, fork_parent_handler, fork_child_handler);
-#endif
 
     atexit(sdb_cleanup);
-#ifdef HAVE_WIN32_PROC
-    SetConsoleCtrlHandler( ctrlc_handler, TRUE );
-#elif defined(HAVE_FORKEXEC)
+#if defined(HAVE_FORKEXEC)
     // No SIGCHLD. Let the service subproc handle its children.
     signal(SIGPIPE, SIG_IGN);
 #endif
 
     init_transport_registration();
 
-
-#if SDB_HOST
-    HOST = 1;
-    usb_init();
-    local_init(DEFAULT_SDB_LOCAL_TRANSPORT_PORT);
-
-    char local_name[30];
-    build_local_name(local_name, sizeof(local_name), server_port);
-    if(install_listener(local_name, "*smartsocket*", NULL)) {
-        exit(1);
-    }
-#else
     /* don't listen on a port (default 5037) if running in secure mode */
     /* don't run as root if we are running in secure mode */
 
@@ -1959,7 +2147,7 @@ int sdb_main(int is_daemon, int server_port)
         cap.inheritable = 0;
         capset(&header, &cap);
 #endif
-        D("Local port disabled\n");
+        I("Local port disabled\n");
     } else {
         char local_name[30];
         build_local_name(local_name, sizeof(local_name), server_port);
@@ -2006,21 +2194,10 @@ int sdb_main(int is_daemon, int server_port)
     init_jdwp();
     D("sdb_main(): post init_jdwp()\n");
 #endif
-#endif
 
-    if (is_daemon)
-    {
-        // inform our parent that we are up and running.
-#ifdef HAVE_WIN32_PROC
-        DWORD  count;
-        WriteFile( GetStdHandle( STD_OUTPUT_HANDLE ), "OK\n", 3, &count, NULL );
-#elif defined(HAVE_FORKEXEC)
-        fprintf(stderr, "OK\n");
-#endif
-        start_logging();
-    }
+    sdb_notify_startup(0, "READY=1");
 
-    D("Event loop starting\n");
+    I("Event loop starting\n");
 
     fdevent_loop();
 
@@ -2031,114 +2208,23 @@ int sdb_main(int is_daemon, int server_port)
     return 0;
 }
 
-#if SDB_HOST
-void connect_device(char* host, char* buffer, int buffer_size)
+void sdb_main_service()
 {
-    int port, fd;
-    char* portstr = strchr(host, ':');
-    char hostbuf[100];
-    char serial[100];
-
-    s_strncpy(hostbuf, host, sizeof(hostbuf) - 1);
-    if (portstr) {
-        if (portstr - host >= sizeof(hostbuf)) {
-            snprintf(buffer, buffer_size, "bad host name %s", host);
-            return;
-        }
-        // zero terminate the host at the point we found the colon
-        hostbuf[portstr - host] = 0;
-        if (sscanf(portstr + 1, "%d", &port) == 0) {
-            snprintf(buffer, buffer_size, "bad port number %s", portstr);
-            return;
-        }
-    } else {
-        port = DEFAULT_SDB_LOCAL_TRANSPORT_PORT;
-    }
-
-    snprintf(serial, sizeof(serial), "%s:%d", hostbuf, port);
-    if (find_transport(serial)) {
-        snprintf(buffer, buffer_size, "already connected to %s", serial);
-        return;
-    }
-
-    fd = socket_network_client(hostbuf, port, SOCK_STREAM);
-    if (fd < 0) {
-        snprintf(buffer, buffer_size, "unable to connect to %s", host);
-        return;
-    }
-
-    D("client: connected on remote on fd %d\n", fd);
-    close_on_exec(fd);
-    disable_tcp_nagle(fd);
-    register_socket_transport(fd, serial, port, 0, NULL);
-    snprintf(buffer, buffer_size, "connected to %s", serial);
-}
-
-void connect_emulator(char* port_spec, char* buffer, int buffer_size)
-{
-    char* port_separator = strchr(port_spec, ',');
-    if (!port_separator) {
-        snprintf(buffer, buffer_size,
-                "unable to parse '%s' as <console port>,<sdb port>",
-                port_spec);
-        return;
-    }
-
-    // Zero-terminate console port and make port_separator point to 2nd port.
-    *port_separator++ = 0;
-    int console_port = strtol(port_spec, NULL, 0);
-    int sdb_port = strtol(port_separator, NULL, 0);
-    if (!(console_port > 0 && sdb_port > 0)) {
-        *(port_separator - 1) = ',';
-        snprintf(buffer, buffer_size,
-                "Invalid port numbers: Expected positive numbers, got '%s'",
-                port_spec);
-        return;
-    }
-
-    /* Check if the emulator is already known.
-     * Note: There's a small but harmless race condition here: An emulator not
-     * present just yet could be registered by another invocation right
-     * after doing this check here. However, local_connect protects
-     * against double-registration too. From here, a better error message
-     * can be produced. In the case of the race condition, the very specific
-     * error message won't be shown, but the data doesn't get corrupted. */
-    atransport* known_emulator = find_emulator_transport_by_sdb_port(sdb_port);
-    if (known_emulator != NULL) {
-        snprintf(buffer, buffer_size,
-                "Emulator on port %d already registered.", sdb_port);
-        return;
-    }
-
-    /* Check if more emulators can be registered. Similar unproblematic
-     * race condition as above. */
-    int candidate_slot = get_available_local_transport_index();
-    if (candidate_slot < 0) {
-        snprintf(buffer, buffer_size, "Cannot accept more emulators.");
-        return;
-    }
-
-    /* Preconditions met, try to connect to the emulator. */
-    if (!local_connect_arbitrary_ports(console_port, sdb_port, NULL)) {
-        snprintf(buffer, buffer_size,
-                "Connected to emulator on ports %d,%d", console_port, sdb_port);
-    } else {
-        snprintf(buffer, buffer_size,
-                "Could not connect to emulator on ports %d,%d",
-                console_port, sdb_port);
-    }
+    load_sdbd_plugin();
+    init_capabilities();
+    init_sdk_requirements();
+    atexit(sdb_service_cleanup);
 }
-#endif
 
 int copy_packet(apacket* dest, apacket* src) {
 
     if(dest == NULL) {
-        D("dest packet is NULL\n");
+        E("dest packet is NULL\n");
         return -1;
     }
 
     if(src == NULL) {
-        D("src packet is NULL\n");
+        E("src packet is NULL\n");
         return -1;
     }
 
@@ -2170,132 +2256,6 @@ int handle_host_request(char *service, transport_type ttype, char* serial, int r
         exit(0);
     }
 
-#if SDB_HOST
-    // "transport:" is used for switching transport with a specified serial number
-    // "transport-usb:" is used for switching transport to the only USB transport
-    // "transport-local:" is used for switching transport to the only local transport
-    // "transport-any:" is used for switching transport to the only transport
-    if (!strncmp(service, "transport", strlen("transport"))) {
-        char* error_string = "unknown failure";
-        transport_type type = kTransportAny;
-
-        if (!strncmp(service, "transport-usb", strlen("transport-usb"))) {
-            type = kTransportUsb;
-        } else if (!strncmp(service, "transport-local", strlen("transport-local"))) {
-            type = kTransportLocal;
-        } else if (!strncmp(service, "transport-any", strlen("transport-any"))) {
-            type = kTransportAny;
-        } else if (!strncmp(service, "transport:", strlen("transport:"))) {
-            service += strlen("transport:");
-            serial = service;
-        }
-
-        transport = acquire_one_transport(CS_ANY, type, serial, &error_string);
-
-        if (transport) {
-            s->transport = transport;
-            sdb_write(reply_fd, "OKAY", 4);
-        } else {
-            sendfailmsg(reply_fd, error_string);
-        }
-        return 1;
-    }
-
-    // return a list of all connected devices
-    if (!strcmp(service, "devices")) {
-        char buffer[4096];
-        memset(buf, 0, sizeof(buf));
-        memset(buffer, 0, sizeof(buffer));
-        D("Getting device list \n");
-        list_transports(buffer, sizeof(buffer));
-        snprintf(buf, sizeof(buf), "OKAY%04x%s",(unsigned)strlen(buffer),buffer);
-        D("Wrote device list \n");
-        writex(reply_fd, buf, strlen(buf));
-        return 0;
-    }
-
-    // add a new TCP transport, device or emulator
-    if (!strncmp(service, "connect:", 8)) {
-        char buffer[4096];
-        char* host = service + 8;
-        if (!strncmp(host, "emu:", 4)) {
-            connect_emulator(host + 4, buffer, sizeof(buffer));
-        } else {
-            connect_device(host, buffer, sizeof(buffer));
-        }
-        // Send response for emulator and device
-        snprintf(buf, sizeof(buf), "OKAY%04x%s",(unsigned)strlen(buffer), buffer);
-        writex(reply_fd, buf, strlen(buf));
-        return 0;
-    }
-
-    // remove TCP transport
-    if (!strncmp(service, "disconnect:", 11)) {
-        char buffer[4096];
-        memset(buffer, 0, sizeof(buffer));
-        char* serial = service + 11;
-        if (serial[0] == 0) {
-            // disconnect from all TCP devices
-            unregister_all_tcp_transports();
-        } else {
-            char hostbuf[100];
-            // assume port 26101 if no port is specified
-            if (!strchr(serial, ':')) {
-                snprintf(hostbuf, sizeof(hostbuf) - 1, "%s:26101", serial);
-                serial = hostbuf;
-            }
-            atransport *t = find_transport(serial);
-
-            if (t) {
-                unregister_transport(t);
-            } else {
-                snprintf(buffer, sizeof(buffer), "No such device %s", serial);
-            }
-        }
-
-        snprintf(buf, sizeof(buf), "OKAY%04x%s",(unsigned)strlen(buffer), buffer);
-        writex(reply_fd, buf, strlen(buf));
-        return 0;
-    }
-
-    // returns our value for SDB_SERVER_VERSION
-    if (!strcmp(service, "version")) {
-        char version[12];
-        snprintf(version, sizeof version, "%04x", SDB_SERVER_VERSION);
-        snprintf(buf, sizeof buf, "OKAY%04x%s", (unsigned)strlen(version), version);
-        writex(reply_fd, buf, strlen(buf));
-        return 0;
-    }
-
-    if(!strncmp(service,"get-serialno",strlen("get-serialno"))) {
-        char *out = "unknown";
-         transport = acquire_one_transport(CS_ANY, ttype, serial, NULL);
-       if (transport && transport->serial) {
-            out = transport->serial;
-        }
-        snprintf(buf, sizeof buf, "OKAY%04x%s",(unsigned)strlen(out),out);
-        writex(reply_fd, buf, strlen(buf));
-        return 0;
-    }
-    // indicates a new emulator instance has started
-       if (!strncmp(service,"emulator:",9)) { /* tizen specific */
-           char *tmp = strtok(service+9, DEVICEMAP_SEPARATOR);
-           int  port = 0;
-
-           if (tmp == NULL) {
-               port = atoi(service+9);
-           } else {
-               port = atoi(tmp);
-               tmp = strtok(NULL, DEVICEMAP_SEPARATOR);
-               if (tmp != NULL) {
-                   local_connect(port, tmp);
-               }
-           }
-           local_connect(port, NULL);
-        return 0;
-    }
-#endif // SDB_HOST
-
     if(!strncmp(service,"forward:",8) || !strncmp(service,"killforward:",12)) {
         char *local, *remote, *err;
         int r;
@@ -2350,56 +2310,3 @@ int handle_host_request(char *service, transport_type ttype, char* serial, int r
     }
     return -1;
 }
-
-#if !SDB_HOST
-int recovery_mode = 0;
-#endif
-
-int main(int argc, char **argv)
-{
-#if SDB_HOST
-    sdb_sysdeps_init();
-    sdb_trace_init();
-    return sdb_commandline(argc - 1, argv + 1);
-#else
-    /* If sdbd runs inside the emulator this will enable sdb tracing via
-     * sdb-debug qemud service in the emulator. */
-#if 0 /* tizen specific */
-    sdb_qemu_trace_init();
-    if((argc > 1) && (!strcmp(argv[1],"recovery"))) {
-        sdb_device_banner = "recovery";
-        recovery_mode = 1;
-    }
-#endif
-
-    apply_sdbd_commandline_defaults(&sdbd_commandline_args);
-    int parse_ret = parse_sdbd_commandline(&sdbd_commandline_args, argc, argv);
-
-    // TODO: Add detailed error messages
-    // TODO: Add individual messages for help and usage
-    if(parse_ret != SDBD_COMMANDLINE_SUCCESS) {
-        if (parse_ret == SDBD_COMMANDLINE_HELP
-                || parse_ret == SDBD_COMMANDLINE_USAGE) {
-            // User requested help or usage
-            print_sdbd_usage_message(stdout);
-            return EXIT_SUCCESS;
-        }
-
-        // Print usage message because of invalid options
-        print_sdbd_usage_message(stderr);
-        return EXIT_FAILURE;
-    }
-
-#if !SDB_HOST
-    if (daemonize() < 0)
-        fatal("daemonize() failed: errno:%d", errno);
-#endif
-
-    D("Handling main()\n");
-
-    //sdbd will never die on emulator!
-    signal(SIGTERM, handle_sig_term); /* tizen specific */
-    return sdb_main(0, DEFAULT_SDB_PORT);
-#endif
-}
-