From 8df630ad36bf733d294058d880cca6f9990ccb48 Mon Sep 17 00:00:00 2001 From: greatim Date: Thu, 3 Nov 2016 17:17:55 +0900 Subject: [PATCH] add data encryption feature add data encryption feature - encryption on / off for each device - encryption message handshaking - encryption module Change-Id: I89337af9d9a5bc6fac45401f962392491b3e43ae Signed-off-by: greatim --- CMakeLists.txt | 3 + packaging/sdbd.spec | 1 + src/sdb.c | 176 +++++++++++++++++++++++++++++++- 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 ++++ 10 files changed, 526 insertions(+), 3 deletions(-) create mode 100644 src/transport_security.c create mode 100644 src/transport_security.h diff --git a/CMakeLists.txt b/CMakeLists.txt index f160f95..43b43b8 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -51,6 +51,7 @@ SET(SDBD_SRCS src/commandline_sdbd.c src/usb_linux_client.c src/usb_funcfs_client.c + src/transport_security.c ) include(FindPkgConfig) @@ -62,6 +63,7 @@ pkg_check_modules(pkgs REQUIRED glib-2.0 dbus-1 dbus-glib-1 + dlog ) FOREACH(flag ${pkgs_CFLAGS}) @@ -79,6 +81,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/sdb.c b/src/sdb.c index d421ba7..ee0fbc1 100644 --- a/src/sdb.c +++ b/src/sdb.c @@ -41,6 +41,10 @@ #include "utils.h" #include "sdktools.h" +#ifdef SUPPORT_ENCRYPT +#include "transport_security.h" +#endif + #if !SDB_HOST #include #define SDB_PIDPATH "/tmp/.sdbd.pid" @@ -367,6 +371,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"); @@ -393,8 +538,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; @@ -737,6 +885,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); @@ -1606,6 +1763,9 @@ static int get_plugin_capability(const char* in_buf, sdbd_plugin_param out) { snprintf(out.data, out.len, "%s", SDBD_CAP_RET_DISABLED); } ret = SDBD_PLUGIN_RET_SUCCESS; + } else if (SDBD_CMP_CAP(in_buf, ENCRYPTION)) { + snprintf(out.data, out.len, "%s", SDBD_CAP_RET_DISABLED); + ret = SDBD_PLUGIN_RET_SUCCESS; } else if (SDBD_CMP_CAP(in_buf, CANLAUNCH)) { snprintf(out.data, out.len, "%s", UNKNOWN); ret = SDBD_PLUGIN_RET_SUCCESS; @@ -1791,6 +1951,10 @@ static void load_sdbd_plugin() { return; } +#ifdef SUPPORT_ENCRYPT + load_sdbd_plugin_security(); // sdbd-plugin 호출 +#endif + D("using sdbd plugin interface.(%s)\n", SDBD_PLUGIN_PATH); } @@ -2041,6 +2205,16 @@ static void init_capabilities(void) { } + // Encryption support + if(!request_plugin_cmd(SDBD_CMD_PLUGIN_CAP, SDBD_CAP_TYPE_ENCRYPTION, + g_capabilities.encryption_support, + sizeof(g_capabilities.encryption_support))) { + D("failed to request. (%s:%s) \n", SDBD_CMD_PLUGIN_CAP, SDBD_CAP_TYPE_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 67f365f..f516ecc 100644 --- a/src/sdb.h +++ b/src/sdb.h @@ -38,6 +38,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 @@ -201,6 +213,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 }; @@ -260,6 +277,7 @@ 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 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 dce56e1..0ffe5e5 100644 --- a/src/sdbd_plugin.h +++ b/src/sdbd_plugin.h @@ -35,6 +35,7 @@ #define SDBD_CAP_TYPE_USBPROTO "usb_protocol_support" #define SDBD_CAP_TYPE_SOCKPROTO "socket_protocol_support" #define SDBD_CAP_TYPE_ROOTONOFF "root_onoff_support" +#define SDBD_CAP_TYPE_ENCRYPTION "encryption_support" #define SDBD_CAP_TYPE_CANLAUNCH "can_launch_target" #define SDBD_CAP_TYPE_PLUGIN_VER "sdbd_plugin_version" #define SDBD_CAP_TYPE_PRODUCT_VER "product_version" diff --git a/src/services.c b/src/services.c index 2478680..f18065e 100644 --- a/src/services.c +++ b/src/services.c @@ -941,6 +941,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 4f3ec83..8b7acd2 100644 --- a/src/sockets.c +++ b/src/sockets.c @@ -315,7 +315,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; @@ -338,11 +348,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 2083fbc..fdc8d0c 100644 --- a/src/transport.c +++ b/src/transport.c @@ -25,6 +25,10 @@ #define TRACE_TAG TRACE_TRANSPORT #include "sdb.h" +#ifdef SUPPORT_ENCRYPT +#include "transport_security.h" +#endif + static void transport_unref(atransport *t); static atransport transport_list = { @@ -284,6 +288,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); @@ -353,6 +366,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..6e196aa --- /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_sdbd_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_sdbd_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_sdbd_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_sdbd_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_sdbd_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_sdbd_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_sdbd_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_sdbd_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_sdbd_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