From 8f1bea264967ff590b889266f1c5fd86a21b44d9 Mon Sep 17 00:00:00 2001 From: bossiel Date: Mon, 8 Mar 2010 18:50:34 +0000 Subject: [PATCH] - Allow end user to set TLS certificates. - Use SSL_pending (after an initial SSL_read) instead of ioctl(FIONREAD) to retrieve # pending bytes. --- trunk/tinyNET/src/tls/tnet_tls.c | 95 +++++++++++++------ trunk/tinyNET/src/tls/tnet_tls.h | 2 +- trunk/tinyNET/src/tnet_transport.c | 7 +- trunk/tinyNET/src/tnet_transport.h | 10 +- trunk/tinyNET/src/tnet_transport_poll.c | 40 ++++---- trunk/tinyNET/src/tnet_transport_win32.c | 27 +++--- trunk/tinyNET/src/tnet_utils.c | 2 +- .../tinysip/transports/tsip_transport.h | 1 + trunk/tinySIP/include/tsip.h | 13 ++- trunk/tinySIP/src/transports/tsip_transport.c | 14 +++ .../src/transports/tsip_transport_ipsec.c | 2 +- .../src/transports/tsip_transport_layer.c | 28 +++--- trunk/tinySIP/src/tsip.c | 33 +++++-- trunk/tinySIP/test/test/test_stack.h | 21 ++-- 14 files changed, 191 insertions(+), 104 deletions(-) diff --git a/trunk/tinyNET/src/tls/tnet_tls.c b/trunk/tinyNET/src/tls/tnet_tls.c index aaed715c..5907f356 100644 --- a/trunk/tinyNET/src/tls/tnet_tls.c +++ b/trunk/tinyNET/src/tls/tnet_tls.c @@ -35,6 +35,7 @@ #include "tsk_memory.h" #include "tsk_debug.h" #include "tsk_safeobj.h" +#include "tsk_thread.h" #define TNET_CIPHER_LIST "AES128-SHA" @@ -154,12 +155,45 @@ int tnet_tls_socket_write(tnet_tls_socket_handle_t* self, const void* data, size /* Write */ tsk_safeobj_lock(socket); ssl_write: - if((rcount--) && ((ret = SSL_write(socket->ssl, data, size)) <= 0)){ + if(rcount && ((ret = SSL_write(socket->ssl, data, size)) <= 0)){ + int want_read; ret = SSL_get_error(socket->ssl, ret); - if(ret == SSL_ERROR_WANT_WRITE || ret == SSL_ERROR_WANT_READ){ - if(!(ret = tnet_sockfd_waitUntil(socket->fd, TNET_TLS_TIMEOUT, (ret == SSL_ERROR_WANT_WRITE)))){ + want_read = (ret == SSL_ERROR_WANT_READ); + + if(ret == SSL_ERROR_WANT_WRITE || want_read){ + + if(!(ret = tnet_sockfd_waitUntil(socket->fd, TNET_TLS_TIMEOUT, !want_read))){ + rcount--; + + if(want_read && !SSL_is_init_finished(socket->ssl)){ + tsk_thread_sleep(200); // FIXME + } goto ssl_write; } + + //if(ret == SSL_ERROR_WANT_READ){ + // if(!SSL_is_init_finished(socket->ssl)){ + // size_t size = 1024; + // char* buffer = tsk_calloc(size, sizeof(uint8_t)); + // int isEncrypted = 1; + // + // // read() + // tsk_safeobj_unlock(socket); + // tnet_tls_socket_recv(socket, &buffer, &size, &isEncrypted); + // TSK_FREE(buffer); + // tsk_safeobj_lock(socket); + // } + // rcount--; + // goto ssl_write; + //} + //else{ + // if(!(ret = tnet_sockfd_waitUntilWritable(socket->fd, TNET_TLS_TIMEOUT))){ + // rcount--; + // goto ssl_write; + // } + // else goto bail; + //} + } else{ TSK_DEBUG_ERROR("SSL_write failed [%d].", ret); @@ -168,17 +202,20 @@ ssl_write: } tsk_safeobj_unlock(socket); +//bail: ret = (ret > 0) ? 0 : -3; return ret; #endif } -int tnet_tls_socket_recv(tnet_tls_socket_handle_t* self, void* data, size_t *size, int *isEncrypted) +int tnet_tls_socket_recv(tnet_tls_socket_handle_t* self, void** data, size_t *size, int *isEncrypted) { #if !TNET_HAVE_OPENSSL_H return -200; #else int ret = -1; + size_t read = 0; + size_t to_read = *size; int rcount = TNET_TLS_RETRY_COUNT; tnet_tls_socket_t* socket; @@ -217,10 +254,11 @@ int tnet_tls_socket_recv(tnet_tls_socket_handle_t* self, void* data, size_t *siz /* Read Application data */ ssl_read: - if((rcount--) && ((ret = SSL_read(socket->ssl, data, *size)) <= 0)){ + if(rcount && ((ret = SSL_read(socket->ssl, (((uint8_t*)*data)+read), to_read)) <= 0)){ ret = SSL_get_error(socket->ssl, ret); if(ret == SSL_ERROR_WANT_WRITE || ret == SSL_ERROR_WANT_READ){ if(!(ret = tnet_sockfd_waitUntil(socket->fd, TNET_TLS_TIMEOUT, (ret == SSL_ERROR_WANT_WRITE)))){ + rcount--; goto ssl_read; } } @@ -233,16 +271,30 @@ ssl_read: TSK_DEBUG_ERROR("SSL_read failed [%d].", ret); } } - else{ - *size = ret; - ret = 0; + else if(ret >=0){ + read += (size_t)ret; + + if((ret = SSL_pending(socket->ssl)) > 0){ + void *ptr; + to_read = ret; + + if((ptr = tsk_realloc(*data, (read + to_read)))){ + *data = ptr; + goto ssl_read; + } + } } - return 0; bail: tsk_safeobj_unlock(socket); - - return ret; + + if(read){ + *size = read; + return 0; + } + else{ + return ret; + } #endif } @@ -258,23 +310,8 @@ int tnet_tls_socket_init(tnet_tls_socket_t* socket) } /* Sets SSL method */ - if(socket->isClient){ - if(socket->mutual_auth){ - socket->ssl_meth = SSLv23_client_method(); - } - else{ - socket->ssl_meth = TLSv1_client_method()/*SSLv23_client_method()*/; - } - } - else{ - if(socket->mutual_auth){ - socket->ssl_meth = SSLv23_server_method(); - } - else{ - socket->ssl_meth = TLSv1_server_method(); - } - } - + socket->ssl_meth = socket->isClient ? TLSv1_client_method() : SSLv23_server_method(); + /* Creates the context */ if(!(socket->ssl_ctx = SSL_CTX_new(socket->ssl_meth))){ return -3; @@ -374,9 +411,9 @@ static void* tnet_tls_socket_create(void * self, va_list * app) /* Initialize SSL: http://www.openssl.org/docs/ssl/SSL_library_init.html */ #if TNET_HAVE_OPENSSL_H if(!__ssl_initialized){ + __ssl_initialized = 1; SSL_library_init(); SSL_load_error_strings(); - __ssl_initialized = 1; } #endif /* Initialize the socket itself: CTX, method, ... */ diff --git a/trunk/tinyNET/src/tls/tnet_tls.h b/trunk/tinyNET/src/tls/tnet_tls.h index 1a56f705..69ac7c5a 100644 --- a/trunk/tinyNET/src/tls/tnet_tls.h +++ b/trunk/tinyNET/src/tls/tnet_tls.h @@ -48,7 +48,7 @@ int tnet_tls_socket_isok(const tnet_tls_socket_handle_t* self); int tnet_tls_socket_connect(tnet_tls_socket_handle_t* self); int tnet_tls_socket_write(tnet_tls_socket_handle_t* self, const void* data, size_t size); #define tnet_tls_socket_send(self, data, size) tnet_tls_socket_write(self, data, size) -int tnet_tls_socket_recv(tnet_tls_socket_handle_t* self, void* data, size_t *size, int *isEncrypted); +int tnet_tls_socket_recv(tnet_tls_socket_handle_t* self, void** data, size_t *size, int *isEncrypted); TINYNET_GEXTERN const void *tnet_tls_socket_def_t; diff --git a/trunk/tinyNET/src/tnet_transport.c b/trunk/tinyNET/src/tnet_transport.c index 7dcf7f8d..eab96939 100644 --- a/trunk/tinyNET/src/tnet_transport.c +++ b/trunk/tinyNET/src/tnet_transport.c @@ -191,7 +191,7 @@ tnet_fd_t tnet_transport_connectto(const tnet_transport_handle_t *handle, const } else{ if(TNET_SOCKET_TYPE_IS_TLS(type)){ - transport->have_tls = 1; + transport->tls.have_tls = 1; transport->connected = !tnet_tls_socket_connect((tnet_tls_socket_handle_t*)tnet_transport_get_tlshandle(handle, fd)); // FIXME: the transport itself not connected } else{ @@ -302,6 +302,11 @@ static void* tnet_transport_destroy(void * self) TSK_OBJECT_SAFE_FREE(transport->master); TSK_OBJECT_SAFE_FREE(transport->context); TSK_FREE(transport->description); + + // tls + TSK_FREE(transport->tls.ca); + TSK_FREE(transport->tls.pbk); + TSK_FREE(transport->tls.pvk); } return self; diff --git a/trunk/tinyNET/src/tnet_transport.h b/trunk/tinyNET/src/tnet_transport.h index d7d1fab0..14a5e246 100644 --- a/trunk/tinyNET/src/tnet_transport.h +++ b/trunk/tinyNET/src/tnet_transport.h @@ -113,10 +113,12 @@ typedef struct tnet_transport_s const void* callback_data; /* TLS certs */ - char* tlsfile_ca; - char* tlsfile_pvk; - char* tlsfile_pbk; - unsigned have_tls:1; + struct { + char* ca; + char* pvk; + char* pbk; + unsigned have_tls:1; + }tls; } tnet_transport_t; diff --git a/trunk/tinyNET/src/tnet_transport_poll.c b/trunk/tinyNET/src/tnet_transport_poll.c index c7884089..eb009c94 100644 --- a/trunk/tinyNET/src/tnet_transport_poll.c +++ b/trunk/tinyNET/src/tnet_transport_poll.c @@ -70,7 +70,7 @@ typedef struct transport_context_s transport_context_t; static transport_socket_t* getSocket(transport_context_t *context, tnet_fd_t fd); -static void addSocket(tnet_fd_t fd, tnet_socket_type_t type, transport_context_t *context, int take_ownership, int is_client); +static void addSocket(tnet_fd_t fd, tnet_socket_type_t type, tnet_transport_t *transport, int take_ownership, int is_client); static void setConnected(tnet_fd_t fd, transport_context_t *context, int connected); static void removeSocket(int index, transport_context_t *context); @@ -101,7 +101,7 @@ int tnet_transport_isconnected(const tnet_transport_handle_t *handle, tnet_fd_t int tnet_transport_add_socket(const tnet_transport_handle_t *handle, tnet_fd_t fd, tnet_socket_type_t type, int take_ownership, int isClient) { tnet_transport_t *transport = (tnet_transport_t*)handle; - transport_context_t *context; + static char c = '\0'; int ret = -1; if(!transport){ @@ -113,18 +113,16 @@ int tnet_transport_add_socket(const tnet_transport_handle_t *handle, tnet_fd_t f transport->have_tls = 1; } - if((context = (transport_context_t*)transport->context)){ - static char c = '\0'; - addSocket(fd, type, context, take_ownership, isClient); - - // signal - ret = write(context->pipeW, &c, 1); - return (ret > 0 ? 0 : ret); - } + static char c = '\0'; + addSocket(fd, type, transport, take_ownership, isClient); - // ... - - return -1; + // signal + if((ret = write(context->pipeW, &c, 1)) > 0){ + return 0; + } + else{ + return ret; + } } /* Remove socket @@ -274,8 +272,9 @@ static transport_socket_t* getSocket(transport_context_t *context, tnet_fd_t fd) } /*== Add new socket ==*/ -void addSocket(tnet_fd_t fd, tnet_socket_type_t type, transport_context_t *context, int take_ownership, int is_client) +void addSocket(tnet_fd_t fd, tnet_socket_type_t type, tnet_transport_t *transport, int take_ownership, int is_client) { + transport_context_t *context = transport?transport->context:0; if(context){ transport_socket_t *sock = tsk_calloc(1, sizeof(transport_socket_t)); sock->fd = fd; @@ -283,7 +282,7 @@ void addSocket(tnet_fd_t fd, tnet_socket_type_t type, transport_context_t *conte sock->owner = take_ownership ? 1 : 0; if(TNET_SOCKET_TYPE_IS_TLS(sock->type)){ - sock->tlshandle = tnet_sockfd_set_tlsfiles(sock->fd, is_client, 0, 0, 0); + sock->tlshandle = tnet_sockfd_set_tlsfiles(sock->fd, is_client, transport->tls.ca, transport->tls.pvk, transport->tls.pbk); } tsk_safeobj_lock(context); @@ -408,10 +407,10 @@ void *tnet_transport_mainthread(void *param) context->pipeR = pipes[0]; context->pipeW = pipes[1]; - addSocket(context->pipeR, transport->master->type, context, 1, 0); + addSocket(context->pipeR, transport->master->type, transport, 1, 0); /* Add the master socket to the context. */ - addSocket(transport->master->fd, transport->master->type, context, 1, 0); + addSocket(transport->master->fd, transport->master->type, transport, 1, 0); /* Set transport to active */ transport->active = 1; @@ -483,15 +482,12 @@ void *tnet_transport_mainthread(void *param) if(active_socket->tlshandle){ int isEncrypted; size_t tlslen = len; - if(!(ret = tnet_tls_socket_recv(active_socket->tlshandle, buffer, &tlslen, &isEncrypted))){ + if(!(ret = tnet_tls_socket_recv(active_socket->tlshandle, &buffer, &tlslen, &isEncrypted))){ if(isEncrypted){ TSK_FREE(buffer); continue; } - else if(tlslen != len){ - len = tlslen; - buffer = tsk_realloc(buffer, tlslen); - } + len = tlslen; } } else if((ret = recv(active_socket->fd, buffer, len, 0)) < 0) diff --git a/trunk/tinyNET/src/tnet_transport_win32.c b/trunk/tinyNET/src/tnet_transport_win32.c index a1d15a37..c610686e 100644 --- a/trunk/tinyNET/src/tnet_transport_win32.c +++ b/trunk/tinyNET/src/tnet_transport_win32.c @@ -63,7 +63,7 @@ typedef struct transport_context_s transport_context_t; static transport_socket_t* getSocket(transport_context_t *context, tnet_fd_t fd); -static void addSocket(tnet_fd_t fd, tnet_socket_type_t type, transport_context_t *context, int take_ownership, int is_client); +static void addSocket(tnet_fd_t fd, tnet_socket_type_t type, tnet_transport_t *transport, int take_ownership, int is_client); static void removeSocket(int index, transport_context_t *context); /* Checks if socket is connected */ @@ -125,7 +125,7 @@ const tnet_tls_socket_handle_t* tnet_transport_get_tlshandle(const tnet_transpor int tnet_transport_add_socket(const tnet_transport_handle_t *handle, tnet_fd_t fd, tnet_socket_type_t type, int take_ownership, int isClient) { tnet_transport_t *transport = (tnet_transport_t*)handle; - transport_context_t *context; + transport_context_t* context; int ret = -1; if(!transport){ @@ -139,10 +139,10 @@ int tnet_transport_add_socket(const tnet_transport_handle_t *handle, tnet_fd_t f } if(TNET_SOCKET_TYPE_IS_TLS(type)){ - transport->have_tls = 1; + transport->tls.have_tls = 1; } - addSocket(fd, type, context, take_ownership, isClient); + addSocket(fd, type, transport, take_ownership, isClient); if(WSAEventSelect(fd, context->events[context->count - 1], FD_ALL_EVENTS) == SOCKET_ERROR){ removeSocket((context->count - 1), context); TNET_PRINT_LAST_ERROR("WSAEventSelect have failed."); @@ -215,7 +215,7 @@ size_t tnet_transport_send(const tnet_transport_handle_t *handle, tnet_fd_t from goto bail; } - if(transport->have_tls){ + if(transport->tls.have_tls){ transport_socket_t* socket = getSocket(transport->context, from); if(socket && socket->tlshandle){ if(!tnet_tls_socket_send(socket->tlshandle, buf, size)){ @@ -325,8 +325,10 @@ static transport_socket_t* getSocket(transport_context_t *context, tnet_fd_t fd) } /*== Add new socket ==*/ -static void addSocket(tnet_fd_t fd, tnet_socket_type_t type, transport_context_t *context, int take_ownership, int is_client) +static void addSocket(tnet_fd_t fd, tnet_socket_type_t type, tnet_transport_t *transport, int take_ownership, int is_client) { + transport_context_t *context = transport?transport->context:0; + if(context){ transport_socket_t *sock = tsk_calloc(1, sizeof(transport_socket_t)); sock->fd = fd; @@ -334,7 +336,7 @@ static void addSocket(tnet_fd_t fd, tnet_socket_type_t type, transport_context_t sock->owner = take_ownership ? 1 : 0; if(TNET_SOCKET_TYPE_IS_TLS(sock->type)){ - sock->tlshandle = tnet_sockfd_set_tlsfiles(sock->fd, is_client, 0, 0, 0); + sock->tlshandle = tnet_sockfd_set_tlsfiles(sock->fd, is_client, transport->tls.ca, transport->tls.pvk, transport->tls.pbk); } tsk_safeobj_lock(context); @@ -425,7 +427,7 @@ void *tnet_transport_mainthread(void *param) } /* Add the current transport socket to the context. */ - addSocket(transport->master->fd, transport->master->type, context, 1, 0); + addSocket(transport->master->fd, transport->master->type, transport, 1, 0); if(ret = WSAEventSelect(transport->master->fd, context->events[context->count - 1], TNET_SOCKET_TYPE_IS_DGRAM(transport->master->type) ? FD_READ : FD_ALL_EVENTS/*FD_ACCEPT | FD_READ | FD_CONNECT | FD_CLOSE*/) == SOCKET_ERROR) { TNET_PRINT_LAST_ERROR("WSAEventSelect have failed."); @@ -478,7 +480,7 @@ void *tnet_transport_mainthread(void *param) if((fd = WSAAccept(active_socket->fd, NULL, NULL, AcceptCondFunc, (DWORD_PTR)context)) != INVALID_SOCKET) { /* Add the new fd to the server context */ - addSocket(fd, transport->master->type, context, 1, 0); + addSocket(fd, transport->master->type, transport, 1, 0); if(WSAEventSelect(fd, context->events[context->count - 1], FD_READ | FD_WRITE | FD_CLOSE) == SOCKET_ERROR) { removeSocket((context->count - 1), context); @@ -547,15 +549,12 @@ void *tnet_transport_mainthread(void *param) if(active_socket->tlshandle){ int isEncrypted; size_t len = wsaBuffer.len; - if(!(ret = tnet_tls_socket_recv(active_socket->tlshandle, wsaBuffer.buf, &len, &isEncrypted))){ + if(!(ret = tnet_tls_socket_recv(active_socket->tlshandle, &wsaBuffer.buf, &len, &isEncrypted))){ if(isEncrypted){ TSK_FREE(wsaBuffer.buf); continue; } - else if(len != wsaBuffer.len){ - wsaBuffer.len = len; - wsaBuffer.buf = tsk_realloc(wsaBuffer.buf, len); - } + wsaBuffer.len = len; } } else{ diff --git a/trunk/tinyNET/src/tnet_utils.c b/trunk/tinyNET/src/tnet_utils.c index 6b14af4d..53daff69 100644 --- a/trunk/tinyNET/src/tnet_utils.c +++ b/trunk/tinyNET/src/tnet_utils.c @@ -1167,7 +1167,7 @@ int tnet_sockfd_close(tnet_fd_t *fd) ret = close(*fd); #endif - *fd = TNET_INVALID_SOCKET; + *fd = TNET_INVALID_FD; return ret; } diff --git a/trunk/tinySIP/include/tinysip/transports/tsip_transport.h b/trunk/tinySIP/include/tinysip/transports/tsip_transport.h index bfde78e2..a36d2282 100644 --- a/trunk/tinySIP/include/tinysip/transports/tsip_transport.h +++ b/trunk/tinySIP/include/tinysip/transports/tsip_transport.h @@ -76,6 +76,7 @@ typedef tsk_list_t tsip_transports_L_t; /**< List of @ref tsip_transport_t eleme int tsip_transport_init(tsip_transport_t* self, tnet_socket_type_t type, const tsip_stack_handle_t *stack, const char *host, tnet_port_t port, const char* description); int tsip_transport_deinit(tsip_transport_t* self); +int tsip_transport_set_tlscerts(tsip_transport_t *self, const char* ca, const char* pbk, const char* pvk); size_t tsip_transport_send(const tsip_transport_t* self, const char *branch, tsip_message_t *msg, const char* destIP, int32_t destPort); tsip_uri_t* tsip_transport_get_uri(const tsip_transport_t *self, int lr); diff --git a/trunk/tinySIP/include/tsip.h b/trunk/tinySIP/include/tsip.h index 37cb3ac7..02bbb0f6 100644 --- a/trunk/tinySIP/include/tsip.h +++ b/trunk/tinySIP/include/tsip.h @@ -54,6 +54,7 @@ typedef uint8_t amf_t[2]; typedef uint8_t operator_id_t[16]; typedef void tsip_stack_handle_t; +// Only for internal use #define TSIP_STACK(self) ((tsip_stack_t*)(self)) typedef enum tsip_stack_param_type_e @@ -100,8 +101,11 @@ typedef enum tsip_stack_param_type_e /* Security */ pname_secagree_ipsec, + pname_secagree_tls, + pname_tls_certs, #define TSIP_STACK_SET_SECAGREE_IPSEC(ALG_STR, EALG_STR, MODE_STR, PROTOCOL_STR) pname_secagree_ipsec, (const char*)ALG_STR, (const char*)EALG_STR, (const char*)MODE_STR, (const char*)PROTOCOL_STR - +#define TSIP_STACK_SET_SECAGREE_TLS(USE_TLS_SECAGREE_INT) pname_secagree_tls, (int)USE_TLS_SECAGREE_INT +#define TSIP_STACK_SET_TLS_CERTS(CA_FILE_STR, PUB_FILE_STR, PRIV_FILE_STR) pname_tls_certs, (const char*)CA_FILE_STR, (const char*)PUB_FILE_STR, (const char*)PRIV_FILE_STR /* Features */ pname_enable_100rel, @@ -158,12 +162,19 @@ typedef struct tsip_stack_s /* Security */ char* secagree_mech; + unsigned enable_secagree_tls:1; + unsigned enable_secagree_ipsec:1; struct{ char* alg; char* ealg; char* mode; char* protocol; } secagree_ipsec; + struct { + char* ca; + char* pbk; + char* pvk; + }tls; /* DNS */ tnet_dns_ctx_t *dns_ctx; diff --git a/trunk/tinySIP/src/transports/tsip_transport.c b/trunk/tinySIP/src/transports/tsip_transport.c index 5782ef2c..f4b92c51 100644 --- a/trunk/tinySIP/src/transports/tsip_transport.c +++ b/trunk/tinySIP/src/transports/tsip_transport.c @@ -120,6 +120,20 @@ int tsip_transport_msg_update(const tsip_transport_t* self, tsip_message_t *msg) return ret; } +int tsip_transport_set_tlscerts(tsip_transport_t *self, const char* ca, const char* pbk, const char* pvk) +{ + tnet_transport_t *transport = self->net_transport; + + if(!self || !transport){ + return -1; + } + + tsk_strupdate(&transport->tls.ca, ca); + tsk_strupdate(&transport->tls.pvk, pvk); + tsk_strupdate(&transport->tls.pbk, pbk); + + return 0; +} size_t tsip_transport_send(const tsip_transport_t* self, const char *branch, tsip_message_t *msg, const char* destIP, int32_t destPort) { diff --git a/trunk/tinySIP/src/transports/tsip_transport_ipsec.c b/trunk/tinySIP/src/transports/tsip_transport_ipsec.c index 39cd06a2..1402edd8 100644 --- a/trunk/tinySIP/src/transports/tsip_transport_ipsec.c +++ b/trunk/tinySIP/src/transports/tsip_transport_ipsec.c @@ -243,7 +243,7 @@ int tsip_transport_ipsec_updateMSG(tsip_transport_ipsec_t* self, tsip_message_t goto bail; } - asso = self->asso_temporary ? self->asso_temporary : self->asso_active; + asso = (self->asso_temporary && msg->request_type == tsip_REGISTER) ? self->asso_temporary : self->asso_active; if(!asso || !asso->ctx){ TSK_DEBUG_ERROR("No IPSec association found."); ret = -2; diff --git a/trunk/tinySIP/src/transports/tsip_transport_layer.c b/trunk/tinySIP/src/transports/tsip_transport_layer.c index 73563243..1215a399 100644 --- a/trunk/tinySIP/src/transports/tsip_transport_layer.c +++ b/trunk/tinySIP/src/transports/tsip_transport_layer.c @@ -101,17 +101,17 @@ static int tsip_transport_layer_stream_cb(const tnet_transport_event_t* e) /* Append new content. */ tsk_buffer_append(transport->buff_stream, e->data, e->size); - + /* Check if we have all SIP headers. */ if((endOfheaders = tsk_strindexOf(TSK_BUFFER_DATA(transport->buff_stream),TSK_BUFFER_SIZE(transport->buff_stream), "\r\n\r\n"/*2CRLF*/)) < 0){ TSK_DEBUG_INFO("No all SIP headers in the TCP buffer."); goto bail; } - + /* If we are there this mean that we have all SIP headers. * ==> Parse the SIP message without the content. */ - tsk_ragel_state_init(&state, e->data, e->size); + tsk_ragel_state_init(&state, TSK_BUFFER_DATA(transport->buff_stream), endOfheaders + 4/*2CRLF*/); if(tsip_message_parse(&state, &message, TSIP_FALSE/* do not extract the content */) == TSIP_TRUE && message->firstVia && message->Call_ID && message->CSeq && message->From && message->To) { @@ -133,10 +133,13 @@ static int tsip_transport_layer_stream_cb(const tnet_transport_event_t* e) } } - /* Handle the incoming message. */ - ret = tsip_transport_layer_handle_incoming_msg(transport, message); - /* Set fd */ - message->sockfd = e->fd; + if(message){ + /* Handle the incoming message. */ + ret = tsip_transport_layer_handle_incoming_msg(transport, message); + /* Set fd */ + message->sockfd = e->fd; + } + else ret = -15; bail: TSK_OBJECT_SAFE_FREE(message); @@ -327,14 +330,15 @@ int tsip_transport_layer_add(tsip_transport_layer_t* self, const char* local_hos TSIP_TRANSPORT_IPSEC_CREATE(self->stack, local_host, local_port, type, description) /* IPSec is a special case. All other are ok. */ : TSIP_TRANSPORT_CREATE(self->stack, local_host, local_port, type, description); /* UDP, SCTP, TCP, TLS */ - if(transport) - { + if(transport && transport->net_transport && self->stack){ + /* Set TLS certs */ + if(TNET_SOCKET_TYPE_IS_TLS(type) || TSIP_STACK(self->stack)->enable_secagree_tls){ + tsip_transport_set_tlscerts(transport, TSIP_STACK(self->stack)->tls.ca, TSIP_STACK(self->stack)->tls.pbk, TSIP_STACK(self->stack)->tls.pvk); + } tsk_list_push_back_data(self->transports, (void**)&transport); return 0; } - else - { - //TSK_OBJECT_SAFE_FREE(transport); + else { return -2; } } diff --git a/trunk/tinySIP/src/tsip.c b/trunk/tinySIP/src/tsip.c index 5f1e84b1..878cf60a 100644 --- a/trunk/tinySIP/src/tsip.c +++ b/trunk/tinySIP/src/tsip.c @@ -204,14 +204,27 @@ int __tsip_stack_set(tsip_stack_t *self, va_list values) * Security */ case pname_secagree_ipsec: - { - tsk_strupdate(&self->secagree_mech, "ipsec-3gpp"); - tsk_strupdate(&self->secagree_ipsec.alg, va_arg(values, const char*)); - tsk_strupdate(&self->secagree_ipsec.ealg, va_arg(values, const char*)); - tsk_strupdate(&self->secagree_ipsec.mode, va_arg(values, const char*)); - tsk_strupdate(&self->secagree_ipsec.protocol, va_arg(values, const char*)); - break; - } + { /* ALG_STR, EALG_STR, MODE_STR, PROTOCOL_STR */ + tsk_strupdate(&self->secagree_mech, "ipsec-3gpp"); + tsk_strupdate(&self->secagree_ipsec.alg, va_arg(values, const char*)); + tsk_strupdate(&self->secagree_ipsec.ealg, va_arg(values, const char*)); + tsk_strupdate(&self->secagree_ipsec.mode, va_arg(values, const char*)); + tsk_strupdate(&self->secagree_ipsec.protocol, va_arg(values, const char*)); + self->enable_secagree_ipsec = 1; + break; + } + case pname_secagree_tls: + { /* USE_TLS_SECAGREE_INT */ + self->enable_secagree_tls = va_arg(values, int) ? 1 : 0; + break; + } + case pname_tls_certs: + { /*CA_FILE_STR, PUB_FILE_STR, PRIV_FILE_STR*/ + tsk_strupdate(&self->tls.ca, va_arg(values, const char*)); + tsk_strupdate(&self->tls.pbk, va_arg(values, const char*)); + tsk_strupdate(&self->tls.pvk, va_arg(values, const char*)); + break; + } /* @@ -693,6 +706,10 @@ static void* tsip_stack_destroy(void * self) TSK_FREE(stack->secagree_ipsec.mode); TSK_FREE(stack->secagree_ipsec.protocol); + TSK_FREE(stack->tls.ca); + TSK_FREE(stack->tls.pbk); + TSK_FREE(stack->tls.pvk); + /* DNS */ TSK_OBJECT_SAFE_FREE(stack->dns_ctx); diff --git a/trunk/tinySIP/test/test/test_stack.h b/trunk/tinySIP/test/test/test_stack.h index 59fd8886..a97a75ce 100644 --- a/trunk/tinySIP/test/test/test_stack.h +++ b/trunk/tinySIP/test/test/test_stack.h @@ -223,9 +223,9 @@ int test_stack_callback(const tsip_event_t *sipevent) void test_stack() { -#define DOMAIN "ericsson.com" +//#define DOMAIN "ericsson.com" -//#define DOMAIN "ims.inexbee.com" +#define DOMAIN "ims.inexbee.com" //#define DOMAIN "sip2sip.info" /* @@ -245,7 +245,7 @@ void test_stack() TSIP_STACK_SET_NETINFO("ADSL;utran-cell-id-3gpp=00000000"), TSIP_STACK_SET_PRIVACY("header;id"), */ - +/* tsip_stack_handle_t *stack = tsip_stack_create(test_stack_callback, TSIP_STACK_SET_DISPLAY_NAME("Mamadou"), TSIP_STACK_SET_PUBLIC_IDENTITY("sip:mamadou@"DOMAIN), @@ -262,8 +262,8 @@ void test_stack() TSIP_STACK_SET_DEVICE_ID("dd1289fa-c3d7-47bd-a40d-f1f1b2cc5ffc"), TSIP_STACK_SET_NETINFO("ADSL;utran-cell-id-3gpp=00000000"), TSIP_STACK_SET_PRIVACY("header;id"), +*/ -/* tsip_stack_handle_t *stack = tsip_stack_create(test_stack_callback, TSIP_STACK_SET_DISPLAY_NAME("Mamadou"), TSIP_STACK_SET_PUBLIC_IDENTITY("sip:mamadou@"DOMAIN), @@ -272,15 +272,16 @@ void test_stack() TSIP_STACK_SET_REALM("sip:"DOMAIN), // FIXME: without sip: TSIP_STACK_SET_LOCAL_IP(LOCAL_IP), //TSIP_STACK_SET_DISCOVERY_NAPTR(1), - TSIP_STACK_SET_PROXY_CSCF("pcscf.ims.inexbee.com", "udp", 1), + TSIP_STACK_SET_PROXY_CSCF("pcscf.ims.inexbee.com", "tls", 0), + TSIP_STACK_SET_TLS_CERTS("C:\\tls\\ca.pki-crt.pem", "C:\\tls\\mamadou-crt.pem", "C:\\tls\\mamadou-key.pem"), //TSIP_STACK_SET_PROXY_CSCF("192.168.0.15", "udp", 0), - TSIP_STACK_SET_PROXY_CSCF_PORT(4060), + TSIP_STACK_SET_PROXY_CSCF_PORT(4061), //TSIP_STACK_SET_SECAGREE_IPSEC("hmac-md5-96", "null", "trans", "esp"), TSIP_STACK_SET_MOBILITY("fixed"), TSIP_STACK_SET_DEVICE_ID("dd1289fa-c3d7-47bd-a40d-f1f1b2cc5ffc"), TSIP_STACK_SET_NETINFO("ADSL;utran-cell-id-3gpp=00000000"), TSIP_STACK_SET_PRIVACY("header;id"), -*/ + /* tsip_stack_handle_t *stack = tsip_stack_create(test_stack_callback, TSIP_STACK_SET_DISPLAY_NAME("Mamadou"), @@ -348,7 +349,7 @@ void test_stack() //} /* PUBLISH */ - { + /*{ tsip_operation_handle_t *op4 = TSIP_OPERATION_CREATE(stack, TSIP_OPERATION_SET_HEADER("expires", "30"), TSIP_OPERATION_SET_HEADER("to", "sip:mamadou@"DOMAIN), @@ -359,7 +360,7 @@ void test_stack() TSIP_OPERATION_SET_PARAM("content", TEST_STACK_PIDF), TSIP_OPERATION_SET_NULL()); - tsip_publish(stack, op4); + tsip_publish(stack, op4);*/ // /*getchar(); // tsip_operation_set(op4, @@ -371,7 +372,7 @@ void test_stack() // getchar(); // tsip_operation_hangup(op4); // - } + //} bail: //while(1);//tsk_thread_sleep(500); //while(1)