From 5afdcc0a0ad220800bf6366343f58e79ac27f7b2 Mon Sep 17 00:00:00 2001 From: Jaewon Lim Date: Wed, 9 Nov 2016 17:51:19 -0800 Subject: [PATCH 01/16] Revert "Revert "Add the appcmd protocol for product extended routine."" This reverts commit 49a0a10876e193945a71849f0519b19883f4752a. Change-Id: If226fb2f2118877976170d80406b53f318344e89 --- CMakeLists.txt | 1 + src/default_plugin.h | 1 + src/default_plugin_appcmd.c | 779 ++++++++++++++++++++++++++++++++++++++++++++ src/default_plugin_basic.c | 2 + src/default_plugin_event.c | 2 +- src/default_plugin_main.c | 8 +- src/log.h | 3 +- src/plugin.c | 91 ++++++ src/plugin.h | 5 + src/sdb.c | 29 +- src/sdb.h | 9 +- src/sdbd_plugin.h | 6 +- src/services.c | 21 +- 13 files changed, 939 insertions(+), 18 deletions(-) create mode 100644 src/default_plugin_appcmd.c diff --git a/CMakeLists.txt b/CMakeLists.txt index ae6f310..6c88b77 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -55,6 +55,7 @@ SET(SDBD_SRCS src/default_plugin_basic.c src/default_plugin_main.c src/default_plugin_event.c + src/default_plugin_appcmd.c src/hashtable.c src/plugin.c ) diff --git a/src/default_plugin.h b/src/default_plugin.h index b8d44f3..800e495 100644 --- a/src/default_plugin.h +++ b/src/default_plugin.h @@ -31,6 +31,7 @@ int auth_support ( parameters* in, parameters* out ); int auth_get_key_file_paths ( parameters* in, parameters* out ); int confirm_public_key ( parameters* in, int out_fd ); +int appcmd_service ( parameters* in, int out_fd ); void create_pwlock_thread(); diff --git a/src/default_plugin_appcmd.c b/src/default_plugin_appcmd.c new file mode 100644 index 0000000..947a8e5 --- /dev/null +++ b/src/default_plugin_appcmd.c @@ -0,0 +1,779 @@ +/* + * Copyright (c) 2011 Samsung Electronics Co., Ltd All Rights Reserved + * + * 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. + */ + +#include +#include +#include +#include +#include + +#define TRACE_TAG TRACE_APPCMD + +#include "sysdeps.h" +#include "sdb.h" +#include "strutils.h" +#include "utils.h" +#include "log.h" + +#include "parameter.h" +#include "sdbd_plugin.h" + +#if APPCMD_USING_PKGMGR +#include +#include +#endif + +#include + +#define APPCMD_RESULT_BUFSIZE (4096) + +typedef struct appcmd_info appcmd_info; +typedef int (*appcmd_gen_shellcmd)(appcmd_info*); +typedef void (*appcmd_receiver)(int, int); +struct appcmd_info { + int fd; + + char* args[MAX_TOKENS]; + size_t args_cnt; + char* raw_command; + + appcmd_gen_shellcmd gen_cmd_func; + appcmd_receiver receiver_func; + + char shell_cmd[SDBD_SHELL_CMD_MAX]; + + int exitcode; +}; + +static int appcmd_install_gen_shellcmd(appcmd_info* p_info) { + char *type = NULL; + char *pkgpath = NULL; + char *pkgid = NULL; + char *teppath = NULL; + char *buf = p_info->shell_cmd; + int len = sizeof(p_info->shell_cmd); + + if (p_info->args_cnt != 5) { + D("failed to parse appcmd.(cnt=%d)\n", p_info->args_cnt); + return -1; + } + + type = p_info->args[1]; + pkgpath = p_info->args[2]; + pkgid = p_info->args[3]; + teppath = p_info->args[4]; + + D("args: type=%s, pkgpath=%s, pkgid=%s, teppath=%s\n", type, pkgpath, pkgid, teppath); + + if (strncmp(pkgid, "null", 4) == 0) { + if (strncmp(teppath, "null", 4) == 0) { + /* Normal install case */ + snprintf(buf, len, "pkgcmd -i -q -t %s -p %s -G", type, pkgpath); + } else { + /* TEP install case */ + snprintf(buf, len, "pkgcmd -i -q -p %s -e %s -G", pkgpath, teppath); + } + } else { + /* Re-install case */ + snprintf(buf, len, "pkgcmd -r -q -t %s -n %s", type, pkgid); + } + + return 0; +} + +static int appcmd_uninstall_gen_shellcmd(appcmd_info* p_info) { + char *type = NULL; + char *pkgid = NULL; + char *buf = p_info->shell_cmd; + int len = sizeof(p_info->shell_cmd); + + if (p_info->args_cnt != 3) { + D("failed to parse appcmd.(cnt=%d)\n", p_info->args_cnt); + return -1; + } + + type = p_info->args[1]; + pkgid = p_info->args[2]; + + D("args: type=%s, pkgid=%s\n", type, pkgid); + + snprintf(buf, len, "pkgcmd -u -q -t %s -n %s", type, pkgid); + + return 0; +} + +static int appcmd_runapp_gen_shellcmd(appcmd_info* p_info) { + char *appid = NULL; + char *buf = p_info->shell_cmd; + int len = sizeof(p_info->shell_cmd); + + if (p_info->args_cnt != 2) { + D("failed to parse appcmd.(cnt=%d)\n", p_info->args_cnt); + return -1; + } + + appid = p_info->args[1]; + + D("args: appid=%s\n", appid); + + snprintf(buf, len, "/usr/bin/app_launcher --start %s", appid); + + return 0; +} + +static int appcmd_rununittestapp_gen_shellcmd(appcmd_info* p_info) { + char *appid = NULL; + char *usr_args = NULL; + char *buf = p_info->shell_cmd; + int len = sizeof(p_info->shell_cmd); + char *ptr = NULL; + char *p_service = NULL; + char *p_appid = NULL; + + free_strings(p_info->args, p_info->args_cnt); + + p_service = strtok_r(p_info->raw_command, ":", &ptr); + p_appid = strtok_r(NULL, ":", &ptr); + if (p_service == NULL || p_appid == NULL) { + D("failed to parse appcmd.(cnt=%d)\n", p_info->args_cnt); + return -1; + } + + p_info->args_cnt = 3; + p_info->args[0] = strdup(p_service); + p_info->args[1] = strdup(p_appid); + p_info->args[2] = strdup(ptr); + + appid = p_info->args[1]; + usr_args = p_info->args[2]; + + D("args: appid=%s, usr_args=%s\n", appid, usr_args); + + snprintf(buf, len, "/usr/bin/app_launcher -s %s __AUL_SDK__ UNIT_TEST __LAUNCH_APP_MODE__ SYNC __DLP_UNIT_TEST_ARG__ \'%s\'", appid, usr_args); + + return 0; +} + +static int appcmd_killapp_gen_shellcmd(appcmd_info* p_info) { + char *appid = NULL; + char *buf = p_info->shell_cmd; + int len = sizeof(p_info->shell_cmd); + + if (p_info->args_cnt != 2) { + D("failed to parse appcmd.(cnt=%d)\n", p_info->args_cnt); + return -1; + } + + appid = p_info->args[1]; + + D("args: appid=%s\n", appid); + + snprintf(buf, len, "/usr/bin/app_launcher --kill %s", appid); + + return 0; +} + +static int appcmd_packagelist_gen_shellcmd(appcmd_info* p_info) { + char *type = NULL; + char *buf = p_info->shell_cmd; + int len = sizeof(p_info->shell_cmd); + + if (p_info->args_cnt != 2) { + D("failed to parse appcmd.(cnt=%d)\n", p_info->args_cnt); + return -1; + } + + type = p_info->args[1]; + + D("args: type=%s\n", type); + + snprintf(buf, len, "/usr/bin/pkgcmd -l -t %s", type); + + return 0; +} + +static int appcmd_debugwebapp_gen_shellcmd(appcmd_info* p_info) { + char *appid = NULL; + char *buf = p_info->shell_cmd; + int len = sizeof(p_info->shell_cmd); + + if (p_info->args_cnt != 2) { + D("failed to parse appcmd.(cnt=%d)\n", p_info->args_cnt); + return -1; + } + + appid = p_info->args[1]; + + D("args: appid=%s\n", appid); + + snprintf(buf, len, "/usr/bin/app_launcher --start %s -w", appid); + + return 0; +} + +static int appcmd_debugnativeapp_gen_shellcmd(appcmd_info* p_info) { + char *debug_port = NULL; + char *appid= NULL; + char *pid_str = NULL; + char *gdbserver_path = NULL; + char *buf = p_info->shell_cmd; + int pid = -1; + int len = sizeof(p_info->shell_cmd); + + if (p_info->args_cnt != 5) { + D("failed to parse appcmd.(cnt=%d)\n", p_info->args_cnt); + return -1; + } + + debug_port = p_info->args[1]; + appid= p_info->args[2]; + pid_str = p_info->args[3]; + gdbserver_path = p_info->args[4]; // not used. for 3.0 platform. + + pid = atoi(pid_str); + D("args: debug_port=%s, appid=%s, pid=%d, gdbserver_path=%s\n", debug_port, appid, pid, gdbserver_path); + + if (pid == -1) { + snprintf(buf, len, "/usr/bin/app_launcher --start %s __AUL_SDK__ DEBUG __DLP_DEBUG_ARG__ :%s __DLP_GDBSERVER_PATH__ %s", appid, debug_port, gdbserver_path); + } else { + /* attach mode */ + snprintf(buf, len, "/usr/bin/launch_debug %s __AUL_SDK__ ATTACH __DLP_GDBSERVER_PATH__ %s __DLP_ATTACH_ARG__ --attach,:%s,%d", appid, gdbserver_path, debug_port, pid); + } + + return 0; +} + +static int appcmd_appinfo_gen_shellcmd(appcmd_info* p_info) { + char *pkgid = NULL; + char *buf = p_info->shell_cmd; + int len = sizeof(p_info->shell_cmd); + + if (p_info->args_cnt != 2) { + D("failed to parse appcmd.(cnt=%d)\n", p_info->args_cnt); + return -1; + } + + pkgid = p_info->args[1]; + + D("args: pkgid=%s\n", pkgid); + + snprintf(buf, len, "/usr/bin/pkginfo --list %s", pkgid); + + return 0; +} + +static void appcmd_receiver_debugwebapp(int fd_in, int fd_out) +{ + char buf[4096] = {0,}; + char port_str[32] = {0,}; + char out_buf[128] = {0,}; + char* sub_str = NULL; + int r; + + for(;;) { + memset(buf, 0, sizeof(buf)); + r = read_line(fd_in, buf, sizeof(buf)); + if (r == 0) { + break; + } else if(r < 0) { + if (errno == EINTR) { + continue; + } else { + break; + } + } + + D("debug webapp output : %s\n", buf); + sub_str = strstr(buf, "port: "); + if (sub_str != NULL && sscanf(sub_str, "port: %s", port_str) == 1) { + snprintf(out_buf, sizeof(out_buf), "\n%s:%s\n", MESSAGE_PREFIX_APPCMD_RETURN, port_str); + writex(fd_out, out_buf, strlen(out_buf)+1); + break; + } + } +} + +static void appcmd_receiver_default(int fd_in, int fd_out) +{ + char buf[4096] = {0,}; + int r; + + for(;;) { + memset(buf, 0, sizeof(buf)); + r = sdb_read(fd_in, buf, sizeof(buf)); + if (r == 0) { + break; + } else if(r < 0) { + if (errno == EINTR) { + continue; + } else { + break; + } + } + + writex(fd_out, buf, strlen(buf)+1); + } +} + +static void appcmd_receiver_packagelist(int fd_in, int fd_out) +{ + char buf[4096] = {0,}; + char out_buf[4096] = {0,}; + int out_ptr = 0; + int r; + + snprintf(out_buf, sizeof(out_buf), "\n%s", MESSAGE_PREFIX_APPCMD_RETURN); + out_ptr = strlen(out_buf); + + for(;;) { + memset(buf, 0, sizeof(buf)); + r = read_line(fd_in, buf, sizeof(buf)); + if (r == 0) { + break; + } else if(r < 0) { + if (errno == EINTR) { + continue; + } else { + break; + } + } + + D("pkgcmd output : %s\n", buf); + char* sub1 = NULL; + char* sub2 = NULL; + sub1 = strstr(buf, "pkgid ["); + if (sub1 != NULL) { + sub1 = strstr(sub1, "[")+1; + sub2 = strstr(sub1, "]"); + sub2[0] = '\0'; + + snprintf(out_buf+out_ptr, sizeof(out_buf)-out_ptr, ":%s", sub1); + out_ptr += strlen(sub1)+1; + } + } + + snprintf(out_buf+out_ptr, sizeof(out_buf)-out_ptr, "\n"); + + D("package list: %s\n", out_buf); + writex(fd_out, out_buf, strlen(out_buf)+1); +} + +static void appcmd_receiver_appinfo(int fd_in, int fd_out) +{ + char buf[4096] = {0,}; + char out_buf[4096] = {0,}; + char appid[128] = {0,}; + char apptype[128] = {0,}; + int out_ptr = 0; + int r; + + snprintf(out_buf, sizeof(out_buf), "\n%s", MESSAGE_PREFIX_APPCMD_RETURN); + out_ptr = strlen(out_buf); + + for(;;) { + memset(buf, 0, sizeof(buf)); + r = read_line(fd_in, buf, sizeof(buf)); + if (r == 0) { + break; + } else if(r < 0) { + if (errno == EINTR) { + continue; + } else { + break; + } + } + + D("pkginfo output : %s\n", buf); + + if (!strncmp(buf, "Appid: ", 7)) { + memset(appid, 0, sizeof(appid)); + sscanf(buf, "Appid: %s", appid); + + snprintf(out_buf+out_ptr, sizeof(out_buf)-out_ptr, ":%s", appid); + out_ptr += strlen(appid)+1; + } else if (!strncmp(buf, "Apptype: ", 9)) { + memset(apptype, 0, sizeof(apptype)); + sscanf(buf, "Apptype: %s", apptype); + + snprintf(out_buf+out_ptr, sizeof(out_buf)-out_ptr, ":%s", apptype); + out_ptr += strlen(apptype)+1; + } + } + + snprintf(out_buf+out_ptr, sizeof(out_buf)-out_ptr, "\n"); + + D("app info: %s\n", out_buf); + writex(fd_out, out_buf, strlen(out_buf)+1); +} + +static int exec_appcmd_shell_process(appcmd_info* p_info) { + int ptm_fd = -1; + pid_t pid; + char *value = NULL; + char *trim_value = NULL; + char path[PATH_MAX]; + memset(path, 0, sizeof(path)); + + char *envp[] = { + "TERM=linux", /* without this, some programs based on screen can't work, e.g. top */ + "DISPLAY=:0", /* without this, some programs based on without launchpad can't work */ + NULL, + NULL, + NULL, + NULL, + NULL + }; + + // For the SDK user privilege. + envp[2] = "HOME=/home/developer"; + get_env("ENV_PATH", &value); + if (value != NULL) { + trim_value = str_trim(value); + if (trim_value != NULL) { + // if string is not including 'PATH=', append it. + if (strncmp(trim_value, "PATH", 4)) { + snprintf(path, sizeof(path), "PATH=%s", trim_value); + } else { + snprintf(path, sizeof(path), "%s", trim_value); + } + envp[3] = path; + free(trim_value); + } else { + envp[3] = value; + } + } + + D("path env:%s,%s,%s,%s\n", envp[0], envp[1], envp[2], envp[3]); + + char *args[] = { + SHELL_COMMAND, + "-c", + NULL, + NULL, + }; + args[2] = p_info->shell_cmd; + + ptm_fd = create_subprocess(SHELL_COMMAND, &pid, (char * const*)args, (char * const*)envp); + D("create_subprocess() ptm_fd=%d pid=%d\n", ptm_fd, pid); + if (ptm_fd < 0) { + D("cannot create service thread\n"); + return -1; + } + + if (p_info->receiver_func != NULL) { + p_info->receiver_func(ptm_fd, p_info->fd); + } + + // wait for shell process + for (;;) { + int status; + pid_t p = waitpid(pid, &status, 0); + if (p == pid) { + D("fd=%d, post waitpid(pid=%d) status=%04x\n", p_info->fd, p, status); + + if (WIFEXITED(status)) { + p_info->exitcode = WEXITSTATUS(status); + D("*** Exit code %d\n", p_info->exitcode); + break; + } + } + } + D("shell exited fd=%d of pid=%d err=%d\n", p_info->fd, pid, errno); + + return 0; +} + +#if APPCMD_USING_PKGMGR +static int get_pkg_info(char* pkgid, char* pkginfo_buf, int buf_size) { + pkgmgrinfo_pkginfo_h handle; + pkgmgr_client* pc = NULL; + char* pkgname = NULL; + char* type = NULL; + bool is_removable = 0; + int is_running = 0; + int ret = -1; + int pid = -1; + + ret = pkgmgrinfo_pkginfo_get_pkginfo(pkgid, &handle); + if (ret < 0) { + D("failed to get pkginfo handle.\n"); + return -1; + } + + ret = pkgmgrinfo_pkginfo_get_mainappid(handle, &pkgname); + if (ret < 0) { + D("failed to get pkg name\n"); + return -1; + } + + ret = pkgmgrinfo_pkginfo_get_type(handle, &type); + if (ret < 0) { + D("failed to get pkg type.\n"); + return -1; + } + + ret = pkgmgrinfo_pkginfo_is_removable(handle, &is_removable); + if (ret < 0) { + D("failed to get removable info.\n"); + return -1; + } + + pc = pkgmgr_client_new(PC_REQUEST); + if (pc == NULL) { + D("failed to create pkgmgr client.\n"); + return -1; + } + + ret = pkgmgr_client_request_service(PM_REQUEST_CHECK_APP, 0, pc, NULL, pkgid, NULL, NULL, &pid); + if (ret < 0) { + D("failed to get running state.\n"); + return -1; + } + is_running = ((pid > 0) ? 1:0); + + D("pkginfo: pkgname=%s, type=%s, is_removagle=%d, is_running=%d, pid=%d\n", pkgname, type, is_removable, is_running, pid); + snprintf(pkginfo_buf, buf_size, "%s:%s:%d:%d", pkgname, type, is_removable, is_running); + return 0; +} + +static void run_appcmd_packageinfo(appcmd_info* p_info) { + char result_buf[APPCMD_RESULT_BUFSIZE] = {0,}; + char pkginfo_buf[256] = {0,}; + char *type = NULL; + char *pkgid = NULL; + + p_info->exitcode = -1; + + if (p_info->args_cnt != 3) { + D("failed to parse appcmd.(cnt=%d)\n", p_info->args_cnt); + return; + } + + type = p_info->args[1]; + pkgid= p_info->args[2]; + + D("args: type=%s, pkgid=%s\n", type, pkgid); + + if (get_pkg_info(pkgid, pkginfo_buf, sizeof(pkginfo_buf)) == 0) { + D("success to get pkginfo. (%s)\n", pkginfo_buf); + p_info->exitcode = 0; + snprintf(result_buf, sizeof(result_buf), "\n%s:%s\n", MESSAGE_PREFIX_APPCMD_RETURN, pkginfo_buf); + writex(p_info->fd, result_buf, strlen(result_buf)); + } else { + D("failed to get pkginfo.\n"); + } +} +#else +static int appcmd_packageinfo_gen_shellcmd(appcmd_info* p_info) { + char *pkgid = NULL; + char *buf = p_info->shell_cmd; + int len = sizeof(p_info->shell_cmd); + + if (p_info->args_cnt != 2) { + D("failed to parse appcmd.(cnt=%d)\n", p_info->args_cnt); + return -1; + } + + pkgid = p_info->args[1]; + + D("args: pkgid=%s\n", pkgid); + + snprintf(buf, len, "/usr/bin/pkginfo --pkg %s;/usr/bin/pkgcmd -C -n %s", pkgid, pkgid); + + return 0; +} + +static void appcmd_receiver_packageinfo(int fd_in, int fd_out) +{ + char buf[4096] = {0,}; + char mainapp_id[128] = {0,}; + char type[128] = {0,}; + int is_removable = 0; + int is_running = 0; + int r; + + for(;;) { + memset(buf, 0, sizeof(buf)); + r = read_line(fd_in, buf, sizeof(buf)); + if (r == 0) { + break; + } else if(r < 0) { + if (errno == EINTR) { + continue; + } else { + break; + } + } + + if (!strncmp(buf, "mainappid : ", 12)) { + sscanf(buf, "mainappid : %s", mainapp_id); + } else if (!strncmp(buf, "Type: ", 6)) { + sscanf(buf, "Type: %s", type); + } else if (!strncmp(buf, "Removable: ", 11)) { + sscanf(buf, "Removable: %d", &is_removable); + } else if (strstr(buf, " is Running") != NULL) { + is_running = 1; + } + } + + memset(buf, 0, sizeof(buf)); + snprintf(buf, sizeof(buf), "\n%s:%s:%s:%d:%d\n", + MESSAGE_PREFIX_APPCMD_RETURN, mainapp_id, type, is_removable, is_running); + + D("package info: %s\n", buf); + writex(fd_out, buf, strlen(buf)+1); +} +#endif + +static void run_appcmd_appinstallpath(appcmd_info* p_info) { + char result_buf[APPCMD_RESULT_BUFSIZE] = {0,}; + + p_info->exitcode = -1; + + const char* path = tzplatform_getenv(TZ_SDK_HOME); + if (path != NULL) { + p_info->exitcode = 0; + snprintf(result_buf, sizeof(result_buf), "\n%s:%s/apps_rw/\n", MESSAGE_PREFIX_APPCMD_RETURN, path); + writex(p_info->fd, result_buf, strlen(result_buf)); + } else { + D("failed to get application install path from tzplatform_getenv."); + } +} + +static void run_appcmd_with_shell_process(appcmd_info* p_info) { + int ret = -1; + + if (p_info == NULL || p_info->gen_cmd_func == NULL) { + D("Invalid arguments.\n"); + p_info->exitcode = -1; + return; + } + + ret = p_info->gen_cmd_func(p_info); + if (ret < 0) { + D("failed to generate install shell command.\n"); + p_info->exitcode = -1; + } else { + ret = exec_appcmd_shell_process(p_info); + D("exec_appcmd_shell_process: ret=%d, exitcode=%d\n", ret, p_info->exitcode); + if (ret < 0) { + D("failed to run shell process\n"); + p_info->exitcode = -1; + } + } +} + +int appcmd_service( parameters* in, int out_fd ) { + appcmd_info info; + char result_buf[APPCMD_RESULT_BUFSIZE] = {0,}; + char* service_name = NULL; + char* command = NULL; + + if (in == NULL || in->number_of_parameter != 1 || in->array_of_parameter == NULL + || in->array_of_parameter[0].type != type_string) { + D ( "Invalid argument\n" ); + return PLUGIN_CMD_FAIL; + } + + command = in->array_of_parameter[0].v_string.data; + D("command=%s(FD:%d)\n", command, out_fd); + + memset(&info, 0, sizeof(info)); + + /* appcmd parameter data map + * "service name:arg1:arg2:...:argN" */ + info.args_cnt = tokenize(command, ":", info.args, MAX_TOKENS); + D("args_cnt=%d\n", info.args_cnt); + if (info.args_cnt < 1) { + D("failed to parse appcmd for install. (%s)\n", command); + info.exitcode = -1; + goto appcmd_done; + } + + info.fd = out_fd; + info.exitcode = -1; + info.raw_command = command; + + service_name = info.args[0]; + D("service name=%s\n", service_name); + + if (strncmp(service_name, "install", 7) == 0) { + info.receiver_func = appcmd_receiver_default; + info.gen_cmd_func = appcmd_install_gen_shellcmd; + run_appcmd_with_shell_process(&info); + // remove pkg files + if (info.args[2] != NULL) { + sdb_unlink(info.args[2]); + } + } else if (strncmp(service_name, "uninstall", 9) == 0) { + info.receiver_func = appcmd_receiver_default; + info.gen_cmd_func = appcmd_uninstall_gen_shellcmd; + run_appcmd_with_shell_process(&info); + } else if (strncmp(service_name, "appinfo", 7) == 0) { + info.gen_cmd_func = appcmd_appinfo_gen_shellcmd; + info.receiver_func = appcmd_receiver_appinfo; + run_appcmd_with_shell_process(&info); + } else if (strncmp(service_name, "packageinfo", 11) == 0) { +#if APPCMD_USING_PKGMGR + run_appcmd_packageinfo(&info); +#else + info.gen_cmd_func = appcmd_packageinfo_gen_shellcmd; + info.receiver_func = appcmd_receiver_packageinfo; + run_appcmd_with_shell_process(&info); +#endif + } else if (strncmp(service_name, "packagelist", 11) == 0) { + info.gen_cmd_func = appcmd_packagelist_gen_shellcmd; + info.receiver_func = appcmd_receiver_packagelist; + run_appcmd_with_shell_process(&info); + } else if (strncmp(service_name, "appinstallpath", 14) == 0) { + run_appcmd_appinstallpath(&info); + } else if (strncmp(service_name, "runapp", 6) == 0) { + info.receiver_func = appcmd_receiver_default; + info.gen_cmd_func = appcmd_runapp_gen_shellcmd; + run_appcmd_with_shell_process(&info); + } else if (strncmp(service_name, "rununittestapp", 14) == 0) { + info.receiver_func = appcmd_receiver_default; + info.gen_cmd_func = appcmd_rununittestapp_gen_shellcmd; + run_appcmd_with_shell_process(&info); + } else if (strncmp(service_name, "killapp", 7) == 0) { + info.receiver_func = appcmd_receiver_default; + info.gen_cmd_func = appcmd_killapp_gen_shellcmd; + run_appcmd_with_shell_process(&info); + } else if (strncmp(service_name, "debugwebapp", 11) == 0) { + info.gen_cmd_func = appcmd_debugwebapp_gen_shellcmd; + info.receiver_func = appcmd_receiver_debugwebapp; + run_appcmd_with_shell_process(&info); + } else if (strncmp(service_name, "debugnativeapp", 14) == 0) { + info.gen_cmd_func = appcmd_debugnativeapp_gen_shellcmd; + run_appcmd_with_shell_process(&info); + } else { + D("not supported appcmd service. (%s)\n", service_name); + info.exitcode = -1; + goto appcmd_done; + } + +appcmd_done: + free_strings(info.args, info.args_cnt); + + snprintf(result_buf, sizeof(result_buf), "\n%s:%d\n", MESSAGE_PREFIX_APPCMD_EXITCODE, info.exitcode); + writex(out_fd, result_buf, strlen(result_buf)); + + if (info.exitcode != 0) { + return PLUGIN_CMD_FAIL; + } + + return PLUGIN_CMD_SUCCESS; +} diff --git a/src/default_plugin_basic.c b/src/default_plugin_basic.c index 58464c7..f8ceba0 100644 --- a/src/default_plugin_basic.c +++ b/src/default_plugin_basic.c @@ -80,6 +80,8 @@ int get_plugin_capability ( parameters* in, parameters* out ) make_string_parameter ( & ( out->array_of_parameter[0] ), "%s", PLUGIN_RET_DISABLED ); } else if ( capability == CAPABILITY_LOG_PATH ) { make_string_parameter ( & ( out->array_of_parameter[0] ), "%s", LOG_DIRECTORY ); + } else if ( capability == CAPABILITY_APPCMD ) { + make_string_parameter ( & ( out->array_of_parameter[0] ), "%s", PLUGIN_RET_ENABLED ); } else { out->number_of_parameter = 0; free ( out->array_of_parameter ); diff --git a/src/default_plugin_event.c b/src/default_plugin_event.c index a336f94..2f7d745 100644 --- a/src/default_plugin_event.c +++ b/src/default_plugin_event.c @@ -37,7 +37,7 @@ int get_lock_state ( parameters* in, parameters* out ) return PLUGIN_CMD_FAIL; } - D ( "shell command : %s\n", in->array_of_parameter[0].v_string.data ); + D ( "lock type: %d\n", in->array_of_parameter[0].v_int32); out->number_of_parameter = 1; out->array_of_parameter = ( parameter* ) malloc ( sizeof ( parameter ) ); diff --git a/src/default_plugin_main.c b/src/default_plugin_main.c index 4bcecb0..a118fe7 100644 --- a/src/default_plugin_main.c +++ b/src/default_plugin_main.c @@ -28,11 +28,11 @@ int default_plugin_init ( eventfunc event_cb, registerfunc register_func ) // default plugin do not need to register command // because unsupported command by plugin should be called with default plugin anyway event_handler = event_cb; - + if (is_supported_by_plugin(PLUGIN_EVENT_PWLOCK) == 0) { create_pwlock_thread(); - } - + } + return PLUGIN_CMD_SUCCESS; } @@ -71,6 +71,8 @@ int default_plugin_async_proc ( int cmd, parameters* in, int out_fd ) if ( cmd == PLUGIN_ASYNC_CMD_AUTH_CONFIRM_PUBLIC ) { ret = confirm_public_key ( in, out_fd ); + } else if ( cmd == PLUGIN_ASYNC_CMD_APPCMD_SERVICE ) { + ret = appcmd_service ( in, out_fd ); } else { ret = PLUGIN_CMD_NOT_SUPPORT; } diff --git a/src/log.h b/src/log.h index f910f90..3d55707 100644 --- a/src/log.h +++ b/src/log.h @@ -41,7 +41,8 @@ typedef enum { TRACE_JDWP, TRACE_SERVICES, TRACE_PROPERTIES, - TRACE_SDKTOOLS + TRACE_SDKTOOLS, + TRACE_APPCMD } SdbTrace; #if SDB_TRACE diff --git a/src/plugin.c b/src/plugin.c index 7ef796f..1cf11f7 100644 --- a/src/plugin.c +++ b/src/plugin.c @@ -35,6 +35,12 @@ PLUGIN_ASYNCHRONOUS_CMD_PROC plugin_async_proc = NULL; hashtable* plugin_cmd_hashtable = NULL; +typedef struct _async_parameter { + int cmd; + parameters* in; + int out_fd; +} async_parameter; + // handler of event to be detected by plugin int plugin_event_handler ( int event_type, parameters* data ) { @@ -183,6 +189,66 @@ static int request_sync_cmd ( int cmd, parameters* in, parameters* out ) return ret; } +static void request_async_cmd ( int cmd, parameters* in, int out_fd ) +{ + int ret, pr; + + ret = hashtable_get ( plugin_cmd_hashtable, cmd, &pr ); + if ( ret == 1 ) { + // supported by plugin + ret = plugin_async_proc ( cmd, in, out_fd ); + if ( ret == PLUGIN_CMD_NOT_SUPPORT ) { + // not supported by plugin + ret = default_plugin_async_proc ( cmd, in, out_fd ); + } + } else { + // not supported by plugin + ret = default_plugin_async_proc ( cmd, in, out_fd ); + } + + release_parameters ( in ); + if ( in != NULL ) { + free( in ); + } + sdb_close(out_fd); +} + +static void *async_proc_bootstrap_func(void *x) +{ + async_parameter *p = x; + request_async_cmd(p->cmd, p->in, p->out_fd); + free(p); + return 0; +} + +static int create_async_proc_thread( int cmd, parameters* in ) +{ + async_parameter* async_param; + sdb_thread_t t; + int s[2]; + + if( sdb_socketpair(s) ) { + D("cannot create async proc socket pair\n"); + return -1; + } + + async_param = ( async_parameter* ) malloc(sizeof(async_parameter)); + if( async_param == NULL ) fatal("cannot allocate async_parameter"); + async_param->cmd = cmd; + async_param->in = in; + async_param->out_fd = s[1]; + + if(sdb_thread_create( &t, async_proc_bootstrap_func, async_param)){ + free(async_param); + sdb_close(s[0]); + sdb_close(s[1]); + D("cannot create async proc thread\n"); + return -1; + } + + D("async proc thread started, %d:%d\n",s[0], s[1]); + return s[0]; +} // return 1 if succeed to get capability from plugin // return 0 otherwise @@ -293,3 +359,28 @@ int request_lock_state_to_plugin ( int lock_type ) return result; } + +// return nonnegative integer that is a socket descriptor for communication +// with async proc thread if success to create async proc thread +// return -1 if failed to create async proc thread +int request_appcmd_to_plugin ( const char* in_buf ) +{ + parameters* in; + int fd; + + in = ( parameters* ) malloc ( sizeof ( parameters ) ); + if ( in_buf != NULL ) { + in->number_of_parameter = 1; + in->array_of_parameter = ( parameter* ) malloc ( sizeof ( parameter ) ); + in->array_of_parameter[0].type = type_string; + in->array_of_parameter[0].v_string.length = strlen ( in_buf ); + in->array_of_parameter[0].v_string.data = strdup ( in_buf ); + } else { + in->number_of_parameter = 0; + in->array_of_parameter = NULL; + } + + fd = create_async_proc_thread( PLUGIN_ASYNC_CMD_APPCMD_SERVICE, in ); + + return fd; +} diff --git a/src/plugin.h b/src/plugin.h index a553e95..fa8288e 100644 --- a/src/plugin.h +++ b/src/plugin.h @@ -49,4 +49,9 @@ int request_conversion_to_plugin ( int cmd, const char* in_buf, char* out_buf, u // return -1 if request failed int request_lock_state_to_plugin ( int lock_type ); +// return nonnegative integer that is a socket descriptor for communication +// with async proc thread if success to create async proc thread +// return -1 if failed to create async proc thread +int request_appcmd_to_plugin ( const char* in_buf ); + #endif //__PLUGIN_H diff --git a/src/sdb.c b/src/sdb.c index 727a7aa..e282ced 100644 --- a/src/sdb.c +++ b/src/sdb.c @@ -203,6 +203,7 @@ void sdb_trace_init(void) { "services", TRACE_SERVICES }, { "properties", TRACE_PROPERTIES }, { "sdktools", TRACE_SDKTOOLS }, + { "appcmd", TRACE_APPCMD }, { NULL, 0 } }; @@ -1809,7 +1810,7 @@ static void init_capabilities(void) { "%s", DISABLED); } - // sdbd log path + // 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); @@ -1817,6 +1818,13 @@ static void init_capabilities(void) { "%s", UNKNOWN); } + // 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); + snprintf(g_capabilities.appcmd_support, sizeof(g_capabilities.appcmd_support), + "%s", UNKNOWN); + } // Capability version snprintf(g_capabilities.sdbd_cap_version, sizeof(g_capabilities.sdbd_cap_version), @@ -1855,13 +1863,28 @@ static void check_emulator_or_device() } } +static void fork_prepare_handler(void) +{ + sdb_mutex_lock(&D_lock); +} + +static void fork_parent_handler(void) +{ + sdb_mutex_unlock(&D_lock); +} + +static void fork_child_handler(void) +{ + sdb_mutex_unlock(&D_lock); +} + int sdb_main(int is_daemon, int server_port) { #if !SDB_HOST check_emulator_or_device(); load_sdbd_plugin(); - + init_capabilities(); sdb_trace_init(); @@ -1875,6 +1898,8 @@ int sdb_main(int is_daemon, int server_port) } umask(000); + + pthread_atfork(fork_prepare_handler, fork_parent_handler, fork_child_handler); #endif atexit(sdb_cleanup); diff --git a/src/sdb.h b/src/sdb.h index 5d7bd94..fec1a5d 100644 --- a/src/sdb.h +++ b/src/sdb.h @@ -256,9 +256,10 @@ typedef struct platform_capabilities char syncwinsz_support[CAPBUF_ITEMSIZE]; // enabled or disabled char usbproto_support[CAPBUF_ITEMSIZE]; // enabled or disabled char sockproto_support[CAPBUF_ITEMSIZE]; // enabled or disabled + char appcmd_support[CAPBUF_ITEMSIZE]; // enabled or disabled - char log_enable[CAPBUF_ITEMSIZE]; // enabled or disabled - char log_path[CAPBUF_LL_ITEMSIZE]; // path of sdbd log + char log_enable[CAPBUF_ITEMSIZE]; // enabled or disabled + char log_path[CAPBUF_LL_ITEMSIZE]; // path of sdbd log char cpu_arch[CAPBUF_ITEMSIZE]; // cpu architecture (ex. x86) char profile_name[CAPBUF_ITEMSIZE]; // profile name (ex. mobile) @@ -523,3 +524,7 @@ int read_line(const int fd, char* ptr, const size_t maxlen); #define USB_FUNCFS_SDB_PATH "/dev/usbgadget/sdb" #define USB_NODE_FILE "/dev/samsung_sdb" +#define SHELL_COMMAND "/bin/sh" +int create_subprocess(const char *cmd, pid_t *pid, char * const argv[], char * const envp[]); +void get_env(char *key, char **env); + diff --git a/src/sdbd_plugin.h b/src/sdbd_plugin.h index 45f2be2..5159928 100644 --- a/src/sdbd_plugin.h +++ b/src/sdbd_plugin.h @@ -36,13 +36,16 @@ // asynchronous command #define PLUGIN_ASYNC_CMD_AUTH_CONFIRM_PUBLIC 2000 +#define PLUGIN_ASYNC_CMD_APPCMD_SERVICE 2001 // event #define PLUGIN_EVENT_PWLOCK 3000 #define PLUGIN_EVENT_FMMLOCK 3001 // message -#define PLUGIN_MESSAGE_CONFIRM_PUBLIC 4000 +#define MESSAGE_PREFIX_CONFIRM_PUBLIC "auth_confirm_return" +#define MESSAGE_PREFIX_APPCMD_EXITCODE "appcmd_exitcode" +#define MESSAGE_PREFIX_APPCMD_RETURN "appcmd_returnstr" // ============================================================================== // capability definition @@ -58,6 +61,7 @@ #define CAPABILITY_PRODUCT_VER 10008 #define CAPABILITY_LOG_ENABLE 10009 #define CAPABILITY_LOG_PATH 10010 +#define CAPABILITY_APPCMD 10011 // =============================================================================== // priority definition diff --git a/src/services.c b/src/services.c index 22b9dda..5d40ce9 100644 --- a/src/services.c +++ b/src/services.c @@ -310,6 +310,7 @@ void inoti_service(int fd, void *arg) if ( ifd < 0 ) { D( "inotify_init failed\n"); + sdb_close(fd); return; } @@ -437,7 +438,7 @@ static void redirect_and_exec(int pts, const char *cmd, char * const argv[], cha execve(cmd, argv, envp); } -static int create_subprocess(const char *cmd, pid_t *pid, char * const argv[], char * const envp[]) +int create_subprocess(const char *cmd, pid_t *pid, char * const argv[], char * const envp[]) { char devname[64]; int ptm; @@ -518,7 +519,6 @@ static int create_subprocess(const char *cmd, pid_t *pid, char * const argv[], c } #endif /* !SDB_HOST */ -#define SHELL_COMMAND "/bin/sh" #define LOGIN_COMMAND "/bin/login" #define SUPER_USER "root" #define LOGIN_CONFIG "/etc/login.defs" @@ -555,7 +555,7 @@ static void subproc_waiter_service(int fd, void *cookie) } } -static void get_env(char *key, char **env) +void get_env(char *key, char **env) { FILE *fp; char buf[1024]; @@ -842,7 +842,6 @@ static int create_syncproc_thread() return ret_fd; } - #endif static void get_platforminfo(int fd, void *cookie) { @@ -995,12 +994,16 @@ static void get_capability(int fd, void *cookie) { "sdbd_cap_version", g_capabilities.sdbd_cap_version); // Sdbd log enable - offset += put_key_value_string(cap_buffer, offset, CAPBUF_SIZE, - "log_enable", g_capabilities.log_enable); + offset += put_key_value_string(cap_buffer, offset, CAPBUF_SIZE, + "log_enable", g_capabilities.log_enable); // Sdbd log path - offset += put_key_value_string(cap_buffer, offset, CAPBUF_SIZE, - "log_path", g_capabilities.log_path); + offset += put_key_value_string(cap_buffer, offset, CAPBUF_SIZE, + "log_path", g_capabilities.log_path); + + // Application command support + offset += put_key_value_string(cap_buffer, offset, CAPBUF_SIZE, + "appcmd_support", g_capabilities.appcmd_support); offset++; // for '\0' character @@ -1165,6 +1168,8 @@ int service_to_fd(const char *name) char* env_variable = NULL; env_variable = strdup(name+14); ret = create_service_thread(get_tzplatform_env, (void *)(env_variable)); + } else if(!strncmp(name, "appcmd:", 7)){ + ret = request_appcmd_to_plugin(name+7); } if (ret >= 0) { -- 2.7.4 From 51e7c759a7a9b311fabb3907eeb564c511e51526 Mon Sep 17 00:00:00 2001 From: Jaewon Lim Date: Wed, 9 Nov 2016 17:52:19 -0800 Subject: [PATCH 02/16] Revert "Revert "modify default plugin's behavior by emulator"" This reverts commit b94610b00ff7573e1f16c8f08cc92d11d88d080a. Change-Id: I8d4d37517c8cd13a6a8e763a68a5f1ccd19038bd --- src/default_plugin_basic.c | 8 ++----- src/default_plugin_event.c | 53 ++++++++++++++++++++++------------------------ src/plugin.c | 16 +++++++++++++- 3 files changed, 42 insertions(+), 35 deletions(-) diff --git a/src/default_plugin_basic.c b/src/default_plugin_basic.c index f8ceba0..2072824 100644 --- a/src/default_plugin_basic.c +++ b/src/default_plugin_basic.c @@ -57,11 +57,7 @@ int get_plugin_capability ( parameters* in, parameters* out ) } else if ( capability == CAPABILITY_FILESYNC ) { make_string_parameter ( & ( out->array_of_parameter[0] ), "%s", PLUGIN_RET_PUSHPULL ); } else if ( capability == CAPABILITY_USB_PROTOCOL ) { - if ( is_emulator() ) { - make_string_parameter ( & ( out->array_of_parameter[0] ), "%s", PLUGIN_RET_DISABLED ); - } else { - make_string_parameter ( & ( out->array_of_parameter[0] ), "%s", PLUGIN_RET_ENABLED ); - } + make_string_parameter ( & ( out->array_of_parameter[0] ), "%s", PLUGIN_RET_ENABLED ); } else if ( capability == CAPABILITY_SOCK_PROTOCOL ) { make_string_parameter ( & ( out->array_of_parameter[0] ), "%s", PLUGIN_RET_ENABLED ); } else if ( capability == CAPABILITY_ROOT_ONOFF ) { @@ -77,7 +73,7 @@ int get_plugin_capability ( parameters* in, parameters* out ) } else if ( capability == CAPABILITY_PRODUCT_VER ) { make_string_parameter ( & ( out->array_of_parameter[0] ), "%s", PLUGIN_RET_UNKNOWN ); } else if ( capability == CAPABILITY_LOG_ENABLE ) { - make_string_parameter ( & ( out->array_of_parameter[0] ), "%s", PLUGIN_RET_DISABLED ); + make_string_parameter ( & ( out->array_of_parameter[0] ), "%s", PLUGIN_RET_ENABLED ); } else if ( capability == CAPABILITY_LOG_PATH ) { make_string_parameter ( & ( out->array_of_parameter[0] ), "%s", LOG_DIRECTORY ); } else if ( capability == CAPABILITY_APPCMD ) { diff --git a/src/default_plugin_event.c b/src/default_plugin_event.c index 2f7d745..6731746 100644 --- a/src/default_plugin_event.c +++ b/src/default_plugin_event.c @@ -17,36 +17,10 @@ #include #include -#define TRACE_TAG TRACE_SDB -#include "log.h" - #include "sysdeps.h" #include "sdbd_plugin.h" #include "default_plugin.h" -int get_lock_state ( parameters* in, parameters* out ) -{ - if ( in == NULL || in->number_of_parameter != 1 || in->array_of_parameter == NULL - || in->array_of_parameter[0].type != type_int32 ) { - D ( "Invalid argument\n" ); - return PLUGIN_CMD_FAIL; - } - - if ( out == NULL ) { - D ( "Invalid argument\n" ); - return PLUGIN_CMD_FAIL; - } - - D ( "lock type: %d\n", in->array_of_parameter[0].v_int32); - - out->number_of_parameter = 1; - out->array_of_parameter = ( parameter* ) malloc ( sizeof ( parameter ) ); - out->array_of_parameter[0].type = type_int32; - out->array_of_parameter[0].v_int32 = ( plugin_pwlocked() == 1 ) ? PLUGIN_RET_ON : PLUGIN_RET_OFF; - - return PLUGIN_CMD_SUCCESS; -} - int plugin_pwlocked ( void ) { int pwlock_status = 0; @@ -82,6 +56,29 @@ int plugin_pwlocked ( void ) return 0; // unlocked! } +int get_lock_state ( parameters* in, parameters* out ) +{ + if ( in == NULL || in->number_of_parameter != 1 || in->array_of_parameter == NULL + || in->array_of_parameter[0].type != type_int32 ) { + PLUGIN_LOG ( "Invalid argument\n" ); + return PLUGIN_CMD_FAIL; + } + + if ( out == NULL ) { + PLUGIN_LOG ( "Invalid argument\n" ); + return PLUGIN_CMD_FAIL; + } + + PLUGIN_LOG ( "lock type: %d\n", in->array_of_parameter[0].v_int32); + + out->number_of_parameter = 1; + out->array_of_parameter = ( parameter* ) malloc ( sizeof ( parameter ) ); + out->array_of_parameter[0].type = type_int32; + out->array_of_parameter[0].v_int32 = ( plugin_pwlocked() == 1 ) ? PLUGIN_RET_ON : PLUGIN_RET_OFF; + + return PLUGIN_CMD_SUCCESS; +} + static void pwlock_cb ( keynode_t *key, void* data ) { PLUGIN_LOG ( "pwlock callback is issued\n" ); @@ -131,8 +128,8 @@ void create_pwlock_thread() { sdb_thread_t t; if ( sdb_thread_create ( &t, pwlock_thread, NULL ) ) { - PLUGIN_LOG ( "cannot create_pwlock_thread.\n" ); + PLUGIN_LOG ( "default plugin : cannot create_pwlock_thread.\n" ); return; } - PLUGIN_LOG ( "created pwlock_thread\n" ); + PLUGIN_LOG ( "default plugin : created pwlock_thread\n" ); } diff --git a/src/plugin.c b/src/plugin.c index 1cf11f7..ff9f19c 100644 --- a/src/plugin.c +++ b/src/plugin.c @@ -73,7 +73,10 @@ int plugin_event_handler ( int event_type, parameters* data ) static int plugin_register_command ( int command, priority cmd_priority ) { if ( plugin_cmd_hashtable ) { - hashtable_put ( plugin_cmd_hashtable, command, cmd_priority ); + int ret = hashtable_put ( plugin_cmd_hashtable, command, cmd_priority ); + D ("register plugin command : cmd(%d), result(%d)\n", command, ret); + } else { + D ("hashtable is not created\n"); } return 0; } @@ -161,6 +164,9 @@ int is_supported_by_plugin ( int cmd ) if ( plugin_cmd_hashtable ) { int value; ret = hashtable_get ( plugin_cmd_hashtable, cmd, &value ); + D ("get from hashtable : cmd(%d), result(%d)\n", cmd, ret); + } else { + D ("hashtable is not created\n"); } return ret; @@ -263,12 +269,16 @@ int request_capability_to_plugin ( int cap, char* out_buf, unsigned int out_len in.array_of_parameter[0].type = type_int32; in.array_of_parameter[0].v_int32 = cap; + D ("requested capability : %d\n", cap); + ret = request_sync_cmd ( PLUGIN_SYNC_CMD_CAPABILITY, &in, &out ); if ( ret == PLUGIN_CMD_SUCCESS ) { strncpy ( out_buf, out.array_of_parameter[0].v_string.data, out_len - 1 ); out_buf[out_len - 1] = '\0'; success = 1; release_parameters ( &out ); + + D ("request capability success : %s\n", out_buf); } release_parameters ( &in ); @@ -294,10 +304,14 @@ int request_validity_to_plugin ( int cmd, const char* in_buf ) in.array_of_parameter = NULL; } + D ("requested validity : %d, %s\n", cmd, in_buf); + ret = request_sync_cmd ( cmd, &in, &out ); if ( ret == PLUGIN_CMD_SUCCESS ) { success = ( out.array_of_parameter[0].v_int32 == PLUGIN_RET_VALID ) ? 1 : 0; release_parameters ( &out ); + + D ("request validity success : %d\n", out.array_of_parameter[0].v_int32); } release_parameters ( &in ); -- 2.7.4 From 1fc8f357b8d134f439cb1e2581da491111ac9e07 Mon Sep 17 00:00:00 2001 From: Jaewon Lim Date: Wed, 9 Nov 2016 17:52:39 -0800 Subject: [PATCH 03/16] Revert "Revert "Merge plugin improvement commit"" This reverts commit 84bfce8dd67d9d74febaf5ef3c0fe0cd6ec16382. Change-Id: I7d5ca566b67230ca712ec276f74ad2115b66e2ca --- src/default_plugin.h | 1 + src/default_plugin_basic.c | 15 +++++++++++++++ src/default_plugin_main.c | 2 ++ src/plugin.c | 16 +++++++++++----- src/sdb.c | 5 ++--- src/sdbd_plugin.h | 1 + src/services.c | 9 ++++++--- src/transport_local.c | 1 + 8 files changed, 39 insertions(+), 11 deletions(-) diff --git a/src/default_plugin.h b/src/default_plugin.h index 800e495..0c8b5b9 100644 --- a/src/default_plugin.h +++ b/src/default_plugin.h @@ -26,6 +26,7 @@ int verify_peer_ip ( parameters* in, parameters* out ); int verify_sdbd_launch ( parameters* in, parameters* out ); int verify_root_cmd ( parameters* in, parameters* out ); int get_lock_state ( parameters* in, parameters* out ); +int get_shell_env ( parameters* in, parameters* out ); int auth_support ( parameters* in, parameters* out ); int auth_get_key_file_paths ( parameters* in, parameters* out ); diff --git a/src/default_plugin_basic.c b/src/default_plugin_basic.c index 2072824..81f313c 100644 --- a/src/default_plugin_basic.c +++ b/src/default_plugin_basic.c @@ -198,3 +198,18 @@ int verify_root_cmd ( parameters* in, parameters* out ) return PLUGIN_CMD_SUCCESS; } + +int get_shell_env ( parameters* in, parameters* out ) +{ + if ( out == NULL ) { + D ( "Invalid argument\n" ); + return PLUGIN_CMD_FAIL; + } + + out->number_of_parameter = 1; + out->array_of_parameter = ( parameter* ) malloc ( sizeof ( parameter ) ); + + make_string_parameter ( & ( out->array_of_parameter[0] ), "%s", "" ); + return PLUGIN_CMD_SUCCESS; +} + diff --git a/src/default_plugin_main.c b/src/default_plugin_main.c index a118fe7..ea71971 100644 --- a/src/default_plugin_main.c +++ b/src/default_plugin_main.c @@ -58,6 +58,8 @@ int default_plugin_sync_proc ( int cmd, parameters* in, parameters* out ) ret = auth_get_key_file_paths ( in, out ); } else if ( cmd == PLUGIN_SYNC_CMD_GET_LOCK_STATE ) { ret = get_lock_state ( in, out ); + } else if ( cmd == PLUGIN_SYNC_CMD_GET_SHELL_ENV ) { + ret = get_shell_env ( in, out ); } else { ret = PLUGIN_CMD_NOT_SUPPORT; } diff --git a/src/plugin.c b/src/plugin.c index ff9f19c..e8c70b9 100644 --- a/src/plugin.c +++ b/src/plugin.c @@ -326,11 +326,16 @@ int request_conversion_to_plugin ( int cmd, const char* in_buf, char* out_buf, u int ret; parameters in, out; - in.number_of_parameter = 1; - in.array_of_parameter = ( parameter* ) malloc ( sizeof ( parameter ) ); - in.array_of_parameter[0].type = type_string; - in.array_of_parameter[0].v_string.length = strlen ( in_buf ); - in.array_of_parameter[0].v_string.data = strdup ( in_buf ); + if ( in_buf != NULL ) { + in.number_of_parameter = 1; + in.array_of_parameter = ( parameter* ) malloc ( sizeof ( parameter ) ); + in.array_of_parameter[0].type = type_string; + in.array_of_parameter[0].v_string.length = strlen ( in_buf ); + in.array_of_parameter[0].v_string.data = strdup ( in_buf ); + } else { + in.number_of_parameter = 0; + in.array_of_parameter = NULL; + } ret = request_sync_cmd ( cmd, &in, &out ); if ( ret == PLUGIN_CMD_SUCCESS ) { @@ -398,3 +403,4 @@ int request_appcmd_to_plugin ( const char* in_buf ) return fd; } + diff --git a/src/sdb.c b/src/sdb.c index e282ced..9a0d5cf 100644 --- a/src/sdb.c +++ b/src/sdb.c @@ -1755,10 +1755,9 @@ 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); + D("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); } diff --git a/src/sdbd_plugin.h b/src/sdbd_plugin.h index 5159928..2bfb450 100644 --- a/src/sdbd_plugin.h +++ b/src/sdbd_plugin.h @@ -33,6 +33,7 @@ #define PLUGIN_SYNC_CMD_AUTH_SUPPORT 1006 #define PLUGIN_SYNC_CMD_AUTH_GET_KEY_FILEPATHS 1007 #define PLUGIN_SYNC_CMD_GET_LOCK_STATE 1008 +#define PLUGIN_SYNC_CMD_GET_SHELL_ENV 1009 // asynchronous command #define PLUGIN_ASYNC_CMD_AUTH_CONFIRM_PUBLIC 2000 diff --git a/src/services.c b/src/services.c index 5d40ce9..1c48905 100644 --- a/src/services.c +++ b/src/services.c @@ -54,6 +54,8 @@ #include "sdbd_plugin.h" #include "plugin.h" +#define ENV_BUF_MAX 4096 + typedef struct stinfo stinfo; struct stinfo { @@ -647,13 +649,14 @@ static int create_subproc_thread(const char *name, int lines, int columns) /* get environment variables from plugin */ char *envp_plugin = NULL; - envp_plugin = malloc(SDBD_PLUGIN_OUTBUF_MAX); + envp_plugin = malloc(ENV_BUF_MAX); if (envp_plugin == NULL) { D("Cannot allocate the shell commnad buffer."); return -1; } - memset(envp_plugin, 0, SDBD_PLUGIN_OUTBUF_MAX); - if (!request_plugin_cmd(SDBD_CMD_SHELL_ENVVAR, "", envp_plugin, SDBD_PLUGIN_OUTBUF_MAX)) { + memset(envp_plugin, 0, ENV_BUF_MAX); + if (!request_conversion_to_plugin(PLUGIN_SYNC_CMD_GET_SHELL_ENV, NULL, + envp_plugin, ENV_BUF_MAX)) { D("Failed to convert the shell command. (%s)\n", name); free(envp_plugin); return -1; diff --git a/src/transport_local.c b/src/transport_local.c index 849fe05..a6adb0b 100644 --- a/src/transport_local.c +++ b/src/transport_local.c @@ -38,6 +38,7 @@ #if !SDB_HOST #include "commandline_sdbd.h" #endif +#include "utils.h" #include "sdbd_plugin.h" #include "plugin.h" -- 2.7.4 From 420ef7eedbc247b0d242d5bffacb7c0c7d751699 Mon Sep 17 00:00:00 2001 From: Jaewon Lim Date: Wed, 9 Nov 2016 17:52:50 -0800 Subject: [PATCH 04/16] Revert "Revert "add data encryption feature"" This reverts commit e5cb6422d20125dc1896e7d8838c6e7e8b77ab86. Change-Id: I9d806afef3826e7c7f40b613bd6b4dd06064b2e8 --- CMakeLists.txt | 3 + packaging/sdbd.spec | 1 + src/plugin.c | 22 ++-- src/sdb.c | 168 +++++++++++++++++++++++++++++- src/sdb.h | 18 ++++ src/sdbd_plugin.h | 1 + src/services.c | 4 + src/sockets.c | 21 +++- src/transport.c | 26 +++++ src/transport_security.c | 261 +++++++++++++++++++++++++++++++++++++++++++++++ src/transport_security.h | 18 ++++ 11 files changed, 529 insertions(+), 14 deletions(-) create mode 100644 src/transport_security.c create mode 100644 src/transport_security.h diff --git a/CMakeLists.txt b/CMakeLists.txt index 6c88b77..47edfd9 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -58,6 +58,7 @@ SET(SDBD_SRCS src/default_plugin_appcmd.c src/hashtable.c src/plugin.c + src/transport_security.c ) include(FindPkgConfig) @@ -69,6 +70,7 @@ pkg_check_modules(pkgs REQUIRED glib-2.0 dbus-1 dbus-glib-1 + dlog ) FOREACH(flag ${pkgs_CFLAGS}) @@ -86,6 +88,7 @@ ADD_DEFINITIONS("-D_GNU_SOURCE") ADD_DEFINITIONS("-DHAVE_FORKEXEC") ADD_DEFINITIONS("-D_DROP_PRIVILEGE") ADD_DEFINITIONS("-D_FILE_OFFSET_BITS=64") +ADD_DEFINITIONS("-DSUPPORT_ENCRYPT") IF (_ARM_TARGET) ADD_DEFINITIONS("-DANDROID_GADGET=1") diff --git a/packaging/sdbd.spec b/packaging/sdbd.spec index 1cf6758..bc9408f 100644 --- a/packaging/sdbd.spec +++ b/packaging/sdbd.spec @@ -25,6 +25,7 @@ BuildRequires: pkgconfig(vconf) BuildRequires: pkgconfig(glib-2.0) BuildRequires: pkgconfig(dbus-1) BuildRequires: pkgconfig(dbus-glib-1) +BuildRequires: pkgconfig(dlog) Requires: dbus %description diff --git a/src/plugin.c b/src/plugin.c index e8c70b9..bee7aa4 100644 --- a/src/plugin.c +++ b/src/plugin.c @@ -27,7 +27,7 @@ #include "plugin.h" #include "sdbd_plugin.h" -static void* plugin_handle = NULL; +void* g_plugin_handle = NULL; PLUGIN_INIT plugin_init_proc = NULL; PLUGIN_SYNCHRONOUS_CMD_PROC plugin_sync_proc = NULL; @@ -89,28 +89,28 @@ static int load_plugin_not_default() plugin_sync_proc = NULL; plugin_async_proc = NULL; - plugin_handle = dlopen ( PLUGIN_PATH, RTLD_NOW ); - if ( plugin_handle == NULL ) { + g_plugin_handle = dlopen ( PLUGIN_PATH, RTLD_NOW ); + if ( g_plugin_handle == NULL ) { D ( "failed to dlopen(%s). error: %s\n", PLUGIN_PATH, dlerror() ); return 0; } - plugin_init_proc = dlsym ( plugin_handle, PLUGIN_PROC_NAME_INIT ); + plugin_init_proc = dlsym ( g_plugin_handle, PLUGIN_PROC_NAME_INIT ); if ( plugin_init_proc == NULL ) { D ( "failed to get the sdbd plugin init function. error: %s\n", dlerror() ); - dlclose ( plugin_handle ); - plugin_handle = NULL; + dlclose ( g_plugin_handle ); + g_plugin_handle = NULL; return 0; } // if there is no implementation of plugin_sync_proc and plugin_async_proc, // then use default_plugin_sync_proc and default_plugin_async_proc - plugin_sync_proc = dlsym ( plugin_handle, PLUGIN_PROC_NAME_SYNC_CMD ); + plugin_sync_proc = dlsym ( g_plugin_handle, PLUGIN_PROC_NAME_SYNC_CMD ); if ( plugin_sync_proc == NULL ) { plugin_sync_proc = default_plugin_sync_proc; } - plugin_async_proc = dlsym ( plugin_handle, PLUGIN_PROC_NAME_ASYNC_CMD ); + plugin_async_proc = dlsym ( g_plugin_handle, PLUGIN_PROC_NAME_ASYNC_CMD ); if ( plugin_async_proc == NULL ) { plugin_async_proc = default_plugin_async_proc; } @@ -149,9 +149,9 @@ void unload_sdbd_plugin() plugin_cmd_hashtable = NULL; } - if ( plugin_handle ) { - dlclose ( plugin_handle ); - plugin_handle = NULL; + if ( g_plugin_handle ) { + dlclose ( g_plugin_handle ); + g_plugin_handle = NULL; } } diff --git a/src/sdb.c b/src/sdb.c index 9a0d5cf..50cf9ed 100644 --- a/src/sdb.c +++ b/src/sdb.c @@ -44,6 +44,10 @@ #include "plugin.h" #include "sdbd_plugin.h" +#ifdef SUPPORT_ENCRYPT +#include "transport_security.h" +#endif + #if !SDB_HOST #include #define SDB_PIDPATH "/tmp/.sdbd.pid" @@ -368,6 +372,147 @@ 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] apacket* enc_p : sdb server로 전송할 메시지 + [in/out] atransport *t : 현재 연결에 대한 atransport +ret : 0 : 정상적으로 메시지 전송 + -1: 메시지 전송 실패 +*/ +int handle_encr_packet(apacket* p, apacket* enc_p, atransport *t){ + static int sessionID = 0; + int retVal = 0; + 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 메시지 파싱 + D("security_parse_server_hello success\n"); + if(security_gen_client_hello(t->sessionID, enc_p) == 1){ // hello 메시지 생성 + D("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 메시지 생성 실패 + D("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 메시지 파싱 실패 + D("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 실패 + D("security_init error\n"); + send_encr_fail(p, t, ENCR_ON_FAIL); + t->encryption = ENCR_OFF; + if (retVal == -1) + { + 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 메시지 파싱 + if(security_gen_client_ack(t->sessionID, enc_p) == 1){ // ack 메시지 생성 + D("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 메시지 생성에 실패한 경우 + D("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 메시지 파싱에 실패한 경우 + D("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에 실패한 경우 + D("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); // 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); // encryption:off 메시지 전송 + } + send_packet(enc_p, t); + } + else if (p->msg.arg0 == ENCR_ON_FAIL) // 암호화 모드를 on 하는 도중 실패한 경우 받는 메시지 + { + t->encryption = ENCR_OFF; // 암호화 모드를 다시 off + D("encryption on failed\n"); + } + else if (p->msg.arg0 == ENCR_OFF_FAIL) // 암호화 모드를 off하는 도중 실패한 경우 받는 메시지 + { + //t->encryption = ENCR_ON; + D("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"); @@ -394,8 +539,11 @@ static void send_connect(atransport *t) 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; @@ -739,6 +887,15 @@ void handle_packet(apacket *p, atransport *t) } } break; +#ifdef SUPPORT_ENCRYPT + case A_ENCR: // 암호화 메시지인 경우 + if(t->connection_state != CS_OFFLINE) { + apacket* enc_p = get_apacket(); + handle_encr_packet(p, enc_p, t); + //put_apacket(enc_p); + } + break; +#endif default: printf("handle_packet: what is %08x?!\n", p->msg.command); @@ -1692,6 +1849,15 @@ static void init_capabilities(void) { } + // Encryption support + if(!request_capability_to_plugin(CAPABILITY_ENCRYPTION, g_capabilities.encryption_support, + sizeof(g_capabilities.encryption_support))) { + D("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), diff --git a/src/sdb.h b/src/sdb.h index fec1a5d..348a7eb 100644 --- a/src/sdb.h +++ b/src/sdb.h @@ -37,6 +37,18 @@ #define A_CLSE 0x45534c43 #define A_WRTE 0x45545257 #define A_STAT 0x54415453 +#define A_ENCR 0x40682018 // encryption 메시지 + +#ifdef SUPPORT_ENCRYPT + #define ENCR_SET_ON_REQ 0 // encryption hello 메시지 + #define ENCR_SET_ON_OK 1 // encryption ack 메시지 + #define ENCR_SET_OFF 2 // encryption mode off 메시지 + #define ENCR_GET 3 // encryption status get 메시지 + #define ENCR_ON_FAIL 4 // encryption on 실패 메시지 + #define ENCR_OFF_FAIL 5 // encryption off 실패 메시지 + #define ENCR_ON 1 // encryption on 상태 + #define ENCR_OFF 0 // encryption off 상태 +#endif #define A_VERSION 0x02000000 // SDB protocol version @@ -200,6 +212,11 @@ struct atransport /* a list of adisconnect callbacks called when the transport is kicked */ int kicked; adisconnect disconnects; + +#ifdef SUPPORT_ENCRYPT + unsigned encryption; // 해당 연결이 암호화 모드인지 확인하는 flag , 0 = no-encryption / 1 = encryption + int sessionID; // 암호화 세션 ID, 암호화 map에 대한 key +#endif }; @@ -257,6 +274,7 @@ typedef struct platform_capabilities char usbproto_support[CAPBUF_ITEMSIZE]; // enabled or disabled char sockproto_support[CAPBUF_ITEMSIZE]; // enabled or disabled char appcmd_support[CAPBUF_ITEMSIZE]; // enabled or disabled + char encryption_support[CAPBUF_ITEMSIZE]; // enabled or disabled char log_enable[CAPBUF_ITEMSIZE]; // enabled or disabled char log_path[CAPBUF_LL_ITEMSIZE]; // path of sdbd log diff --git a/src/sdbd_plugin.h b/src/sdbd_plugin.h index 2bfb450..bcaaa8d 100644 --- a/src/sdbd_plugin.h +++ b/src/sdbd_plugin.h @@ -63,6 +63,7 @@ #define CAPABILITY_LOG_ENABLE 10009 #define CAPABILITY_LOG_PATH 10010 #define CAPABILITY_APPCMD 10011 +#define CAPABILITY_ENCRYPTION 10012 // =============================================================================== // priority definition diff --git a/src/services.c b/src/services.c index 1c48905..d2d1500 100644 --- a/src/services.c +++ b/src/services.c @@ -948,6 +948,10 @@ static void get_capability(int fd, void *cookie) { offset += put_key_value_string(cap_buffer, offset, CAPBUF_SIZE, "rootonoff_support", g_capabilities.rootonoff_support); + // Encryption support + offset += put_key_value_string(cap_buffer, offset, CAPBUF_SIZE, + "encryption_support", g_capabilities.encryption_support); + // Zone support offset += put_key_value_string(cap_buffer, offset, CAPBUF_SIZE, "zone_support", g_capabilities.zone_support); diff --git a/src/sockets.c b/src/sockets.c index 574820a..801ff42 100644 --- a/src/sockets.c +++ b/src/sockets.c @@ -317,7 +317,17 @@ static void local_socket_event_func(int fd, unsigned ev, void *_s) if(ev & FDE_READ){ apacket *p = get_apacket(); unsigned char *x = p->data; - size_t avail = MAX_PAYLOAD; +#ifdef SUPPORT_ENCRYPT + // sdb.c:536에서 sdb server의 패킷은 MAX_PAYLOAD-100으로 정하여서, + // sdb server에서 패킷 데이터의 크기를 MAX_PAYLOAD-100보다 작은 지를 체크함. + // sdbd에서 패킷 데이터를 MAX_PAYLOAD - 200로 잡아서 암호화 하게되면 + // 최대 MAX_PAYLOAD - 100 크기의 패킷을 생성하게 됨. + const size_t max_payload = MAX_PAYLOAD - 200; + size_t avail = max_payload; +#else + size_t avail = MAX_PAYLOAD; +#endif + int r = 0; int is_eof = 0; @@ -340,11 +350,18 @@ static void local_socket_event_func(int fd, unsigned ev, void *_s) } D("LS(%d): fd=%d post avail loop. r=%d is_eof=%d forced_eof=%d\n", s->id, s->fd, r, is_eof, s->fde.force_eof); +#ifdef SUPPORT_ENCRYPT + //변경된 최대 패킷 크기로 코드 수정 + if((avail == max_payload) || (s->peer == 0)) { + put_apacket(p); + } else { + p->len = max_payload - avail; +#else if((avail == MAX_PAYLOAD) || (s->peer == 0)) { put_apacket(p); } else { p->len = MAX_PAYLOAD - avail; - +#endif r = s->peer->enqueue(s->peer, p); D("LS(%d): fd=%d post peer->enqueue(). r=%d\n", s->id, s->fd, r); diff --git a/src/transport.c b/src/transport.c index 7e2af39..bc471d6 100644 --- a/src/transport.c +++ b/src/transport.c @@ -27,6 +27,10 @@ #include "sdb.h" +#ifdef SUPPORT_ENCRYPT +#include "transport_security.h" +#endif + static void transport_unref(atransport *t); static atransport transport_list = { @@ -286,6 +290,15 @@ static void *output_thread(void *_t) if(t->read_from_remote(p, t) == 0){ D("%s: received remote packet, sending to transport\n", t->serial); + +#ifdef SUPPORT_ENCRYPT + if (t->encryption == ENCR_ON && p->msg.command != A_ENCR) // 현재 연결이 암호화 모드이고, 암호화 관련 메시지가 아닌 경우, 메시지 복호화 + { + security_decrypt(t->sessionID, p); + } + +#endif + if(write_packet(t->fd, t->serial, &p)){ put_apacket(p); D("%s: failed to write apacket to transport\n", t->serial); @@ -355,6 +368,19 @@ static void *input_thread(void *_t) } else { if(active) { D("%s: transport got packet, sending to remote\n", t->serial); + +#ifdef SUPPORT_ENCRYPT + if (t->encryption == ENCR_ON && p->msg.command != A_ENCR) // 현재 연결이 암호화 모드이고, 암호화 관련 메시지가 아닌 경우, 메시지를 암호화 + { + security_encrypt(t->sessionID, p); + } + else if(t->encryption == ENCR_OFF) + { + + } + +#endif + t->write_to_remote(p, t); } else { D("%s: transport ignoring packet while offline\n", t->serial); diff --git a/src/transport_security.c b/src/transport_security.c new file mode 100644 index 0000000..37d3b58 --- /dev/null +++ b/src/transport_security.c @@ -0,0 +1,261 @@ +#include +#include "transport_security.h" + +#define LOG_TAG "SDBD" +#include + +#define SAKEP_AKE_MSG_RECORD_FIXED_LEN 36 +#define SAKEP_AES_ECB_ADDED_PADDING_SIZE 16 + +extern void* g_plugin_handle; + +typedef int (*SDBD_PLUGIN_CMD_SECURITY_INIT_PROC_PTR)(const int nID, const char* pUserID); +typedef int (*SDBD_PLUGIN_CMD_SECURITY_DEINIT_PROC_PTR)(const int nID); +typedef int (*SDBD_PLUGIN_CMD_SECURITY_PARSE_SERVER_HELLO_PROC_PTR)(const int nID, unsigned char* pSrc, unsigned int* nSrcLen); +typedef int (*SDBD_PLUGIN_CMD_SECURITY_GEN_CLIENT_HELLO_PROC_PTR)(const int nID, unsigned char* pSrc, unsigned int* nSrcLen); +typedef int (*SDBD_PLUGIN_CMD_SECURITY_PARSE_SERVER_ACK_PROC_PTR)(const int nID, unsigned char* pSrc, unsigned int* nSrcLen); +typedef int (*SDBD_PLUGIN_CMD_SECURITY_GEN_CLIENT_ACK_PROC_PTR)(const int nID, unsigned char* pSrc, unsigned int* nSrcLen); +typedef int (*SDBD_PLUGIN_CMD_SECURITY_ENCRYPT_PROC_PTR)(const int nID, const unsigned char* pSrc, const unsigned int nSrcLen, + unsigned char* pDst, unsigned int* pnDstLen); +typedef int (*SDBD_PLUGIN_CMD_SECURITY_DECRYPT_PROC_PTR)(const int nID, const unsigned char* pSrc, const unsigned int nSrcLen, + unsigned char* pDst, unsigned int* pnDstLen); + +SDBD_PLUGIN_CMD_SECURITY_INIT_PROC_PTR sdbd_plugin_cmd_security_init = NULL; +SDBD_PLUGIN_CMD_SECURITY_DEINIT_PROC_PTR sdbd_plugin_cmd_security_deinit = NULL; +SDBD_PLUGIN_CMD_SECURITY_PARSE_SERVER_HELLO_PROC_PTR sdbd_plugin_cmd_security_parse_server_hello = NULL; +SDBD_PLUGIN_CMD_SECURITY_GEN_CLIENT_HELLO_PROC_PTR sdbd_plugin_cmd_security_gen_client_hello = NULL; +SDBD_PLUGIN_CMD_SECURITY_PARSE_SERVER_ACK_PROC_PTR sdbd_plugin_cmd_security_parse_server_ack = NULL; +SDBD_PLUGIN_CMD_SECURITY_GEN_CLIENT_ACK_PROC_PTR sdbd_plugin_cmd_security_gen_client_ack = NULL; +SDBD_PLUGIN_CMD_SECURITY_ENCRYPT_PROC_PTR sdbd_plugin_cmd_security_encrypt = NULL; +SDBD_PLUGIN_CMD_SECURITY_DECRYPT_PROC_PTR sdbd_plugin_cmd_security_decrypt = NULL; + +#define SDBD_PLUGIN_CMD_SECURITY_INIT_INTF "sdbd_plugin_cmd_security_init" +#define SDBD_PLUGIN_CMD_SECURITY_DEINIT_INTF "sdbd_plugin_cmd_security_deinit" +#define SDBD_PLUGIN_CMD_SECURITY_PARSE_SERVER_HELLO_INTF "sdbd_plugin_cmd_security_parse_server_hello" +#define SDBD_PLUGIN_CMD_SECURITY_GEN_CLIENT_HELLO_INTF "sdbd_plugin_cmd_security_gen_client_hello" +#define SDBD_PLUGIN_CMD_SECURITY_PARSE_SERVER_ACK_INTF "sdbd_plugin_cmd_security_parse_server_ack" +#define SDBD_PLUGIN_CMD_SECURITY_GEN_CLIENT_ACK_INTF "sdbd_plugin_cmd_security_gen_client_ack" +#define SDBD_PLUGIN_CMD_SECURITY_ENCRYPT_INTF "sdbd_plugin_cmd_security_encrypt" +#define SDBD_PLUGIN_CMD_SECURITY_DECRYPT_INTF "sdbd_plugin_cmd_security_decrypt" + +int load_sdbd_plugin_security() { + + if( sdbd_plugin_cmd_security_init == NULL ) { + LOGI("sdbd_plugin_cmd_security_init == NULL, dlsym sdbd_plugin_cmd_security_init"); + sdbd_plugin_cmd_security_init = dlsym(g_plugin_handle, SDBD_PLUGIN_CMD_SECURITY_INIT_INTF); + if( sdbd_plugin_cmd_security_init == NULL ) { + LOGI("sdbd_plugin_cmd_security_init == NULL, dlerror = [%s]", dlerror()); + } + } + LOGI("sdbd_plugin_cmd_security_init = [0x%p]", sdbd_plugin_cmd_security_init); + + + if( sdbd_plugin_cmd_security_deinit == NULL ) { + LOGI("sdbd_plugin_cmd_security_deinit == NULL, dlsym sdbd_plugin_cmd_security_deinit\n"); + sdbd_plugin_cmd_security_deinit = dlsym(g_plugin_handle, SDBD_PLUGIN_CMD_SECURITY_DEINIT_INTF); + if( sdbd_plugin_cmd_security_deinit == NULL ) { + LOGI("sdbd_plugin_cmd_security_deinit == NULL, dlerror = [%s]\n", dlerror()); + } + } + LOGI("sdbd_plugin_cmd_security_deinit = [0x%p]\n", sdbd_plugin_cmd_security_deinit); +// + if( sdbd_plugin_cmd_security_parse_server_hello == NULL ) { + LOGI("sdbd_plugin_cmd_security_parse_server_hello == NULL, dlsym sdbd_plugin_cmd_security_parse_server_hello\n"); + sdbd_plugin_cmd_security_parse_server_hello = dlsym(g_plugin_handle, SDBD_PLUGIN_CMD_SECURITY_PARSE_SERVER_HELLO_INTF); + if( sdbd_plugin_cmd_security_parse_server_hello == NULL ) { + LOGI("sdbd_plugin_cmd_security_parse_server_hello == NULL, dlerror = [%s]\n", dlerror()); + } + } + LOGI("sdbd_plugin_cmd_security_parse_server_hello = [0x%p]\n", sdbd_plugin_cmd_security_parse_server_hello); +// + if( sdbd_plugin_cmd_security_gen_client_hello == NULL ) { + LOGI("sdbd_plugin_cmd_security_gen_client_hello == NULL, dlsym sdbd_plugin_cmd_security_gen_client_hello\n"); + sdbd_plugin_cmd_security_gen_client_hello = dlsym(g_plugin_handle, SDBD_PLUGIN_CMD_SECURITY_GEN_CLIENT_HELLO_INTF); + if( sdbd_plugin_cmd_security_gen_client_hello == NULL ) { + LOGI("sdbd_plugin_cmd_security_gen_client_hello == NULL, dlerror = [%s]\n", dlerror()); + } + } + LOGI("sdbd_plugin_cmd_security_gen_client_hello = [0x%p]\n", sdbd_plugin_cmd_security_gen_client_hello); +// + if( sdbd_plugin_cmd_security_parse_server_ack == NULL ) { + LOGI("sdbd_plugin_cmd_security_parse_server_ack == NULL, dlsym sdbd_plugin_cmd_security_parse_server_ack\n"); + sdbd_plugin_cmd_security_parse_server_ack = dlsym(g_plugin_handle, SDBD_PLUGIN_CMD_SECURITY_PARSE_SERVER_ACK_INTF); + if( sdbd_plugin_cmd_security_parse_server_ack == NULL ) { + LOGI("sdbd_plugin_cmd_security_parse_server_ack == NULL, dlerror = [%s]\n", dlerror()); + } + } + LOGI("sdbd_plugin_cmd_security_parse_server_ack = [0x%p]\n", sdbd_plugin_cmd_security_parse_server_ack); +// + if( sdbd_plugin_cmd_security_gen_client_ack == NULL ) { + LOGI("sdbd_plugin_cmd_security_gen_client_ack == NULL, dlsym sdbd_plugin_cmd_security_gen_client_ack\n"); + sdbd_plugin_cmd_security_gen_client_ack = dlsym(g_plugin_handle, SDBD_PLUGIN_CMD_SECURITY_GEN_CLIENT_ACK_INTF); + if( sdbd_plugin_cmd_security_gen_client_ack == NULL ) { + LOGI("sdbd_plugin_cmd_security_gen_client_ack == NULL, dlerror = [%s]\n", dlerror()); + } + } + LOGI("sdbd_plugin_cmd_security_gen_client_ack = [0x%p]\n", sdbd_plugin_cmd_security_gen_client_ack); + + if( sdbd_plugin_cmd_security_encrypt == NULL ) { + LOGI("sdbd_plugin_cmd_security_encrypt == NULL, dlsym sdbd_plugin_cmd_security_encrypt"); + sdbd_plugin_cmd_security_encrypt = dlsym(g_plugin_handle, SDBD_PLUGIN_CMD_SECURITY_ENCRYPT_INTF); + if( sdbd_plugin_cmd_security_encrypt == NULL ) { + LOGI("sdbd_plugin_cmd_security_encrypt == NULL, dlerror = [%s]", dlerror()); + } + } + LOGI("sdbd_plugin_cmd_security_encrypt = [0x%p]", sdbd_plugin_cmd_security_encrypt); + + if( sdbd_plugin_cmd_security_decrypt == NULL ) { + LOGI("sdbd_plugin_cmd_security_decrypt == NULL, dlsym sdbd_plugin_cmd_security_decrypt"); + sdbd_plugin_cmd_security_decrypt = dlsym(g_plugin_handle, SDBD_PLUGIN_CMD_SECURITY_DECRYPT_INTF); + if( sdbd_plugin_cmd_security_decrypt == NULL ) { + LOGI("sdbd_plugin_cmd_security_decrypt == NULL, dlerror = [%s]", dlerror()); + } + } + LOGI("sdbd_plugin_cmd_security_decrypt = [0x%p]", sdbd_plugin_cmd_security_decrypt); + + return 1; +} + + +int security_init(const int nSessionID, const char* pUserID) { + + if( sdbd_plugin_cmd_security_init == NULL ) { + LOGI("sdbd_plugin_cmd_security_init == NULL, return 0"); + return 0; + } + + return sdbd_plugin_cmd_security_init(nSessionID, pUserID); +} + +int security_deinit(const int nSessionID) { + if( sdbd_plugin_cmd_security_deinit == NULL ) { + LOGI("sdbd_plugin_cmd_security_deinit == NULL, return 0\n"); + return 0; + } + + return sdbd_plugin_cmd_security_deinit(nSessionID); +} + + +int security_parse_server_hello(const int nSessionID, apacket* pApacket){ + if( sdbd_plugin_cmd_security_parse_server_hello == NULL ) { + LOGI("sdbd_plugin_cmd_security_parse_server_hello == NULL, return 0\n"); + return 0; + } + if( pApacket == NULL ) { + LOGI("pApacket == NULL, return 0\n"); + return 0; + } + + if( 0 == sdbd_plugin_cmd_security_parse_server_hello(nSessionID, pApacket->data, &pApacket->msg.data_length) ) { + LOGI("sdbd_plugin_cmd_security_parse_server_hello return 0\n"); + return 0; + } + return 1; +} + +int security_gen_client_hello(const int nSessionID, apacket* pApacket){ + if( sdbd_plugin_cmd_security_gen_client_hello == NULL ) { + LOGI("sdbd_plugin_cmd_security_gen_client_hello == NULL, return 0\n"); + return 0; + } + if( pApacket == NULL ) { + LOGI("pApacket == NULL, return 0\n"); + return 0; + } + + if( 0 == sdbd_plugin_cmd_security_gen_client_hello(nSessionID, pApacket->data, &pApacket->msg.data_length) ) { + LOGI("sdbd_plugin_cmd_security_gen_client_hello return 0\n"); + return 0; + } + return 1; +} + +int security_parse_server_ack(const int nSessionID, apacket* pApacket){ + if( sdbd_plugin_cmd_security_parse_server_ack == NULL ) { + LOGI("sdbd_plugin_cmd_security_parse_server_ack == NULL, return 0\n"); + return 0; + } + if( pApacket == NULL ) { + LOGI("pApacket == NULL, return 0\n"); + return 0; + } + + if( 0 == sdbd_plugin_cmd_security_parse_server_ack(nSessionID, pApacket->data, &pApacket->msg.data_length) ) { + LOGI("sdbd_plugin_cmd_security_parse_server_ack return 0\n"); + return 0; + } + return 1; +} + +int security_gen_client_ack(const int nSessionID, apacket* pApacket){ + if( sdbd_plugin_cmd_security_gen_client_ack == NULL ) { + LOGI("sdbd_plugin_cmd_security_gen_client_ack == NULL, return 0\n"); + return 0; + } + if( pApacket == NULL ) { + LOGI("pApacket == NULL, return 0\n"); + return 0; + } + + if( 0 == sdbd_plugin_cmd_security_gen_client_ack(nSessionID, pApacket->data, &pApacket->msg.data_length) ) { + LOGI("sdbd_plugin_cmd_security_gen_client_ack return 0\n"); + return 0; + } + return 1; +} + + +int security_encrypt(const int nSessionID, apacket* pApacket) { + + if( pApacket == NULL ) { + LOGI("pApacket == NULL, return 0"); + return 0; + } + + unsigned char *szTemp; + szTemp = (unsigned char *)malloc(pApacket->msg.data_length + SAKEP_AKE_MSG_RECORD_FIXED_LEN + SAKEP_AES_ECB_ADDED_PADDING_SIZE); + memset(szTemp, 0x00, pApacket->msg.data_length + SAKEP_AKE_MSG_RECORD_FIXED_LEN + SAKEP_AES_ECB_ADDED_PADDING_SIZE); + + unsigned int nDstLen = 0; + if( 0 == sdbd_plugin_cmd_security_encrypt(nSessionID, pApacket->data, pApacket->msg.data_length, szTemp, &nDstLen) ) { + LOGI("sdbd_plugin_cmd_security_encrypt return 0"); + return 0; + } + + int i=0; + for(i=0 ; idata[i] = szTemp[i]; + } + + pApacket->msg.data_length = nDstLen; + free(szTemp); + return 1; + +} + +int security_decrypt(const int nSessionID, apacket* pApacket) { + + if( pApacket == NULL ) { + LOGI("pApacket == NULL, return 0"); + return 0; + } + + unsigned char *szTemp; + szTemp = (unsigned char *)malloc(pApacket->msg.data_length); + memset(szTemp, 0x00, pApacket->msg.data_length); + unsigned int nDstLen = 0; + if( 0 == sdbd_plugin_cmd_security_decrypt(nSessionID, pApacket->data, pApacket->msg.data_length, szTemp, &nDstLen) ) { + LOGI("sdbd_plugin_cmd_security_decrypt return 0"); + return 0; + } + + int i = 0; + for(i=0 ; idata[i] = szTemp[i]; + } + + pApacket->msg.data_length = nDstLen; + free(szTemp); + return 1; +} diff --git a/src/transport_security.h b/src/transport_security.h new file mode 100644 index 0000000..12fd689 --- /dev/null +++ b/src/transport_security.h @@ -0,0 +1,18 @@ +#ifndef __TRANSPORT_SECURITY_H__ +#define __TRANSPORT_SECURITY_H__ + +#include +#include "sdb.h" + +int load_sdbd_plugin_security(); + +int security_init(const int nID, const char* pUserID); +int security_deinit(const int nSessionID); +int security_parse_server_hello(const int nSessionID, apacket* pApacket); +int security_gen_client_hello(const int nSessionID, apacket* pApacket); +int security_parse_server_ack(const int nSessionID, apacket* pApacket); +int security_gen_client_ack(const int nSessionID, apacket* pApacket); +int security_encrypt(const int nID, apacket* pApacket); +int security_decrypt(const int nID, apacket* pApacket); + +#endif -- 2.7.4 From 0709619232f7ea3538e9508c392a8d395a80e743 Mon Sep 17 00:00:00 2001 From: greatim Date: Thu, 10 Nov 2016 19:56:19 +0900 Subject: [PATCH 05/16] fix a bug that sdb shell command over 128 byte is cut modify string buffer size of parameter for plugin invocation Change-Id: Ia3925eca3d444bf4b1c66c7c6c9827225ea90294 Signed-off-by: greatim --- src/default_plugin_main.c | 2 -- src/parameter.h | 2 +- 2 files changed, 1 insertion(+), 3 deletions(-) diff --git a/src/default_plugin_main.c b/src/default_plugin_main.c index ea71971..37e5f54 100644 --- a/src/default_plugin_main.c +++ b/src/default_plugin_main.c @@ -19,8 +19,6 @@ #include "default_plugin.h" #include "plugin.h" -#define MAX_OUT_BUF_SIZE 128 - eventfunc event_handler = NULL; int default_plugin_init ( eventfunc event_cb, registerfunc register_func ) diff --git a/src/parameter.h b/src/parameter.h index c526bb7..ea15996 100644 --- a/src/parameter.h +++ b/src/parameter.h @@ -65,7 +65,7 @@ typedef struct _parameters { parameter* array_of_parameter; } parameters; -#define MAX_OUT_BUF_SIZE 128 +#define MAX_OUT_BUF_SIZE 4096 static __inline__ void make_string_parameter ( parameter* pstring, const char* format, ... ) { -- 2.7.4 From 0634e2589b1ab56dd275635128b6f38d44e853e4 Mon Sep 17 00:00:00 2001 From: greatim Date: Fri, 11 Nov 2016 15:10:54 +0900 Subject: [PATCH 06/16] Fixed SVACE issue Fixed SVACE issue Change-Id: Ia5f7ee4c56ae82702809ff0d69eb229594647a1f Signed-off-by: greatim --- src/default_plugin_appcmd.c | 7 ++++++- src/file_sync_service.c | 3 ++- src/parameter.h | 2 +- 3 files changed, 9 insertions(+), 3 deletions(-) diff --git a/src/default_plugin_appcmd.c b/src/default_plugin_appcmd.c index 947a8e5..3fd2f64 100644 --- a/src/default_plugin_appcmd.c +++ b/src/default_plugin_appcmd.c @@ -656,7 +656,12 @@ static void run_appcmd_appinstallpath(appcmd_info* p_info) { static void run_appcmd_with_shell_process(appcmd_info* p_info) { int ret = -1; - if (p_info == NULL || p_info->gen_cmd_func == NULL) { + if (p_info == NULL) { + D("Invalid arguments. p_info is null\n"); + return; + } + + if (p_info->gen_cmd_func == NULL) { D("Invalid arguments.\n"); p_info->exitcode = -1; return; diff --git a/src/file_sync_service.c b/src/file_sync_service.c index ffaf0bc..6c418a5 100644 --- a/src/file_sync_service.c +++ b/src/file_sync_service.c @@ -713,6 +713,8 @@ void file_sync_service(int fd, void *cookie) goto fail; } } + } else { + sdb_close(s[1]); } @@ -723,6 +725,5 @@ fail: D("sync: done\n"); sync_send_label_notify(s[0], name, 0); sdb_close(s[0]); - sdb_close(s[1]); sdb_close(fd); } diff --git a/src/parameter.h b/src/parameter.h index ea15996..5d9276c 100644 --- a/src/parameter.h +++ b/src/parameter.h @@ -79,7 +79,7 @@ static __inline__ void make_string_parameter ( parameter* pstring, const char* f pstring->type = type_string; pstring->v_string.length = strlen ( buf ); pstring->v_string.data = ( char* ) malloc ( pstring->v_string.length + 1 ); - strcpy ( pstring->v_string.data, buf ); + strncpy ( pstring->v_string.data, buf, pstring->v_string.length ); } static __inline__ void release_parameters ( parameters* param ) -- 2.7.4 From 2d1b9a883313e75e4e06abc1b06a08185c5c0e68 Mon Sep 17 00:00:00 2001 From: SangJin Kim Date: Wed, 16 Nov 2016 20:17:23 +0900 Subject: [PATCH 07/16] Fix the bug that a shell command buffer is not initialized Change-Id: Ib295d3c8a4782d71add779c659e9c4a99dda6304 Signed-off-by: SangJin Kim --- src/parameter.h | 1 + 1 file changed, 1 insertion(+) diff --git a/src/parameter.h b/src/parameter.h index 5d9276c..953602a 100644 --- a/src/parameter.h +++ b/src/parameter.h @@ -79,6 +79,7 @@ static __inline__ void make_string_parameter ( parameter* pstring, const char* f pstring->type = type_string; pstring->v_string.length = strlen ( buf ); pstring->v_string.data = ( char* ) malloc ( pstring->v_string.length + 1 ); + memset(pstring->v_string.data, 0, pstring->v_string.length + 1); strncpy ( pstring->v_string.data, buf, pstring->v_string.length ); } -- 2.7.4 From d9f0c072ce93afc724584a2d85cb7ecb2a9d7036 Mon Sep 17 00:00:00 2001 From: greatim Date: Thu, 17 Nov 2016 11:45:32 +0900 Subject: [PATCH 08/16] fix to add null-termination character when copy string by strncpy fix to add null-termination character when copy string by strncpy Change-Id: Icad071a0f17a0f1e8aff893cefd343ba12e2dd66 Signed-off-by: greatim --- src/parameter.h | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/src/parameter.h b/src/parameter.h index 953602a..a6c50bf 100644 --- a/src/parameter.h +++ b/src/parameter.h @@ -79,8 +79,7 @@ static __inline__ void make_string_parameter ( parameter* pstring, const char* f pstring->type = type_string; pstring->v_string.length = strlen ( buf ); pstring->v_string.data = ( char* ) malloc ( pstring->v_string.length + 1 ); - memset(pstring->v_string.data, 0, pstring->v_string.length + 1); - strncpy ( pstring->v_string.data, buf, pstring->v_string.length ); + strncpy ( pstring->v_string.data, buf, pstring->v_string.length + 1 ); } static __inline__ void release_parameters ( parameters* param ) -- 2.7.4 From 34ed53befff4507579eebad21922a4524696af74 Mon Sep 17 00:00:00 2001 From: greatim Date: Fri, 25 Nov 2016 15:33:00 +0900 Subject: [PATCH 09/16] refactor calling encryption functions of plugin modify the implementation of encryption function according to new plugin architecture Change-Id: I62c142b5bf95fe7c4d8529c9272213274883b0a5 Signed-off-by: greatim --- CMakeLists.txt | 2 +- src/plugin.c | 2 +- src/plugin.h | 2 + src/plugin_encrypt.c | 234 ++++++++++++++++++++++ src/{transport_security.h => plugin_encrypt.h} | 3 - src/sdb.c | 13 +- src/sdbd_plugin.h | 9 + src/transport.c | 2 +- src/transport_security.c | 261 ------------------------- 9 files changed, 255 insertions(+), 273 deletions(-) create mode 100644 src/plugin_encrypt.c rename src/{transport_security.h => plugin_encrypt.h} (89%) delete mode 100644 src/transport_security.c diff --git a/CMakeLists.txt b/CMakeLists.txt index 47edfd9..83b0a0a 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -58,7 +58,7 @@ SET(SDBD_SRCS src/default_plugin_appcmd.c src/hashtable.c src/plugin.c - src/transport_security.c + src/plugin_encrypt.c ) include(FindPkgConfig) diff --git a/src/plugin.c b/src/plugin.c index bee7aa4..68a02c6 100644 --- a/src/plugin.c +++ b/src/plugin.c @@ -172,7 +172,7 @@ int is_supported_by_plugin ( int cmd ) return ret; } -static int request_sync_cmd ( int cmd, parameters* in, parameters* out ) +int request_sync_cmd ( int cmd, parameters* in, parameters* out ) { int ret, pr; diff --git a/src/plugin.h b/src/plugin.h index fa8288e..47ed3dc 100644 --- a/src/plugin.h +++ b/src/plugin.h @@ -28,6 +28,8 @@ int default_plugin_async_proc ( int cmd, parameters* in, int out_fd ); void load_sdbd_plugin(); void unload_sdbd_plugin(); +int request_sync_cmd ( int cmd, parameters* in, parameters* out ); + // return 1 if plugin support given command // return 0 if plugin does not support given command int is_supported_by_plugin ( int cmd ); diff --git a/src/plugin_encrypt.c b/src/plugin_encrypt.c new file mode 100644 index 0000000..1c6b34a --- /dev/null +++ b/src/plugin_encrypt.c @@ -0,0 +1,234 @@ + +#include + +//#define LOG_TAG "SDBD" +//#include +#define TRACE_TAG TRACE_SDB +#include "log.h" + +#include "plugin.h" +#include "plugin_encrypt.h" +#include "parameter.h" +#include "sdbd_plugin.h" + +#define SAKEP_AKE_MSG_RECORD_FIXED_LEN 36 +#define SAKEP_AES_ECB_ADDED_PADDING_SIZE 16 + +// return 1 if success +// return 0 otherwise +int security_init(const int nSessionID, const char* pUserID) +{ + int success = 0; + int ret; + parameters in, out; + + if (pUserID == NULL) { + in.number_of_parameter = 1; + in.array_of_parameter = ( parameter* ) malloc ( sizeof (parameter) ); + in.array_of_parameter[0].type = type_int32; + in.array_of_parameter[0].v_int32 = nSessionID; + } else { + in.number_of_parameter = 2; + in.array_of_parameter = ( parameter* ) malloc ( sizeof (parameter) ); + in.array_of_parameter[0].type = type_int32; + in.array_of_parameter[0].v_int32 = nSessionID; + in.array_of_parameter[1].type = type_string; + in.array_of_parameter[1].v_string.length = strlen(pUserID); + in.array_of_parameter[1].v_string.data = strdup(pUserID); + } + + ret = request_sync_cmd ( PLUGIN_SYNC_CMD_SEC_INIT, &in, &out ); + if ( ret == PLUGIN_CMD_SUCCESS ) { + success = 1; + release_parameters ( &out ); + } + + release_parameters ( &in ); + return success; +} + +// return 1 if success +// return 0 otherwise +int security_deinit(const int nSessionID) +{ + int success = 0; + int ret; + parameters in, out; + + in.number_of_parameter = 1; + in.array_of_parameter = ( parameter* ) malloc ( sizeof (parameter) ); + in.array_of_parameter[0].type = type_int32; + in.array_of_parameter[0].v_int32 = nSessionID; + + ret = request_sync_cmd ( PLUGIN_SYNC_CMD_SEC_DEINIT, &in, &out ); + if ( ret == PLUGIN_CMD_SUCCESS ) { + success = 1; + release_parameters ( &out ); + } + + release_parameters ( &in ); + return success; +} + +// return 1 if success +// return 0 otherwise +int security_parse_server_hello(const int nSessionID, apacket* pApacket) +{ + int success = 0; + int ret; + parameters in, out; + + in.number_of_parameter = 2; + in.array_of_parameter = ( parameter* ) malloc ( sizeof (parameter) ); + in.array_of_parameter[0].type = type_int32; + in.array_of_parameter[0].v_int32 = nSessionID; + in.array_of_parameter[1].type = type_chunk; + in.array_of_parameter[1].v_chunk.size = pApacket->msg.data_length; + in.array_of_parameter[1].v_chunk.data = pApacket->data; + + ret = request_sync_cmd ( PLUGIN_SYNC_CMD_SEC_PARSE_SERVER_HELLO, &in, &out ); + if ( ret == PLUGIN_CMD_SUCCESS ) { + success = 1; + release_parameters ( &out ); + } + + // avoid to free + in.array_of_parameter[1].v_chunk.data = NULL; + release_parameters ( &in ); + return success; +} + +// return 1 if success +// return 0 otherwise +int security_gen_client_hello(const int nSessionID, apacket* pApacket) +{ + int success = 0; + int ret; + parameters in, out; + + in.number_of_parameter = 1; + in.array_of_parameter = ( parameter* ) malloc ( sizeof (parameter) ); + in.array_of_parameter[0].type = type_int32; + in.array_of_parameter[0].v_int32 = nSessionID; + + ret = request_sync_cmd ( PLUGIN_SYNC_CMD_SEC_GEN_CLIENT_HELLO, &in, &out ); + if ( ret == PLUGIN_CMD_SUCCESS ) { + memcpy(pApacket->data, out.array_of_parameter[0].v_chunk.data, out.array_of_parameter[0].v_chunk.size); + pApacket->msg.data_length = out.array_of_parameter[0].v_chunk.size; + success = 1; + release_parameters ( &out ); + } + + release_parameters ( &in ); + return success; +} + +// return 1 if success +// return 0 otherwise +int security_parse_server_ack(const int nSessionID, apacket* pApacket) +{ + int success = 0; + int ret; + parameters in, out; + + in.number_of_parameter = 2; + in.array_of_parameter = ( parameter* ) malloc ( sizeof (parameter) ); + in.array_of_parameter[0].type = type_int32; + in.array_of_parameter[0].v_int32 = nSessionID; + in.array_of_parameter[1].type = type_chunk; + in.array_of_parameter[1].v_chunk.size = pApacket->msg.data_length; + in.array_of_parameter[1].v_chunk.data = pApacket->data; + + ret = request_sync_cmd ( PLUGIN_SYNC_CMD_SEC_PARSE_SERVER_ACK, &in, &out ); + if ( ret == PLUGIN_CMD_SUCCESS ) { + success = 1; + release_parameters ( &out ); + } + + // avoid to free + in.array_of_parameter[1].v_chunk.data = NULL; + release_parameters ( &in ); + return success; +} + +// return 1 if success +// return 0 otherwise +int security_gen_client_ack(const int nSessionID, apacket* pApacket) +{ + int success = 0; + int ret; + parameters in, out; + + in.number_of_parameter = 1; + in.array_of_parameter = ( parameter* ) malloc ( sizeof (parameter) ); + in.array_of_parameter[0].type = type_int32; + in.array_of_parameter[0].v_int32 = nSessionID; + + ret = request_sync_cmd ( PLUGIN_SYNC_CMD_SEC_GEN_CLIENT_ACK, &in, &out ); + if ( ret == PLUGIN_CMD_SUCCESS ) { + memcpy(pApacket->data, out.array_of_parameter[0].v_chunk.data, out.array_of_parameter[0].v_chunk.size); + pApacket->msg.data_length = out.array_of_parameter[0].v_chunk.size; + success = 1; + release_parameters ( &out ); + } + + release_parameters ( &in ); + return success; +} + +// return 1 if success +// return 0 otherwise +int security_encrypt(const int nSessionID, apacket* pApacket) +{ + int success = 0; + int ret; + parameters in, out; + + in.number_of_parameter = 2; + in.array_of_parameter = ( parameter* ) malloc ( sizeof (parameter) ); + in.array_of_parameter[0].type = type_int32; + in.array_of_parameter[0].v_int32 = nSessionID; + in.array_of_parameter[1].type = type_chunk; + in.array_of_parameter[1].v_chunk.size = pApacket->msg.data_length; + in.array_of_parameter[1].v_chunk.data = pApacket->data; + + ret = request_sync_cmd ( PLUGIN_SYNC_CMD_SEC_ENCRYPT, &in, &out ); + if ( ret == PLUGIN_CMD_SUCCESS ) { + memcpy(pApacket->data, out.array_of_parameter[0].v_chunk.data, out.array_of_parameter[0].v_chunk.size); + pApacket->msg.data_length = out.array_of_parameter[0].v_chunk.size; + success = 1; + release_parameters ( &out ); + } + + release_parameters ( &in ); + return success; +} + +// return 1 if success +// return 0 otherwise +int security_decrypt(const int nSessionID, apacket* pApacket) +{ + int success = 0; + int ret; + parameters in, out; + + in.number_of_parameter = 2; + in.array_of_parameter = ( parameter* ) malloc ( sizeof (parameter) ); + in.array_of_parameter[0].type = type_int32; + in.array_of_parameter[0].v_int32 = nSessionID; + in.array_of_parameter[1].type = type_chunk; + in.array_of_parameter[1].v_chunk.size = pApacket->msg.data_length; + in.array_of_parameter[1].v_chunk.data = pApacket->data; + + ret = request_sync_cmd ( PLUGIN_SYNC_CMD_SEC_DECRYPT, &in, &out ); + if ( ret == PLUGIN_CMD_SUCCESS ) { + memcpy(pApacket->data, out.array_of_parameter[0].v_chunk.data, out.array_of_parameter[0].v_chunk.size); + pApacket->msg.data_length = out.array_of_parameter[0].v_chunk.size; + success = 1; + release_parameters ( &out ); + } + + release_parameters ( &in ); + return success; +} + diff --git a/src/transport_security.h b/src/plugin_encrypt.h similarity index 89% rename from src/transport_security.h rename to src/plugin_encrypt.h index 12fd689..c54ff2b 100644 --- a/src/transport_security.h +++ b/src/plugin_encrypt.h @@ -1,11 +1,8 @@ #ifndef __TRANSPORT_SECURITY_H__ #define __TRANSPORT_SECURITY_H__ -#include #include "sdb.h" -int load_sdbd_plugin_security(); - int security_init(const int nID, const char* pUserID); int security_deinit(const int nSessionID); int security_parse_server_hello(const int nSessionID, apacket* pApacket); diff --git a/src/sdb.c b/src/sdb.c index 50cf9ed..ac7f573 100644 --- a/src/sdb.c +++ b/src/sdb.c @@ -45,7 +45,7 @@ #include "sdbd_plugin.h" #ifdef SUPPORT_ENCRYPT -#include "transport_security.h" +#include "plugin_encrypt.h" #endif #if !SDB_HOST @@ -392,19 +392,21 @@ void send_encr_fail(apacket* p, atransport *t, unsigned failed_value){ /* desc. : 암호화 메시지 핸들링 parameter : [in] apacket* p : sdbd로 들어온 메시지 - [in/out] apacket* enc_p : sdb server로 전송할 메시지 [in/out] atransport *t : 현재 연결에 대한 atransport ret : 0 : 정상적으로 메시지 전송 -1: 메시지 전송 실패 */ -int handle_encr_packet(apacket* p, apacket* enc_p, atransport *t){ +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 메시지 파싱 D("security_parse_server_hello success\n"); + enc_p = get_apacket(); if(security_gen_client_hello(t->sessionID, enc_p) == 1){ // hello 메시지 생성 D("security_gen_client_hello success\n"); enc_p->msg.command = A_ENCR; @@ -443,6 +445,7 @@ int handle_encr_packet(apacket* p, apacket* enc_p, atransport *t){ } 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 메시지 생성 D("security_gen_client_ack success\n"); enc_p->msg.command = A_ENCR; @@ -890,9 +893,7 @@ void handle_packet(apacket *p, atransport *t) #ifdef SUPPORT_ENCRYPT case A_ENCR: // 암호화 메시지인 경우 if(t->connection_state != CS_OFFLINE) { - apacket* enc_p = get_apacket(); - handle_encr_packet(p, enc_p, t); - //put_apacket(enc_p); + handle_encr_packet(p, t); } break; #endif diff --git a/src/sdbd_plugin.h b/src/sdbd_plugin.h index bcaaa8d..e98ef69 100644 --- a/src/sdbd_plugin.h +++ b/src/sdbd_plugin.h @@ -35,6 +35,15 @@ #define PLUGIN_SYNC_CMD_GET_LOCK_STATE 1008 #define PLUGIN_SYNC_CMD_GET_SHELL_ENV 1009 +#define PLUGIN_SYNC_CMD_SEC_INIT 1100 +#define PLUGIN_SYNC_CMD_SEC_DEINIT 1101 +#define PLUGIN_SYNC_CMD_SEC_PARSE_SERVER_HELLO 1102 +#define PLUGIN_SYNC_CMD_SEC_GEN_CLIENT_HELLO 1103 +#define PLUGIN_SYNC_CMD_SEC_PARSE_SERVER_ACK 1104 +#define PLUGIN_SYNC_CMD_SEC_GEN_CLIENT_ACK 1105 +#define PLUGIN_SYNC_CMD_SEC_ENCRYPT 1106 +#define PLUGIN_SYNC_CMD_SEC_DECRYPT 1107 + // asynchronous command #define PLUGIN_ASYNC_CMD_AUTH_CONFIRM_PUBLIC 2000 #define PLUGIN_ASYNC_CMD_APPCMD_SERVICE 2001 diff --git a/src/transport.c b/src/transport.c index bc471d6..470e55f 100644 --- a/src/transport.c +++ b/src/transport.c @@ -28,7 +28,7 @@ #include "sdb.h" #ifdef SUPPORT_ENCRYPT -#include "transport_security.h" +#include "plugin_encrypt.h" #endif static void transport_unref(atransport *t); diff --git a/src/transport_security.c b/src/transport_security.c deleted file mode 100644 index 37d3b58..0000000 --- a/src/transport_security.c +++ /dev/null @@ -1,261 +0,0 @@ -#include -#include "transport_security.h" - -#define LOG_TAG "SDBD" -#include - -#define SAKEP_AKE_MSG_RECORD_FIXED_LEN 36 -#define SAKEP_AES_ECB_ADDED_PADDING_SIZE 16 - -extern void* g_plugin_handle; - -typedef int (*SDBD_PLUGIN_CMD_SECURITY_INIT_PROC_PTR)(const int nID, const char* pUserID); -typedef int (*SDBD_PLUGIN_CMD_SECURITY_DEINIT_PROC_PTR)(const int nID); -typedef int (*SDBD_PLUGIN_CMD_SECURITY_PARSE_SERVER_HELLO_PROC_PTR)(const int nID, unsigned char* pSrc, unsigned int* nSrcLen); -typedef int (*SDBD_PLUGIN_CMD_SECURITY_GEN_CLIENT_HELLO_PROC_PTR)(const int nID, unsigned char* pSrc, unsigned int* nSrcLen); -typedef int (*SDBD_PLUGIN_CMD_SECURITY_PARSE_SERVER_ACK_PROC_PTR)(const int nID, unsigned char* pSrc, unsigned int* nSrcLen); -typedef int (*SDBD_PLUGIN_CMD_SECURITY_GEN_CLIENT_ACK_PROC_PTR)(const int nID, unsigned char* pSrc, unsigned int* nSrcLen); -typedef int (*SDBD_PLUGIN_CMD_SECURITY_ENCRYPT_PROC_PTR)(const int nID, const unsigned char* pSrc, const unsigned int nSrcLen, - unsigned char* pDst, unsigned int* pnDstLen); -typedef int (*SDBD_PLUGIN_CMD_SECURITY_DECRYPT_PROC_PTR)(const int nID, const unsigned char* pSrc, const unsigned int nSrcLen, - unsigned char* pDst, unsigned int* pnDstLen); - -SDBD_PLUGIN_CMD_SECURITY_INIT_PROC_PTR sdbd_plugin_cmd_security_init = NULL; -SDBD_PLUGIN_CMD_SECURITY_DEINIT_PROC_PTR sdbd_plugin_cmd_security_deinit = NULL; -SDBD_PLUGIN_CMD_SECURITY_PARSE_SERVER_HELLO_PROC_PTR sdbd_plugin_cmd_security_parse_server_hello = NULL; -SDBD_PLUGIN_CMD_SECURITY_GEN_CLIENT_HELLO_PROC_PTR sdbd_plugin_cmd_security_gen_client_hello = NULL; -SDBD_PLUGIN_CMD_SECURITY_PARSE_SERVER_ACK_PROC_PTR sdbd_plugin_cmd_security_parse_server_ack = NULL; -SDBD_PLUGIN_CMD_SECURITY_GEN_CLIENT_ACK_PROC_PTR sdbd_plugin_cmd_security_gen_client_ack = NULL; -SDBD_PLUGIN_CMD_SECURITY_ENCRYPT_PROC_PTR sdbd_plugin_cmd_security_encrypt = NULL; -SDBD_PLUGIN_CMD_SECURITY_DECRYPT_PROC_PTR sdbd_plugin_cmd_security_decrypt = NULL; - -#define SDBD_PLUGIN_CMD_SECURITY_INIT_INTF "sdbd_plugin_cmd_security_init" -#define SDBD_PLUGIN_CMD_SECURITY_DEINIT_INTF "sdbd_plugin_cmd_security_deinit" -#define SDBD_PLUGIN_CMD_SECURITY_PARSE_SERVER_HELLO_INTF "sdbd_plugin_cmd_security_parse_server_hello" -#define SDBD_PLUGIN_CMD_SECURITY_GEN_CLIENT_HELLO_INTF "sdbd_plugin_cmd_security_gen_client_hello" -#define SDBD_PLUGIN_CMD_SECURITY_PARSE_SERVER_ACK_INTF "sdbd_plugin_cmd_security_parse_server_ack" -#define SDBD_PLUGIN_CMD_SECURITY_GEN_CLIENT_ACK_INTF "sdbd_plugin_cmd_security_gen_client_ack" -#define SDBD_PLUGIN_CMD_SECURITY_ENCRYPT_INTF "sdbd_plugin_cmd_security_encrypt" -#define SDBD_PLUGIN_CMD_SECURITY_DECRYPT_INTF "sdbd_plugin_cmd_security_decrypt" - -int load_sdbd_plugin_security() { - - if( sdbd_plugin_cmd_security_init == NULL ) { - LOGI("sdbd_plugin_cmd_security_init == NULL, dlsym sdbd_plugin_cmd_security_init"); - sdbd_plugin_cmd_security_init = dlsym(g_plugin_handle, SDBD_PLUGIN_CMD_SECURITY_INIT_INTF); - if( sdbd_plugin_cmd_security_init == NULL ) { - LOGI("sdbd_plugin_cmd_security_init == NULL, dlerror = [%s]", dlerror()); - } - } - LOGI("sdbd_plugin_cmd_security_init = [0x%p]", sdbd_plugin_cmd_security_init); - - - if( sdbd_plugin_cmd_security_deinit == NULL ) { - LOGI("sdbd_plugin_cmd_security_deinit == NULL, dlsym sdbd_plugin_cmd_security_deinit\n"); - sdbd_plugin_cmd_security_deinit = dlsym(g_plugin_handle, SDBD_PLUGIN_CMD_SECURITY_DEINIT_INTF); - if( sdbd_plugin_cmd_security_deinit == NULL ) { - LOGI("sdbd_plugin_cmd_security_deinit == NULL, dlerror = [%s]\n", dlerror()); - } - } - LOGI("sdbd_plugin_cmd_security_deinit = [0x%p]\n", sdbd_plugin_cmd_security_deinit); -// - if( sdbd_plugin_cmd_security_parse_server_hello == NULL ) { - LOGI("sdbd_plugin_cmd_security_parse_server_hello == NULL, dlsym sdbd_plugin_cmd_security_parse_server_hello\n"); - sdbd_plugin_cmd_security_parse_server_hello = dlsym(g_plugin_handle, SDBD_PLUGIN_CMD_SECURITY_PARSE_SERVER_HELLO_INTF); - if( sdbd_plugin_cmd_security_parse_server_hello == NULL ) { - LOGI("sdbd_plugin_cmd_security_parse_server_hello == NULL, dlerror = [%s]\n", dlerror()); - } - } - LOGI("sdbd_plugin_cmd_security_parse_server_hello = [0x%p]\n", sdbd_plugin_cmd_security_parse_server_hello); -// - if( sdbd_plugin_cmd_security_gen_client_hello == NULL ) { - LOGI("sdbd_plugin_cmd_security_gen_client_hello == NULL, dlsym sdbd_plugin_cmd_security_gen_client_hello\n"); - sdbd_plugin_cmd_security_gen_client_hello = dlsym(g_plugin_handle, SDBD_PLUGIN_CMD_SECURITY_GEN_CLIENT_HELLO_INTF); - if( sdbd_plugin_cmd_security_gen_client_hello == NULL ) { - LOGI("sdbd_plugin_cmd_security_gen_client_hello == NULL, dlerror = [%s]\n", dlerror()); - } - } - LOGI("sdbd_plugin_cmd_security_gen_client_hello = [0x%p]\n", sdbd_plugin_cmd_security_gen_client_hello); -// - if( sdbd_plugin_cmd_security_parse_server_ack == NULL ) { - LOGI("sdbd_plugin_cmd_security_parse_server_ack == NULL, dlsym sdbd_plugin_cmd_security_parse_server_ack\n"); - sdbd_plugin_cmd_security_parse_server_ack = dlsym(g_plugin_handle, SDBD_PLUGIN_CMD_SECURITY_PARSE_SERVER_ACK_INTF); - if( sdbd_plugin_cmd_security_parse_server_ack == NULL ) { - LOGI("sdbd_plugin_cmd_security_parse_server_ack == NULL, dlerror = [%s]\n", dlerror()); - } - } - LOGI("sdbd_plugin_cmd_security_parse_server_ack = [0x%p]\n", sdbd_plugin_cmd_security_parse_server_ack); -// - if( sdbd_plugin_cmd_security_gen_client_ack == NULL ) { - LOGI("sdbd_plugin_cmd_security_gen_client_ack == NULL, dlsym sdbd_plugin_cmd_security_gen_client_ack\n"); - sdbd_plugin_cmd_security_gen_client_ack = dlsym(g_plugin_handle, SDBD_PLUGIN_CMD_SECURITY_GEN_CLIENT_ACK_INTF); - if( sdbd_plugin_cmd_security_gen_client_ack == NULL ) { - LOGI("sdbd_plugin_cmd_security_gen_client_ack == NULL, dlerror = [%s]\n", dlerror()); - } - } - LOGI("sdbd_plugin_cmd_security_gen_client_ack = [0x%p]\n", sdbd_plugin_cmd_security_gen_client_ack); - - if( sdbd_plugin_cmd_security_encrypt == NULL ) { - LOGI("sdbd_plugin_cmd_security_encrypt == NULL, dlsym sdbd_plugin_cmd_security_encrypt"); - sdbd_plugin_cmd_security_encrypt = dlsym(g_plugin_handle, SDBD_PLUGIN_CMD_SECURITY_ENCRYPT_INTF); - if( sdbd_plugin_cmd_security_encrypt == NULL ) { - LOGI("sdbd_plugin_cmd_security_encrypt == NULL, dlerror = [%s]", dlerror()); - } - } - LOGI("sdbd_plugin_cmd_security_encrypt = [0x%p]", sdbd_plugin_cmd_security_encrypt); - - if( sdbd_plugin_cmd_security_decrypt == NULL ) { - LOGI("sdbd_plugin_cmd_security_decrypt == NULL, dlsym sdbd_plugin_cmd_security_decrypt"); - sdbd_plugin_cmd_security_decrypt = dlsym(g_plugin_handle, SDBD_PLUGIN_CMD_SECURITY_DECRYPT_INTF); - if( sdbd_plugin_cmd_security_decrypt == NULL ) { - LOGI("sdbd_plugin_cmd_security_decrypt == NULL, dlerror = [%s]", dlerror()); - } - } - LOGI("sdbd_plugin_cmd_security_decrypt = [0x%p]", sdbd_plugin_cmd_security_decrypt); - - return 1; -} - - -int security_init(const int nSessionID, const char* pUserID) { - - if( sdbd_plugin_cmd_security_init == NULL ) { - LOGI("sdbd_plugin_cmd_security_init == NULL, return 0"); - return 0; - } - - return sdbd_plugin_cmd_security_init(nSessionID, pUserID); -} - -int security_deinit(const int nSessionID) { - if( sdbd_plugin_cmd_security_deinit == NULL ) { - LOGI("sdbd_plugin_cmd_security_deinit == NULL, return 0\n"); - return 0; - } - - return sdbd_plugin_cmd_security_deinit(nSessionID); -} - - -int security_parse_server_hello(const int nSessionID, apacket* pApacket){ - if( sdbd_plugin_cmd_security_parse_server_hello == NULL ) { - LOGI("sdbd_plugin_cmd_security_parse_server_hello == NULL, return 0\n"); - return 0; - } - if( pApacket == NULL ) { - LOGI("pApacket == NULL, return 0\n"); - return 0; - } - - if( 0 == sdbd_plugin_cmd_security_parse_server_hello(nSessionID, pApacket->data, &pApacket->msg.data_length) ) { - LOGI("sdbd_plugin_cmd_security_parse_server_hello return 0\n"); - return 0; - } - return 1; -} - -int security_gen_client_hello(const int nSessionID, apacket* pApacket){ - if( sdbd_plugin_cmd_security_gen_client_hello == NULL ) { - LOGI("sdbd_plugin_cmd_security_gen_client_hello == NULL, return 0\n"); - return 0; - } - if( pApacket == NULL ) { - LOGI("pApacket == NULL, return 0\n"); - return 0; - } - - if( 0 == sdbd_plugin_cmd_security_gen_client_hello(nSessionID, pApacket->data, &pApacket->msg.data_length) ) { - LOGI("sdbd_plugin_cmd_security_gen_client_hello return 0\n"); - return 0; - } - return 1; -} - -int security_parse_server_ack(const int nSessionID, apacket* pApacket){ - if( sdbd_plugin_cmd_security_parse_server_ack == NULL ) { - LOGI("sdbd_plugin_cmd_security_parse_server_ack == NULL, return 0\n"); - return 0; - } - if( pApacket == NULL ) { - LOGI("pApacket == NULL, return 0\n"); - return 0; - } - - if( 0 == sdbd_plugin_cmd_security_parse_server_ack(nSessionID, pApacket->data, &pApacket->msg.data_length) ) { - LOGI("sdbd_plugin_cmd_security_parse_server_ack return 0\n"); - return 0; - } - return 1; -} - -int security_gen_client_ack(const int nSessionID, apacket* pApacket){ - if( sdbd_plugin_cmd_security_gen_client_ack == NULL ) { - LOGI("sdbd_plugin_cmd_security_gen_client_ack == NULL, return 0\n"); - return 0; - } - if( pApacket == NULL ) { - LOGI("pApacket == NULL, return 0\n"); - return 0; - } - - if( 0 == sdbd_plugin_cmd_security_gen_client_ack(nSessionID, pApacket->data, &pApacket->msg.data_length) ) { - LOGI("sdbd_plugin_cmd_security_gen_client_ack return 0\n"); - return 0; - } - return 1; -} - - -int security_encrypt(const int nSessionID, apacket* pApacket) { - - if( pApacket == NULL ) { - LOGI("pApacket == NULL, return 0"); - return 0; - } - - unsigned char *szTemp; - szTemp = (unsigned char *)malloc(pApacket->msg.data_length + SAKEP_AKE_MSG_RECORD_FIXED_LEN + SAKEP_AES_ECB_ADDED_PADDING_SIZE); - memset(szTemp, 0x00, pApacket->msg.data_length + SAKEP_AKE_MSG_RECORD_FIXED_LEN + SAKEP_AES_ECB_ADDED_PADDING_SIZE); - - unsigned int nDstLen = 0; - if( 0 == sdbd_plugin_cmd_security_encrypt(nSessionID, pApacket->data, pApacket->msg.data_length, szTemp, &nDstLen) ) { - LOGI("sdbd_plugin_cmd_security_encrypt return 0"); - return 0; - } - - int i=0; - for(i=0 ; idata[i] = szTemp[i]; - } - - pApacket->msg.data_length = nDstLen; - free(szTemp); - return 1; - -} - -int security_decrypt(const int nSessionID, apacket* pApacket) { - - if( pApacket == NULL ) { - LOGI("pApacket == NULL, return 0"); - return 0; - } - - unsigned char *szTemp; - szTemp = (unsigned char *)malloc(pApacket->msg.data_length); - memset(szTemp, 0x00, pApacket->msg.data_length); - unsigned int nDstLen = 0; - if( 0 == sdbd_plugin_cmd_security_decrypt(nSessionID, pApacket->data, pApacket->msg.data_length, szTemp, &nDstLen) ) { - LOGI("sdbd_plugin_cmd_security_decrypt return 0"); - return 0; - } - - int i = 0; - for(i=0 ; idata[i] = szTemp[i]; - } - - pApacket->msg.data_length = nDstLen; - free(szTemp); - return 1; -} -- 2.7.4 From 3126c861c0e2d0bdcefefb44bfd9a71a9623ea40 Mon Sep 17 00:00:00 2001 From: greatim Date: Wed, 30 Nov 2016 14:30:22 +0900 Subject: [PATCH 10/16] fix a bug that cause dynamic overflow fix a bug that cause dynamic overflow Change-Id: I1cf2159915442a98257e06948bcb193886ccb547 Signed-off-by: greatim --- src/plugin_encrypt.c | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/src/plugin_encrypt.c b/src/plugin_encrypt.c index 1c6b34a..e8a96a3 100644 --- a/src/plugin_encrypt.c +++ b/src/plugin_encrypt.c @@ -29,7 +29,7 @@ int security_init(const int nSessionID, const char* pUserID) in.array_of_parameter[0].v_int32 = nSessionID; } else { in.number_of_parameter = 2; - in.array_of_parameter = ( parameter* ) malloc ( sizeof (parameter) ); + in.array_of_parameter = ( parameter* ) malloc ( sizeof (parameter) * in.number_of_parameter ); in.array_of_parameter[0].type = type_int32; in.array_of_parameter[0].v_int32 = nSessionID; in.array_of_parameter[1].type = type_string; @@ -79,7 +79,7 @@ int security_parse_server_hello(const int nSessionID, apacket* pApacket) parameters in, out; in.number_of_parameter = 2; - in.array_of_parameter = ( parameter* ) malloc ( sizeof (parameter) ); + in.array_of_parameter = ( parameter* ) malloc ( sizeof (parameter) * in.number_of_parameter ); in.array_of_parameter[0].type = type_int32; in.array_of_parameter[0].v_int32 = nSessionID; in.array_of_parameter[1].type = type_chunk; @@ -132,7 +132,7 @@ int security_parse_server_ack(const int nSessionID, apacket* pApacket) parameters in, out; in.number_of_parameter = 2; - in.array_of_parameter = ( parameter* ) malloc ( sizeof (parameter) ); + in.array_of_parameter = ( parameter* ) malloc ( sizeof (parameter) * in.number_of_parameter ); in.array_of_parameter[0].type = type_int32; in.array_of_parameter[0].v_int32 = nSessionID; in.array_of_parameter[1].type = type_chunk; @@ -185,7 +185,7 @@ int security_encrypt(const int nSessionID, apacket* pApacket) parameters in, out; in.number_of_parameter = 2; - in.array_of_parameter = ( parameter* ) malloc ( sizeof (parameter) ); + in.array_of_parameter = ( parameter* ) malloc ( sizeof (parameter) * in.number_of_parameter ); in.array_of_parameter[0].type = type_int32; in.array_of_parameter[0].v_int32 = nSessionID; in.array_of_parameter[1].type = type_chunk; @@ -213,7 +213,7 @@ int security_decrypt(const int nSessionID, apacket* pApacket) parameters in, out; in.number_of_parameter = 2; - in.array_of_parameter = ( parameter* ) malloc ( sizeof (parameter) ); + in.array_of_parameter = ( parameter* ) malloc ( sizeof (parameter) * in.number_of_parameter ); in.array_of_parameter[0].type = type_int32; in.array_of_parameter[0].v_int32 = nSessionID; in.array_of_parameter[1].type = type_chunk; -- 2.7.4 From c15dfdb55cc4702f2ab8d20b5bd1b4ebb0b29d61 Mon Sep 17 00:00:00 2001 From: greatim Date: Wed, 30 Nov 2016 16:22:59 +0900 Subject: [PATCH 11/16] modify default app command behavior for uninstall command modify default app command behavior for uninstall command Change-Id: I8acbd3761af9672f6d51a2f94330bfe3509938da Signed-off-by: greatim --- src/default_plugin_appcmd.c | 10 ++++------ 1 file changed, 4 insertions(+), 6 deletions(-) diff --git a/src/default_plugin_appcmd.c b/src/default_plugin_appcmd.c index 3fd2f64..4bc158e 100644 --- a/src/default_plugin_appcmd.c +++ b/src/default_plugin_appcmd.c @@ -95,22 +95,20 @@ static int appcmd_install_gen_shellcmd(appcmd_info* p_info) { } static int appcmd_uninstall_gen_shellcmd(appcmd_info* p_info) { - char *type = NULL; char *pkgid = NULL; char *buf = p_info->shell_cmd; int len = sizeof(p_info->shell_cmd); - if (p_info->args_cnt != 3) { + if (p_info->args_cnt != 2) { D("failed to parse appcmd.(cnt=%d)\n", p_info->args_cnt); return -1; } - type = p_info->args[1]; - pkgid = p_info->args[2]; + pkgid = p_info->args[1]; - D("args: type=%s, pkgid=%s\n", type, pkgid); + D("args: pkgid=%s\n", pkgid); - snprintf(buf, len, "pkgcmd -u -q -t %s -n %s", type, pkgid); + snprintf(buf, len, "pkgcmd -u -q -n %s", pkgid); return 0; } -- 2.7.4 From c753485c167a8a10512e5502be5449c362a695be Mon Sep 17 00:00:00 2001 From: greatim Date: Fri, 2 Dec 2016 09:30:15 +0900 Subject: [PATCH 12/16] fix a bug (free the static buffer) fix a bug (free the static buffer) Change-Id: If31caa5c8ff36ae7658bb33daa1df07e20f053be Signed-off-by: greatim --- src/plugin_encrypt.c | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/src/plugin_encrypt.c b/src/plugin_encrypt.c index e8a96a3..51df016 100644 --- a/src/plugin_encrypt.c +++ b/src/plugin_encrypt.c @@ -200,6 +200,8 @@ int security_encrypt(const int nSessionID, apacket* pApacket) release_parameters ( &out ); } + // avoid to free + in.array_of_parameter[1].v_chunk.data = NULL; release_parameters ( &in ); return success; } @@ -228,6 +230,8 @@ int security_decrypt(const int nSessionID, apacket* pApacket) release_parameters ( &out ); } + // avoid to free + in.array_of_parameter[1].v_chunk.data = NULL; release_parameters ( &in ); return success; } -- 2.7.4 From e8b8b9b96255b8bf5f8a838bff20ae12fe9f763d Mon Sep 17 00:00:00 2001 From: greatim Date: Mon, 5 Dec 2016 10:13:14 +0900 Subject: [PATCH 13/16] disable printing log in emulator by default disable printing log in emulator by default Change-Id: I88ad00f7824b055847e0dcb8d580675334e12d7b Signed-off-by: greatim --- src/default_plugin_basic.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/default_plugin_basic.c b/src/default_plugin_basic.c index 81f313c..91d8df2 100644 --- a/src/default_plugin_basic.c +++ b/src/default_plugin_basic.c @@ -73,7 +73,7 @@ int get_plugin_capability ( parameters* in, parameters* out ) } else if ( capability == CAPABILITY_PRODUCT_VER ) { make_string_parameter ( & ( out->array_of_parameter[0] ), "%s", PLUGIN_RET_UNKNOWN ); } else if ( capability == CAPABILITY_LOG_ENABLE ) { - make_string_parameter ( & ( out->array_of_parameter[0] ), "%s", PLUGIN_RET_ENABLED ); + make_string_parameter ( & ( out->array_of_parameter[0] ), "%s", PLUGIN_RET_DISABLED ); } else if ( capability == CAPABILITY_LOG_PATH ) { make_string_parameter ( & ( out->array_of_parameter[0] ), "%s", LOG_DIRECTORY ); } else if ( capability == CAPABILITY_APPCMD ) { -- 2.7.4 From 046f23e7ea9c15c72de74fc46530c3319bc7622d Mon Sep 17 00:00:00 2001 From: Kim Gunsoo Date: Thu, 6 Oct 2016 21:12:34 +0900 Subject: [PATCH 14/16] Modify the SMACK label for SDB shell. - Previously, there was a problem that the SDB shell has the SMACK authority of sdbd. In order to prevent this, it has been modified to run a separate SMACK label between sdbd and SDB shell. Change-Id: I768ef0b165cf66fe88648cc272638819c4bd96fe Signed-off-by: Kim Gunsoo --- packaging/sdbd.spec | 4 ++++ src/default_plugin_appcmd.c | 5 +++-- src/sdb.c | 54 +++++++++++++++++++++++++++++++++++++++------ src/sdb.h | 3 ++- src/sdktools.h | 1 + src/services.c | 16 ++++++++++++++ 6 files changed, 73 insertions(+), 10 deletions(-) diff --git a/packaging/sdbd.spec b/packaging/sdbd.spec index bc9408f..15eb808 100644 --- a/packaging/sdbd.spec +++ b/packaging/sdbd.spec @@ -109,6 +109,10 @@ if ! getent passwd "${TZ_SDK_USER_NAME}" > /dev/null; then done fi +cp -f /bin/sh /bin/sh-user +chsmack -a "_" /bin/sh-user +chsmack -e "User::Shell" /bin/sh-user + %files %manifest sdbd.manifest %license LICENSE diff --git a/src/default_plugin_appcmd.c b/src/default_plugin_appcmd.c index 4bc158e..83cecca 100644 --- a/src/default_plugin_appcmd.c +++ b/src/default_plugin_appcmd.c @@ -38,6 +38,7 @@ #include +#define SHELL_COMMAND "/bin/sh" #define APPCMD_RESULT_BUFSIZE (4096) typedef struct appcmd_info appcmd_info; @@ -641,10 +642,10 @@ static void run_appcmd_appinstallpath(appcmd_info* p_info) { p_info->exitcode = -1; - const char* path = tzplatform_getenv(TZ_SDK_HOME); + const char* path = tzplatform_getenv(TZ_SDK_TOOLS); if (path != NULL) { p_info->exitcode = 0; - snprintf(result_buf, sizeof(result_buf), "\n%s:%s/apps_rw/\n", MESSAGE_PREFIX_APPCMD_RETURN, path); + snprintf(result_buf, sizeof(result_buf), "\n%s:%s\n", MESSAGE_PREFIX_APPCMD_RETURN, path); writex(p_info->fd, result_buf, strlen(result_buf)); } else { D("failed to get application install path from tzplatform_getenv."); diff --git a/src/sdb.c b/src/sdb.c index ac7f573..2be2345 100644 --- a/src/sdb.c +++ b/src/sdb.c @@ -31,6 +31,7 @@ #include #include #include +#include #include "sysdeps.h" #include "log.h" @@ -58,6 +59,7 @@ #define PROC_CMDLINE_PATH "/proc/cmdline" #define USB_SERIAL_PATH "/sys/class/usb_mode/usb0/iSerial" +#define APPID2PID_PATH "/usr/bin/appid2pid" #include #include @@ -125,6 +127,29 @@ int is_emulator(void) { #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_container_enabled(void) { bool value; int ret; @@ -373,7 +398,7 @@ void print_packet(const char *label, apacket *p) #endif #ifdef SUPPORT_ENCRYPT -/* +/* desc. : 암호화 실패 메시지 전송 parameter : [in] apacket* p : sdbd로 들어온 메시지 [in] atransport *t : 현재 연결에 대한 atransport @@ -389,7 +414,7 @@ void send_encr_fail(apacket* p, atransport *t, unsigned failed_value){ //put_apacket(enc_p); } -/* +/* desc. : 암호화 메시지 핸들링 parameter : [in] apacket* p : sdbd로 들어온 메시지 [in/out] atransport *t : 현재 연결에 대한 atransport @@ -403,12 +428,12 @@ int handle_encr_packet(apacket* p, atransport *t){ if(p->msg.arg0 == ENCR_SET_ON_REQ){ // hello 메시지인 경우 t->sessionID = sessionID; - if((retVal = security_init(t->sessionID, NULL)) == 1){ // 암호화 handshaking을 위한 init + if((retVal = security_init(t->sessionID, NULL)) == 1){ // 암호화 handshaking을 위한 init if(security_parse_server_hello(t->sessionID, p) == 1){ // hello 메시지 파싱 D("security_parse_server_hello success\n"); enc_p = get_apacket(); if(security_gen_client_hello(t->sessionID, enc_p) == 1){ // hello 메시지 생성 - D("security_gen_client_hello success\n"); + D("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; @@ -419,7 +444,7 @@ int handle_encr_packet(apacket* p, atransport *t){ D("security_gen_client_hello error\n"); send_encr_fail(p, t, ENCR_ON_FAIL); // 암호화 on 실패 메시지 전송 t->encryption = ENCR_OFF; // 암호화 모드는 off - security_deinit(t->sessionID); + security_deinit(t->sessionID); return -1; } } @@ -428,7 +453,7 @@ int handle_encr_packet(apacket* p, atransport *t){ send_encr_fail(p, t, ENCR_ON_FAIL); t->encryption = ENCR_OFF; security_deinit(t->sessionID); - + return -1; } } else { // init 실패 @@ -511,7 +536,7 @@ int handle_encr_packet(apacket* p, atransport *t){ } //put_apacket(enc_p); return 0; - + } #endif @@ -1228,6 +1253,10 @@ void start_device_log(void) return; } + if (smack_setlabel(path, SDK_SHELL_LABEL_NAME, SMACK_LABEL_ACCESS) == -1) { + D("unable to set sdk shell smack label %s due to (errno:%d)\n", SDK_SHELL_LABEL_NAME, errno); + } + // redirect stdout and stderr to the log file dup2(fd, 1); dup2(fd, 2); @@ -1992,6 +2021,17 @@ static void init_capabilities(void) { "%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 + snprintf(g_capabilities.pkgcmd_debugmode, sizeof(g_capabilities.pkgcmd_debugmode), + "%s", ENABLED); + + // Capability version snprintf(g_capabilities.sdbd_cap_version, sizeof(g_capabilities.sdbd_cap_version), "%d.%d", SDBD_CAP_VERSION_MAJOR, SDBD_CAP_VERSION_MINOR); diff --git a/src/sdb.h b/src/sdb.h index 348a7eb..052d49d 100644 --- a/src/sdb.h +++ b/src/sdb.h @@ -275,6 +275,8 @@ typedef struct platform_capabilities char sockproto_support[CAPBUF_ITEMSIZE]; // enabled or disabled char appcmd_support[CAPBUF_ITEMSIZE]; // enabled or disabled char encryption_support[CAPBUF_ITEMSIZE]; // enabled or disabled + char appid2pid_support[CAPBUF_ITEMSIZE]; // enabled or disabled + char pkgcmd_debugmode[CAPBUF_ITEMSIZE]; // enabled or disabled char log_enable[CAPBUF_ITEMSIZE]; // enabled or disabled char log_path[CAPBUF_LL_ITEMSIZE]; // path of sdbd log @@ -542,7 +544,6 @@ int read_line(const int fd, char* ptr, const size_t maxlen); #define USB_FUNCFS_SDB_PATH "/dev/usbgadget/sdb" #define USB_NODE_FILE "/dev/samsung_sdb" -#define SHELL_COMMAND "/bin/sh" int create_subprocess(const char *cmd, pid_t *pid, char * const argv[], char * const envp[]); void get_env(char *key, char **env); diff --git a/src/sdktools.h b/src/sdktools.h index 9027970..e73bfec 100644 --- a/src/sdktools.h +++ b/src/sdktools.h @@ -37,6 +37,7 @@ struct arg_permit_rule #define APPID_MAX_LENGTH 50 #define SDBD_LABEL_NAME "sdbd" #define SDK_HOME_LABEL_NAME "sdbd::home" +#define SDK_SHELL_LABEL_NAME "User::Shell" int verify_root_commands(const char *arg1); int verify_app_path(const char* path); diff --git a/src/services.c b/src/services.c index d2d1500..76c28d1 100644 --- a/src/services.c +++ b/src/services.c @@ -44,6 +44,7 @@ #include "utils.h" #include #include +#include #include #include @@ -461,6 +462,12 @@ int create_subprocess(const char *cmd, pid_t *pid, char * const argv[], char * c return -1; } + if (smack_setlabel(devname, SDK_SHELL_LABEL_NAME, SMACK_LABEL_ACCESS) == -1) { + D("unable to set sdk shell smack label %s due to (errno:%d)\n", SDK_SHELL_LABEL_NAME, errno); + sdb_close(ptm); + return -1; + } + *pid = fork(); if(*pid < 0) { D("- fork failed: errno:%d -\n", errno); @@ -521,6 +528,7 @@ int create_subprocess(const char *cmd, pid_t *pid, char * const argv[], char * c } #endif /* !SDB_HOST */ +#define SHELL_COMMAND "/bin/sh-user" #define LOGIN_COMMAND "/bin/login" #define SUPER_USER "root" #define LOGIN_CONFIG "/etc/login.defs" @@ -1012,6 +1020,14 @@ static void get_capability(int fd, void *cookie) { offset += put_key_value_string(cap_buffer, offset, CAPBUF_SIZE, "appcmd_support", g_capabilities.appcmd_support); + // appid2pid support + offset += put_key_value_string(cap_buffer, offset, CAPBUF_SIZE, + "appid2pid_support", g_capabilities.appid2pid_support); + + // pkgcmd debug mode support + offset += put_key_value_string(cap_buffer, offset, CAPBUF_SIZE, + "pkgcmd_debugmode", g_capabilities.pkgcmd_debugmode); + offset++; // for '\0' character writex(fd, &offset, sizeof(uint16_t)); -- 2.7.4 From 37ca0ed4a0610cc20f954cb94a2ac7698ba52d56 Mon Sep 17 00:00:00 2001 From: Jaewon Lim Date: Sun, 11 Dec 2016 20:32:40 -0800 Subject: [PATCH 15/16] Revert "Modify the SMACK label for SDB shell." This reverts commit 046f23e7ea9c15c72de74fc46530c3319bc7622d. Change-Id: I196d5d4d975e9aec1efd28a39c3f1aaf2a9da6f9 --- packaging/sdbd.spec | 4 ---- src/default_plugin_appcmd.c | 5 ++--- src/sdb.c | 54 ++++++--------------------------------------- src/sdb.h | 3 +-- src/sdktools.h | 1 - src/services.c | 16 -------------- 6 files changed, 10 insertions(+), 73 deletions(-) diff --git a/packaging/sdbd.spec b/packaging/sdbd.spec index 15eb808..bc9408f 100644 --- a/packaging/sdbd.spec +++ b/packaging/sdbd.spec @@ -109,10 +109,6 @@ if ! getent passwd "${TZ_SDK_USER_NAME}" > /dev/null; then done fi -cp -f /bin/sh /bin/sh-user -chsmack -a "_" /bin/sh-user -chsmack -e "User::Shell" /bin/sh-user - %files %manifest sdbd.manifest %license LICENSE diff --git a/src/default_plugin_appcmd.c b/src/default_plugin_appcmd.c index 83cecca..4bc158e 100644 --- a/src/default_plugin_appcmd.c +++ b/src/default_plugin_appcmd.c @@ -38,7 +38,6 @@ #include -#define SHELL_COMMAND "/bin/sh" #define APPCMD_RESULT_BUFSIZE (4096) typedef struct appcmd_info appcmd_info; @@ -642,10 +641,10 @@ static void run_appcmd_appinstallpath(appcmd_info* p_info) { p_info->exitcode = -1; - const char* path = tzplatform_getenv(TZ_SDK_TOOLS); + const char* path = tzplatform_getenv(TZ_SDK_HOME); if (path != NULL) { p_info->exitcode = 0; - snprintf(result_buf, sizeof(result_buf), "\n%s:%s\n", MESSAGE_PREFIX_APPCMD_RETURN, path); + snprintf(result_buf, sizeof(result_buf), "\n%s:%s/apps_rw/\n", MESSAGE_PREFIX_APPCMD_RETURN, path); writex(p_info->fd, result_buf, strlen(result_buf)); } else { D("failed to get application install path from tzplatform_getenv."); diff --git a/src/sdb.c b/src/sdb.c index 2be2345..ac7f573 100644 --- a/src/sdb.c +++ b/src/sdb.c @@ -31,7 +31,6 @@ #include #include #include -#include #include "sysdeps.h" #include "log.h" @@ -59,7 +58,6 @@ #define PROC_CMDLINE_PATH "/proc/cmdline" #define USB_SERIAL_PATH "/sys/class/usb_mode/usb0/iSerial" -#define APPID2PID_PATH "/usr/bin/appid2pid" #include #include @@ -127,29 +125,6 @@ int is_emulator(void) { #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_container_enabled(void) { bool value; int ret; @@ -398,7 +373,7 @@ void print_packet(const char *label, apacket *p) #endif #ifdef SUPPORT_ENCRYPT -/* +/* desc. : 암호화 실패 메시지 전송 parameter : [in] apacket* p : sdbd로 들어온 메시지 [in] atransport *t : 현재 연결에 대한 atransport @@ -414,7 +389,7 @@ void send_encr_fail(apacket* p, atransport *t, unsigned failed_value){ //put_apacket(enc_p); } -/* +/* desc. : 암호화 메시지 핸들링 parameter : [in] apacket* p : sdbd로 들어온 메시지 [in/out] atransport *t : 현재 연결에 대한 atransport @@ -428,12 +403,12 @@ int handle_encr_packet(apacket* p, atransport *t){ if(p->msg.arg0 == ENCR_SET_ON_REQ){ // hello 메시지인 경우 t->sessionID = sessionID; - if((retVal = security_init(t->sessionID, NULL)) == 1){ // 암호화 handshaking을 위한 init + if((retVal = security_init(t->sessionID, NULL)) == 1){ // 암호화 handshaking을 위한 init if(security_parse_server_hello(t->sessionID, p) == 1){ // hello 메시지 파싱 D("security_parse_server_hello success\n"); enc_p = get_apacket(); if(security_gen_client_hello(t->sessionID, enc_p) == 1){ // hello 메시지 생성 - D("security_gen_client_hello success\n"); + D("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; @@ -444,7 +419,7 @@ int handle_encr_packet(apacket* p, atransport *t){ D("security_gen_client_hello error\n"); send_encr_fail(p, t, ENCR_ON_FAIL); // 암호화 on 실패 메시지 전송 t->encryption = ENCR_OFF; // 암호화 모드는 off - security_deinit(t->sessionID); + security_deinit(t->sessionID); return -1; } } @@ -453,7 +428,7 @@ int handle_encr_packet(apacket* p, atransport *t){ send_encr_fail(p, t, ENCR_ON_FAIL); t->encryption = ENCR_OFF; security_deinit(t->sessionID); - + return -1; } } else { // init 실패 @@ -536,7 +511,7 @@ int handle_encr_packet(apacket* p, atransport *t){ } //put_apacket(enc_p); return 0; - + } #endif @@ -1253,10 +1228,6 @@ void start_device_log(void) return; } - if (smack_setlabel(path, SDK_SHELL_LABEL_NAME, SMACK_LABEL_ACCESS) == -1) { - D("unable to set sdk shell smack label %s due to (errno:%d)\n", SDK_SHELL_LABEL_NAME, errno); - } - // redirect stdout and stderr to the log file dup2(fd, 1); dup2(fd, 2); @@ -2021,17 +1992,6 @@ static void init_capabilities(void) { "%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 - snprintf(g_capabilities.pkgcmd_debugmode, sizeof(g_capabilities.pkgcmd_debugmode), - "%s", ENABLED); - - // Capability version snprintf(g_capabilities.sdbd_cap_version, sizeof(g_capabilities.sdbd_cap_version), "%d.%d", SDBD_CAP_VERSION_MAJOR, SDBD_CAP_VERSION_MINOR); diff --git a/src/sdb.h b/src/sdb.h index 052d49d..348a7eb 100644 --- a/src/sdb.h +++ b/src/sdb.h @@ -275,8 +275,6 @@ typedef struct platform_capabilities char sockproto_support[CAPBUF_ITEMSIZE]; // enabled or disabled char appcmd_support[CAPBUF_ITEMSIZE]; // enabled or disabled char encryption_support[CAPBUF_ITEMSIZE]; // enabled or disabled - char appid2pid_support[CAPBUF_ITEMSIZE]; // enabled or disabled - char pkgcmd_debugmode[CAPBUF_ITEMSIZE]; // enabled or disabled char log_enable[CAPBUF_ITEMSIZE]; // enabled or disabled char log_path[CAPBUF_LL_ITEMSIZE]; // path of sdbd log @@ -544,6 +542,7 @@ int read_line(const int fd, char* ptr, const size_t maxlen); #define USB_FUNCFS_SDB_PATH "/dev/usbgadget/sdb" #define USB_NODE_FILE "/dev/samsung_sdb" +#define SHELL_COMMAND "/bin/sh" int create_subprocess(const char *cmd, pid_t *pid, char * const argv[], char * const envp[]); void get_env(char *key, char **env); diff --git a/src/sdktools.h b/src/sdktools.h index e73bfec..9027970 100644 --- a/src/sdktools.h +++ b/src/sdktools.h @@ -37,7 +37,6 @@ struct arg_permit_rule #define APPID_MAX_LENGTH 50 #define SDBD_LABEL_NAME "sdbd" #define SDK_HOME_LABEL_NAME "sdbd::home" -#define SDK_SHELL_LABEL_NAME "User::Shell" int verify_root_commands(const char *arg1); int verify_app_path(const char* path); diff --git a/src/services.c b/src/services.c index 76c28d1..d2d1500 100644 --- a/src/services.c +++ b/src/services.c @@ -44,7 +44,6 @@ #include "utils.h" #include #include -#include #include #include @@ -462,12 +461,6 @@ int create_subprocess(const char *cmd, pid_t *pid, char * const argv[], char * c return -1; } - if (smack_setlabel(devname, SDK_SHELL_LABEL_NAME, SMACK_LABEL_ACCESS) == -1) { - D("unable to set sdk shell smack label %s due to (errno:%d)\n", SDK_SHELL_LABEL_NAME, errno); - sdb_close(ptm); - return -1; - } - *pid = fork(); if(*pid < 0) { D("- fork failed: errno:%d -\n", errno); @@ -528,7 +521,6 @@ int create_subprocess(const char *cmd, pid_t *pid, char * const argv[], char * c } #endif /* !SDB_HOST */ -#define SHELL_COMMAND "/bin/sh-user" #define LOGIN_COMMAND "/bin/login" #define SUPER_USER "root" #define LOGIN_CONFIG "/etc/login.defs" @@ -1020,14 +1012,6 @@ static void get_capability(int fd, void *cookie) { offset += put_key_value_string(cap_buffer, offset, CAPBUF_SIZE, "appcmd_support", g_capabilities.appcmd_support); - // appid2pid support - offset += put_key_value_string(cap_buffer, offset, CAPBUF_SIZE, - "appid2pid_support", g_capabilities.appid2pid_support); - - // pkgcmd debug mode support - offset += put_key_value_string(cap_buffer, offset, CAPBUF_SIZE, - "pkgcmd_debugmode", g_capabilities.pkgcmd_debugmode); - offset++; // for '\0' character writex(fd, &offset, sizeof(uint16_t)); -- 2.7.4 From cb4d1bb8af186a59661e4e35bdb13fecdc1a0163 Mon Sep 17 00:00:00 2001 From: Jaewon Lim Date: Thu, 22 Dec 2016 23:57:25 -0800 Subject: [PATCH 16/16] Revert "Revert "Modify the SMACK label for SDB shell."" This reverts commit 37ca0ed4a0610cc20f954cb94a2ac7698ba52d56. Change-Id: Idc727cc0a259d750634d3ef70b4f71dc9a160eba --- packaging/sdbd.spec | 4 ++++ src/default_plugin_appcmd.c | 5 +++-- src/sdb.c | 54 +++++++++++++++++++++++++++++++++++++++------ src/sdb.h | 3 ++- src/sdktools.h | 1 + src/services.c | 16 ++++++++++++++ 6 files changed, 73 insertions(+), 10 deletions(-) diff --git a/packaging/sdbd.spec b/packaging/sdbd.spec index bc9408f..15eb808 100644 --- a/packaging/sdbd.spec +++ b/packaging/sdbd.spec @@ -109,6 +109,10 @@ if ! getent passwd "${TZ_SDK_USER_NAME}" > /dev/null; then done fi +cp -f /bin/sh /bin/sh-user +chsmack -a "_" /bin/sh-user +chsmack -e "User::Shell" /bin/sh-user + %files %manifest sdbd.manifest %license LICENSE diff --git a/src/default_plugin_appcmd.c b/src/default_plugin_appcmd.c index 4bc158e..83cecca 100644 --- a/src/default_plugin_appcmd.c +++ b/src/default_plugin_appcmd.c @@ -38,6 +38,7 @@ #include +#define SHELL_COMMAND "/bin/sh" #define APPCMD_RESULT_BUFSIZE (4096) typedef struct appcmd_info appcmd_info; @@ -641,10 +642,10 @@ static void run_appcmd_appinstallpath(appcmd_info* p_info) { p_info->exitcode = -1; - const char* path = tzplatform_getenv(TZ_SDK_HOME); + const char* path = tzplatform_getenv(TZ_SDK_TOOLS); if (path != NULL) { p_info->exitcode = 0; - snprintf(result_buf, sizeof(result_buf), "\n%s:%s/apps_rw/\n", MESSAGE_PREFIX_APPCMD_RETURN, path); + snprintf(result_buf, sizeof(result_buf), "\n%s:%s\n", MESSAGE_PREFIX_APPCMD_RETURN, path); writex(p_info->fd, result_buf, strlen(result_buf)); } else { D("failed to get application install path from tzplatform_getenv."); diff --git a/src/sdb.c b/src/sdb.c index ac7f573..2be2345 100644 --- a/src/sdb.c +++ b/src/sdb.c @@ -31,6 +31,7 @@ #include #include #include +#include #include "sysdeps.h" #include "log.h" @@ -58,6 +59,7 @@ #define PROC_CMDLINE_PATH "/proc/cmdline" #define USB_SERIAL_PATH "/sys/class/usb_mode/usb0/iSerial" +#define APPID2PID_PATH "/usr/bin/appid2pid" #include #include @@ -125,6 +127,29 @@ int is_emulator(void) { #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_container_enabled(void) { bool value; int ret; @@ -373,7 +398,7 @@ void print_packet(const char *label, apacket *p) #endif #ifdef SUPPORT_ENCRYPT -/* +/* desc. : 암호화 실패 메시지 전송 parameter : [in] apacket* p : sdbd로 들어온 메시지 [in] atransport *t : 현재 연결에 대한 atransport @@ -389,7 +414,7 @@ void send_encr_fail(apacket* p, atransport *t, unsigned failed_value){ //put_apacket(enc_p); } -/* +/* desc. : 암호화 메시지 핸들링 parameter : [in] apacket* p : sdbd로 들어온 메시지 [in/out] atransport *t : 현재 연결에 대한 atransport @@ -403,12 +428,12 @@ int handle_encr_packet(apacket* p, atransport *t){ if(p->msg.arg0 == ENCR_SET_ON_REQ){ // hello 메시지인 경우 t->sessionID = sessionID; - if((retVal = security_init(t->sessionID, NULL)) == 1){ // 암호화 handshaking을 위한 init + if((retVal = security_init(t->sessionID, NULL)) == 1){ // 암호화 handshaking을 위한 init if(security_parse_server_hello(t->sessionID, p) == 1){ // hello 메시지 파싱 D("security_parse_server_hello success\n"); enc_p = get_apacket(); if(security_gen_client_hello(t->sessionID, enc_p) == 1){ // hello 메시지 생성 - D("security_gen_client_hello success\n"); + D("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; @@ -419,7 +444,7 @@ int handle_encr_packet(apacket* p, atransport *t){ D("security_gen_client_hello error\n"); send_encr_fail(p, t, ENCR_ON_FAIL); // 암호화 on 실패 메시지 전송 t->encryption = ENCR_OFF; // 암호화 모드는 off - security_deinit(t->sessionID); + security_deinit(t->sessionID); return -1; } } @@ -428,7 +453,7 @@ int handle_encr_packet(apacket* p, atransport *t){ send_encr_fail(p, t, ENCR_ON_FAIL); t->encryption = ENCR_OFF; security_deinit(t->sessionID); - + return -1; } } else { // init 실패 @@ -511,7 +536,7 @@ int handle_encr_packet(apacket* p, atransport *t){ } //put_apacket(enc_p); return 0; - + } #endif @@ -1228,6 +1253,10 @@ void start_device_log(void) return; } + if (smack_setlabel(path, SDK_SHELL_LABEL_NAME, SMACK_LABEL_ACCESS) == -1) { + D("unable to set sdk shell smack label %s due to (errno:%d)\n", SDK_SHELL_LABEL_NAME, errno); + } + // redirect stdout and stderr to the log file dup2(fd, 1); dup2(fd, 2); @@ -1992,6 +2021,17 @@ static void init_capabilities(void) { "%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 + snprintf(g_capabilities.pkgcmd_debugmode, sizeof(g_capabilities.pkgcmd_debugmode), + "%s", ENABLED); + + // Capability version snprintf(g_capabilities.sdbd_cap_version, sizeof(g_capabilities.sdbd_cap_version), "%d.%d", SDBD_CAP_VERSION_MAJOR, SDBD_CAP_VERSION_MINOR); diff --git a/src/sdb.h b/src/sdb.h index 348a7eb..052d49d 100644 --- a/src/sdb.h +++ b/src/sdb.h @@ -275,6 +275,8 @@ typedef struct platform_capabilities char sockproto_support[CAPBUF_ITEMSIZE]; // enabled or disabled char appcmd_support[CAPBUF_ITEMSIZE]; // enabled or disabled char encryption_support[CAPBUF_ITEMSIZE]; // enabled or disabled + char appid2pid_support[CAPBUF_ITEMSIZE]; // enabled or disabled + char pkgcmd_debugmode[CAPBUF_ITEMSIZE]; // enabled or disabled char log_enable[CAPBUF_ITEMSIZE]; // enabled or disabled char log_path[CAPBUF_LL_ITEMSIZE]; // path of sdbd log @@ -542,7 +544,6 @@ int read_line(const int fd, char* ptr, const size_t maxlen); #define USB_FUNCFS_SDB_PATH "/dev/usbgadget/sdb" #define USB_NODE_FILE "/dev/samsung_sdb" -#define SHELL_COMMAND "/bin/sh" int create_subprocess(const char *cmd, pid_t *pid, char * const argv[], char * const envp[]); void get_env(char *key, char **env); diff --git a/src/sdktools.h b/src/sdktools.h index 9027970..e73bfec 100644 --- a/src/sdktools.h +++ b/src/sdktools.h @@ -37,6 +37,7 @@ struct arg_permit_rule #define APPID_MAX_LENGTH 50 #define SDBD_LABEL_NAME "sdbd" #define SDK_HOME_LABEL_NAME "sdbd::home" +#define SDK_SHELL_LABEL_NAME "User::Shell" int verify_root_commands(const char *arg1); int verify_app_path(const char* path); diff --git a/src/services.c b/src/services.c index d2d1500..76c28d1 100644 --- a/src/services.c +++ b/src/services.c @@ -44,6 +44,7 @@ #include "utils.h" #include #include +#include #include #include @@ -461,6 +462,12 @@ int create_subprocess(const char *cmd, pid_t *pid, char * const argv[], char * c return -1; } + if (smack_setlabel(devname, SDK_SHELL_LABEL_NAME, SMACK_LABEL_ACCESS) == -1) { + D("unable to set sdk shell smack label %s due to (errno:%d)\n", SDK_SHELL_LABEL_NAME, errno); + sdb_close(ptm); + return -1; + } + *pid = fork(); if(*pid < 0) { D("- fork failed: errno:%d -\n", errno); @@ -521,6 +528,7 @@ int create_subprocess(const char *cmd, pid_t *pid, char * const argv[], char * c } #endif /* !SDB_HOST */ +#define SHELL_COMMAND "/bin/sh-user" #define LOGIN_COMMAND "/bin/login" #define SUPER_USER "root" #define LOGIN_CONFIG "/etc/login.defs" @@ -1012,6 +1020,14 @@ static void get_capability(int fd, void *cookie) { offset += put_key_value_string(cap_buffer, offset, CAPBUF_SIZE, "appcmd_support", g_capabilities.appcmd_support); + // appid2pid support + offset += put_key_value_string(cap_buffer, offset, CAPBUF_SIZE, + "appid2pid_support", g_capabilities.appid2pid_support); + + // pkgcmd debug mode support + offset += put_key_value_string(cap_buffer, offset, CAPBUF_SIZE, + "pkgcmd_debugmode", g_capabilities.pkgcmd_debugmode); + offset++; // for '\0' character writex(fd, &offset, sizeof(uint16_t)); -- 2.7.4