Fix for single threaded case with double free on suites.

This commit is contained in:
David Garske
2019-02-26 11:03:02 -08:00
parent efc1ab8c42
commit a3af2fc960
4 changed files with 144 additions and 2 deletions
+16 -2
View File
@@ -4833,7 +4833,15 @@ int InitSSL(WOLFSSL* ssl, WOLFSSL_CTX* ctx, int writeDup)
WOLFSSL_MSG("Suites Memory error");
return MEMORY_E;
}
#ifdef SINGLE_THREADED
ssl->options.ownSuites = 1;
#endif
}
#ifdef SINGLE_THREADED
else {
ssl->options.ownSuites = 0;
}
#endif
}
/* Initialize SSL with the appropriate fields from it's ctx */
@@ -5192,9 +5200,13 @@ void SSL_ResourceFree(WOLFSSL* ssl)
XFREE(ssl->rng, ssl->heap, DYNAMIC_TYPE_RNG);
}
#ifdef SINGLE_THREADED
if (ssl->suites != ssl->ctx->suites)
if (ssl->options.ownSuites)
#endif
{
XFREE(ssl->suites, ssl->heap, DYNAMIC_TYPE_SUITES);
}
ssl->suites = NULL;
FreeHandshakeHashes(ssl);
XFREE(ssl->buffers.domainName.buffer, ssl->heap, DYNAMIC_TYPE_DOMAIN);
@@ -5416,9 +5428,11 @@ void FreeHandshakeResources(WOLFSSL* ssl)
{
/* suites */
#ifdef SINGLE_THREADED
if (ssl->suites != ssl->ctx->suites)
if (ssl->options.ownSuites)
#endif
{
XFREE(ssl->suites, ssl->heap, DYNAMIC_TYPE_SUITES);
}
ssl->suites = NULL;
/* hsHashes */
+12
View File
@@ -8728,6 +8728,18 @@ int wolfSSL_CTX_set_cipher_list(WOLFSSL_CTX* ctx, const char* list)
int wolfSSL_set_cipher_list(WOLFSSL* ssl, const char* list)
{
WOLFSSL_ENTER("wolfSSL_set_cipher_list");
#ifdef SINGLE_THREADED
if (ssl->ctx->suites == ssl->suites) {
ssl->suites = (Suites*)XMALLOC(sizeof(Suites), ssl->heap,
DYNAMIC_TYPE_SUITES);
if (ssl->suites == NULL) {
WOLFSSL_MSG("Suites Memory error");
return MEMORY_E;
}
ssl->options.ownSuites = 1;
}
#endif
return (SetCipherList(ssl->ctx, ssl->suites, list)) ? WOLFSSL_SUCCESS : WOLFSSL_FAILURE;
}
+112
View File
@@ -607,6 +607,114 @@ static void test_wolfSSL_CTX_new(WOLFSSL_METHOD *method)
}
#endif
#if (!defined(NO_WOLFSSL_CLIENT) || !defined(NO_WOLFSSL_SERVER)) && \
(!defined(NO_RSA) || defined(HAVE_ECC))
static void test_for_double_Free(void)
{
WOLFSSL_CTX* ctx;
WOLFSSL* ssl;
int skipTest = 0;
const char* testCertFile;
const char* testKeyFile;
char optionsCiphers[] = "RC4-SHA:RC4-MD5:DES-CBC3-SHA:AES128-SHA:AES256-SHA"
":NULL-SHA:NULL-SHA256:DHE-RSA-AES128-SHA:DHE-RSA-AES256-SHA:DHE-PSK-AES256-GCM"
"-SHA384:DHE-PSK-AES128-GCM-SHA256:PSK-AES256-GCM-SHA384:PSK-AES128-GCM-SHA256:"
"DHE-PSK-AES256-CBC-SHA384:DHE-PSK-AES128-CBC-SHA256:PSK-AES256-CBC-SHA384:PSK-"
"AES128-CBC-SHA256:PSK-AES128-CBC-SHA:PSK-AES256-CBC-SHA:DHE-PSK-AES128-CCM:DHE"
"-PSK-AES256-CCM:PSK-AES128-CCM:PSK-AES256-CCM:PSK-AES128-CCM-8:PSK-AES256-CCM-"
"8:DHE-PSK-NULL-SHA384:DHE-PSK-NULL-SHA256:PSK-NULL-SHA384:PSK-NULL-SHA256:PSK-"
"NULL-SHA:HC128-MD5:HC128-SHA:RABBIT-SHA:AES128-CCM-8:AES256-CCM-8:ECDHE-ECDSA-"
"AES128-CCM:ECDHE-ECDSA-AES128-CCM-8:ECDHE-ECDSA-AES256-CCM-8:ECDHE-RSA-AES128-"
"SHA:ECDHE-RSA-AES256-SHA:ECDHE-ECDSA-AES128-SHA:ECDHE-ECDSA-AES256-SHA:ECDHE-R"
"SA-RC4-SHA:ECDHE-RSA-DES-CBC3-SHA:ECDHE-ECDSA-RC4-SHA:ECDHE-ECDSA-DES-CBC3-SHA"
":AES128-SHA256:AES256-SHA256:DHE-RSA-AES128-SHA256:DHE-RSA-AES256-SHA256:ECDH-"
"RSA-AES128-SHA:ECDH-RSA-AES256-SHA:ECDH-ECDSA-AES128-SHA:ECDH-ECDSA-AES256-SHA"
":ECDH-RSA-RC4-SHA:ECDH-RSA-DES-CBC3-SHA:ECDH-ECDSA-RC4-SHA:ECDH-ECDSA-DES-CBC3"
"-SHA:AES128-GCM-SHA256:AES256-GCM-SHA384:DHE-RSA-AES128-GCM-SHA256:DHE-RSA-AES"
"256-GCM-SHA384:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-E"
"CDSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDH-RSA-AES128-GCM-SHA25"
"6:ECDH-RSA-AES256-GCM-SHA384:ECDH-ECDSA-AES128-GCM-SHA256:ECDH-ECDSA-AES256-GC"
"M-SHA384:CAMELLIA128-SHA:DHE-RSA-CAMELLIA128-SHA:CAMELLIA256-SHA:DHE-RSA-CAMEL"
"LIA256-SHA:CAMELLIA128-SHA256:DHE-RSA-CAMELLIA128-SHA256:CAMELLIA256-SHA256:DH"
"E-RSA-CAMELLIA256-SHA256:ECDHE-RSA-AES128-SHA256:ECDHE-ECDSA-AES128-SHA256:ECD"
"H-RSA-AES128-SHA256:ECDH-ECDSA-AES128-SHA256:ECDHE-RSA-AES256-SHA384:ECDHE-ECD"
"SA-AES256-SHA384:ECDH-RSA-AES256-SHA384:ECDH-ECDSA-AES256-SHA384:ECDHE-RSA-CHA"
"CHA20-POLY1305:ECDHE-ECDSA-CHACHA20-POLY1305:DHE-RSA-CHACHA20-POLY1305:ECDHE-R"
"SA-CHACHA20-POLY1305-OLD:ECDHE-ECDSA-CHACHA20-POLY1305-OLD:DHE-RSA-CHACHA20-PO"
"LY1305-OLD:IDEA-CBC-SHA:ECDHE-ECDSA-NULL-SHA:ECDHE-PSK-NULL-SHA256:ECDHE-PSK-A"
"ES128-CBC-SHA256:PSK-CHACHA20-POLY1305:ECDHE-PSK-CHACHA20-POLY1305:DHE-PSK-CHA"
"CHA20-POLY1305:EDH-RSA-DES-CBC3-SHA:TLS13-AES128-GCM-SHA256:TLS13-AES256-GCM-S"
"HA384:TLS13-CHACHA20-POLY1305-SHA256:TLS13-AES128-CCM-SHA256:TLS13-AES128-CCM-"
"8-SHA256";
#ifndef NO_RSA
testCertFile = svrCertFile;
testKeyFile = svrKeyFile;
#elif defined(HAVE_ECC)
testCertFile = eccCertFile;
testKeyFile = eccKeyFile;
#else
skipTest = 1;
#endif
if (skipTest != 1) {
#ifndef NO_WOLFSSL_SERVER
AssertNotNull(ctx = wolfSSL_CTX_new(wolfSSLv23_server_method()));
#else
AssertNotNull(ctx = wolfSSL_CTX_new(wolfSSLv23_client_method()));
#endif
AssertTrue(wolfSSL_CTX_use_certificate_file(ctx, testCertFile, WOLFSSL_FILETYPE_PEM));
AssertTrue(wolfSSL_CTX_use_PrivateKey_file(ctx, testKeyFile, WOLFSSL_FILETYPE_PEM));
AssertNotNull(ssl = wolfSSL_new(ctx));
/* First test freeing SSL, then CTX */
wolfSSL_free(ssl);
wolfSSL_CTX_free(ctx);
wolfSSL_Cleanup();
#ifndef NO_WOLFSSL_CLIENT
AssertNotNull(ctx = wolfSSL_CTX_new(wolfSSLv23_client_method()));
#else
AssertNotNull(ctx = wolfSSL_CTX_new(wolfSSLv23_server_method()));
#endif
AssertTrue(wolfSSL_CTX_use_certificate_file(ctx, testCertFile, WOLFSSL_FILETYPE_PEM));
AssertTrue(wolfSSL_CTX_use_PrivateKey_file(ctx, testKeyFile, WOLFSSL_FILETYPE_PEM));
AssertNotNull(ssl = wolfSSL_new(ctx));
/* Next test freeing CTX then SSL */
wolfSSL_CTX_free(ctx);
wolfSSL_free(ssl);
#ifndef NO_WOLFSSL_SERVER
AssertNotNull(ctx = wolfSSL_CTX_new(wolfSSLv23_server_method()));
#else
AssertNotNull(ctx = wolfSSL_CTX_new(wolfSSLv23_client_method()));
#endif
/* Test setting ciphers at ctx level */
AssertTrue(wolfSSL_CTX_use_certificate_file(ctx, testCertFile, WOLFSSL_FILETYPE_PEM));
AssertTrue(wolfSSL_CTX_use_PrivateKey_file(ctx, testKeyFile, WOLFSSL_FILETYPE_PEM));
AssertTrue(wolfSSL_CTX_set_cipher_list(ctx, optionsCiphers));
AssertNotNull(ssl = wolfSSL_new(ctx));
wolfSSL_CTX_free(ctx);
wolfSSL_free(ssl);
#ifndef NO_WOLFSSL_CLIENT
AssertNotNull(ctx = wolfSSL_CTX_new(wolfSSLv23_client_method()));
#else
AssertNotNull(ctx = wolfSSL_CTX_new(wolfSSLv23_server_method()));
#endif
AssertTrue(wolfSSL_CTX_use_certificate_file(ctx, testCertFile, WOLFSSL_FILETYPE_PEM));
AssertTrue(wolfSSL_CTX_use_PrivateKey_file(ctx, testKeyFile, WOLFSSL_FILETYPE_PEM));
AssertNotNull(ssl = wolfSSL_new(ctx));
/* test setting ciphers at SSL level */
AssertTrue(wolfSSL_set_cipher_list(ssl, optionsCiphers));
wolfSSL_CTX_free(ctx);
wolfSSL_free(ssl);
}
}
#endif
static void test_wolfSSL_CTX_use_certificate_file(void)
{
@@ -23267,6 +23375,10 @@ void ApiTest(void)
test_wolfSSL_Method_Allocators();
#ifndef NO_WOLFSSL_SERVER
test_wolfSSL_CTX_new(wolfSSLv23_server_method());
#endif
#if (!defined(NO_WOLFSSL_CLIENT) || !defined(NO_WOLFSSL_SERVER)) && \
(!defined(NO_RSA) || defined(HAVE_ECC))
test_for_double_Free();
#endif
test_wolfSSL_CTX_use_certificate_file();
AssertIntEQ(test_wolfSSL_CTX_use_certificate_buffer(), WOLFSSL_SUCCESS);
+4
View File
@@ -3257,6 +3257,10 @@ typedef struct Options {
word16 dhKeyTested:1; /* Set when key has been tested. */
#endif
#endif
#ifdef SINGLE_THREADED
word16 ownSuites:1; /* if suites are malloced in ssl object */
#endif
/* need full byte values for this section */
byte processReply; /* nonblocking resume */
byte cipherSuite0; /* first byte, normally 0 */