From 87d8739ecd9b208899528d994921eb08ee9e19db Mon Sep 17 00:00:00 2001 From: Nick Peng Date: Mon, 11 Feb 2019 02:36:05 +0800 Subject: [PATCH] Resolve tls mode multi-thread issue. --- src/dns_client.c | 3 ++- src/smartdns.c | 2 ++ src/util.c | 64 +++++++++++++++++++++++++++++++++++++++++++++++- src/util.h | 4 +++ 4 files changed, 71 insertions(+), 2 deletions(-) diff --git a/src/dns_client.c b/src/dns_client.c index ec55d35..15ff972 100644 --- a/src/dns_client.c +++ b/src/dns_client.c @@ -52,6 +52,7 @@ #define DNS_TCP_BUFFER (32 * 1024) #define DNS_TCP_IDLE_TIMEOUT (60 * 10) #define DNS_TCP_CONNECT_TIMEOUT (5) +#define DNS_QUERY_TIMEOUT (500) #ifndef TCP_FASTOPEN_CONNECT #define TCP_FASTOPEN_CONNECT 30 @@ -634,7 +635,7 @@ void _dns_client_period_run(void) pthread_mutex_lock(&client.domain_map_lock); list_for_each_entry_safe(query, tmp, &client.dns_request_list, dns_request_list) { - if (now - query->send_tick >= 400 && query->send_tick > 0) { + if (now - query->send_tick >= DNS_QUERY_TIMEOUT && query->send_tick > 0) { list_add(&query->period_list, &check_list); _dns_client_query_get(query); } diff --git a/src/smartdns.c b/src/smartdns.c index 1c69ed6..30ba26a 100644 --- a/src/smartdns.c +++ b/src/smartdns.c @@ -200,12 +200,14 @@ int smartdns_init_ssl(void) SSL_load_error_strings(); SSL_library_init(); OpenSSL_add_all_algorithms(); + SSL_CRYPTO_thread_setup(); return 0; } int smartdns_destroy_ssl(void) { + SSL_CRYPTO_thread_cleanup(); ERR_free_strings(); EVP_cleanup(); diff --git a/src/util.c b/src/util.c index 9bd21d4..834fa73 100644 --- a/src/util.c +++ b/src/util.c @@ -7,6 +7,9 @@ #include #include #include +#include +#include +#include #define NFNL_SUBSYS_IPSET 6 @@ -331,4 +334,63 @@ int ipset_add(const char *ipsetname, const unsigned char addr[], int addr_len) int ipset_del(const char *ipsetname, const unsigned char addr[], int addr_len) { return _ipset_operate(ipsetname, addr, addr_len, IPSET_DEL); -} \ No newline at end of file +} + + +#define THREAD_STACK_SIZE (16*1024) +static pthread_mutex_t *lock_cs; +static long *lock_count; + +void pthreads_locking_callback(int mode, int type, const char *file, int line) +{ + if (mode & CRYPTO_LOCK) { + pthread_mutex_lock(&(lock_cs[type])); + lock_count[type]++; + } else { + pthread_mutex_unlock(&(lock_cs[type])); + } +} + +unsigned long pthreads_thread_id(void) +{ + unsigned long ret; + + ret = (unsigned long)pthread_self(); + return (ret); +} + +void SSL_CRYPTO_thread_setup(void) +{ + int i; + + lock_cs = OPENSSL_malloc(CRYPTO_num_locks() * sizeof(pthread_mutex_t)); + lock_count = OPENSSL_malloc(CRYPTO_num_locks() * sizeof(long)); + if (!lock_cs || !lock_count) { + /* Nothing we can do about this...void function! */ + if (lock_cs) + OPENSSL_free(lock_cs); + if (lock_count) + OPENSSL_free(lock_count); + return; + } + for (i = 0; i < CRYPTO_num_locks(); i++) { + lock_count[i] = 0; + pthread_mutex_init(&(lock_cs[i]), NULL); + } + + CRYPTO_set_id_callback(pthreads_thread_id); + CRYPTO_set_locking_callback(pthreads_locking_callback); +} + +void SSL_CRYPTO_thread_cleanup(void) +{ + int i; + + CRYPTO_set_locking_callback(NULL); + for (i = 0; i < CRYPTO_num_locks(); i++) { + pthread_mutex_destroy(&(lock_cs[i])); + } + OPENSSL_free(lock_cs); + OPENSSL_free(lock_count); +} + diff --git a/src/util.h b/src/util.h index 1621905..624ff64 100644 --- a/src/util.h +++ b/src/util.h @@ -26,4 +26,8 @@ int ipset_add(const char *ipsetname, const unsigned char addr[], int addr_len); int ipset_del(const char *ipsetname, const unsigned char addr[], int addr_len); +void SSL_CRYPTO_thread_setup(void); + +void SSL_CRYPTO_thread_cleanup(void); + #endif \ No newline at end of file