Fix memory leak by creating the SSL context once for ADC client.
This is done using reference counted global memory.
This commit is contained in:
parent
4919aea8d5
commit
d7c8c9426d
|
@ -155,7 +155,7 @@ struct ssl_context_handle* net_ssl_context_create(const char* tls_version, const
|
|||
return (struct ssl_context_handle*) ctx;
|
||||
}
|
||||
|
||||
extern void net_ssl_context_destroy(struct ssl_context_handle* ctx_)
|
||||
void net_ssl_context_destroy(struct ssl_context_handle* ctx_)
|
||||
{
|
||||
struct net_context_openssl* ctx = (struct net_context_openssl*) ctx_;
|
||||
SSL_CTX_free(ctx->ssl);
|
||||
|
@ -266,6 +266,7 @@ ssize_t net_con_ssl_connect(struct net_connection* con)
|
|||
ssize_t net_con_ssl_handshake(struct net_connection* con, enum net_con_ssl_mode ssl_mode, struct ssl_context_handle* ssl_ctx)
|
||||
{
|
||||
uhub_assert(con);
|
||||
uhub_assert(ssl_ctx);
|
||||
|
||||
struct net_context_openssl* ctx = (struct net_context_openssl*) ssl_ctx;
|
||||
struct net_ssl_openssl* handle = (struct net_ssl_openssl*) hub_malloc_zero(sizeof(struct net_ssl_openssl));
|
||||
|
@ -285,7 +286,7 @@ ssize_t net_con_ssl_handshake(struct net_connection* con, enum net_con_ssl_mode
|
|||
}
|
||||
else
|
||||
{
|
||||
handle->ssl = SSL_new(SSL_CTX_new(TLSv1_2_method()));
|
||||
handle->ssl = SSL_new(ctx->ssl);
|
||||
SSL_set_fd(handle->ssl, con->sd);
|
||||
handle->bio = SSL_get_rbio(handle->ssl);
|
||||
con->ssl = (struct ssl_handle*) handle;
|
||||
|
@ -353,6 +354,7 @@ void net_ssl_shutdown(struct net_connection* con)
|
|||
void net_ssl_destroy(struct net_connection* con)
|
||||
{
|
||||
struct net_ssl_openssl* handle = get_handle(con);
|
||||
LOG_TRACE("net_ssl_destroy: %p", con);
|
||||
SSL_free(handle->ssl);
|
||||
hub_free(handle);
|
||||
}
|
||||
|
|
|
@ -27,6 +27,18 @@
|
|||
|
||||
// #define ADCC_DEBUG
|
||||
// #define ADC_CLIENT_DEBUG_PROTO
|
||||
|
||||
struct ADC_client_global
|
||||
{
|
||||
size_t references;
|
||||
#ifdef SSL_SUPPORT
|
||||
struct ssl_context_handle* ctx;
|
||||
#endif
|
||||
};
|
||||
|
||||
static struct ADC_client_global* g_adc_client = NULL;
|
||||
|
||||
|
||||
enum ADC_client_state
|
||||
{
|
||||
ps_none, /* Not connected */
|
||||
|
@ -541,6 +553,17 @@ struct ADC_client* ADC_client_create(const char* nickname, const char* descripti
|
|||
client->recv_queue = ioq_recv_create();
|
||||
|
||||
client->ptr = ptr;
|
||||
|
||||
if (!g_adc_client)
|
||||
{
|
||||
g_adc_client = (struct ADC_client_global*) hub_malloc_zero(sizeof(struct ADC_client_global));
|
||||
#ifdef SSL_SUPPORT
|
||||
g_adc_client->ctx = net_ssl_context_create("1.2", "HIGH");
|
||||
|
||||
#endif
|
||||
}
|
||||
g_adc_client->references++;
|
||||
|
||||
return client;
|
||||
}
|
||||
|
||||
|
@ -556,6 +579,20 @@ void ADC_client_destroy(struct ADC_client* client)
|
|||
hub_free(client->desc);
|
||||
hub_free(client->address.hostname);
|
||||
hub_free(client);
|
||||
|
||||
if (g_adc_client && g_adc_client->references > 0)
|
||||
{
|
||||
g_adc_client->references--;
|
||||
if (!g_adc_client->references)
|
||||
{
|
||||
#ifdef SSL_SUPPORT
|
||||
net_ssl_context_destroy(g_adc_client->ctx);
|
||||
g_adc_client->ctx = NULL;
|
||||
#endif
|
||||
hub_free(g_adc_client);
|
||||
g_adc_client = NULL;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void connect_callback(struct net_connect_handle* handle, enum net_connect_status status, struct net_connection* con, void* ptr)
|
||||
|
@ -622,7 +659,7 @@ static void ADC_client_on_connected(struct ADC_client* client)
|
|||
net_con_update(client->con, NET_EVENT_READ | NET_EVENT_WRITE);
|
||||
client->callback(client, ADC_CLIENT_SSL_HANDSHAKE, 0);
|
||||
ADC_client_set_state(client, ps_conn_ssl);
|
||||
net_con_ssl_handshake(client->con, net_con_ssl_mode_client, NULL);
|
||||
net_con_ssl_handshake(client->con, net_con_ssl_mode_client, g_adc_client->ctx);
|
||||
}
|
||||
else
|
||||
#endif
|
||||
|
|
Loading…
Reference in New Issue