Track SetDigest usage to avoid invalid free under error conditions.

This commit is contained in:
billphipps
2023-03-23 15:46:38 -04:00
parent e0e590f126
commit 9f6388d272
2 changed files with 43 additions and 5 deletions

View File

@@ -4377,24 +4377,28 @@ static void SetDigest(WOLFSSL* ssl, int hashAlgo)
switch (hashAlgo) {
#ifndef NO_SHA
case sha_mac:
ssl->options.dontFreeDigest=1;
ssl->buffers.digest.buffer = ssl->hsHashes->certHashes.sha;
ssl->buffers.digest.length = WC_SHA_DIGEST_SIZE;
break;
#endif /* !NO_SHA */
#ifndef NO_SHA256
case sha256_mac:
ssl->options.dontFreeDigest=1;
ssl->buffers.digest.buffer = ssl->hsHashes->certHashes.sha256;
ssl->buffers.digest.length = WC_SHA256_DIGEST_SIZE;
break;
#endif /* !NO_SHA256 */
#ifdef WOLFSSL_SHA384
case sha384_mac:
ssl->options.dontFreeDigest=1;
ssl->buffers.digest.buffer = ssl->hsHashes->certHashes.sha384;
ssl->buffers.digest.length = WC_SHA384_DIGEST_SIZE;
break;
#endif /* WOLFSSL_SHA384 */
#ifdef WOLFSSL_SHA512
case sha512_mac:
ssl->options.dontFreeDigest=1;
ssl->buffers.digest.buffer = ssl->hsHashes->certHashes.sha512;
ssl->buffers.digest.length = WC_SHA512_DIGEST_SIZE;
break;
@@ -7530,9 +7534,12 @@ void FreeKeyExchange(WOLFSSL* ssl)
/* Cleanup digest buffer */
if (ssl->buffers.digest.buffer) {
XFREE(ssl->buffers.digest.buffer, ssl->heap, DYNAMIC_TYPE_DIGEST);
if(!ssl->options.dontFreeDigest) {
XFREE(ssl->buffers.digest.buffer, ssl->heap, DYNAMIC_TYPE_DIGEST);
}
ssl->buffers.digest.buffer = NULL;
ssl->buffers.digest.length = 0;
ssl->options.dontFreeDigest=0;
}
/* Free handshake key */
@@ -26216,6 +26223,14 @@ static int HashSkeData(WOLFSSL* ssl, enum wc_HashType hashType,
ssl->buffers.digest.length = (unsigned int)digest_sz;
/* buffer for hash */
if(!ssl->buffers.digest.buffer) {
if(!ssl->options.dontFreeDigest) {
XFREE(ssl->buffers.digest.buffer, ssl->heap,
DYNAMIC_TYPE_DIGEST);
}
}
ssl->options.dontFreeDigest=0;
ssl->buffers.digest.buffer = (byte*)XMALLOC(ssl->buffers.digest.length,
ssl->heap, DYNAMIC_TYPE_DIGEST);
if (ssl->buffers.digest.buffer == NULL) {
@@ -30454,8 +30469,16 @@ exit_scv:
#endif /* WOLFSSL_ASYNC_IO */
/* Digest is not allocated, so do this to prevent free */
if(ssl->buffers.digest.buffer) {
if(!ssl->options.dontFreeDigest) {
/*This should not happen*/
XFREE(ssl->buffers.digest.buffer,
ssl->heap, DYNAMIC_TYPE_DIGEST);
}
}
ssl->buffers.digest.buffer = NULL;
ssl->buffers.digest.length = 0;
ssl->options.dontFreeDigest=0;
/* Final cleanup */
#ifdef WOLFSSL_ASYNC_IO
@@ -31938,8 +31961,11 @@ static int DoSessionTicket(WOLFSSL* ssl, const byte* input, word32* inOutIdx,
TypeHash(ssl->options.hashAlgo));
/* Replace sig buffer with new one */
XFREE(ssl->buffers.digest.buffer, ssl->heap,
DYNAMIC_TYPE_DIGEST);
if(!ssl->options.dontFreeDigest) {
XFREE(ssl->buffers.digest.buffer,
ssl->heap, DYNAMIC_TYPE_DIGEST);
}
ssl->options.dontFreeDigest=0;
ssl->buffers.digest.buffer = encodedSig;
}
@@ -32156,8 +32182,11 @@ static int DoSessionTicket(WOLFSSL* ssl, const byte* input, word32* inOutIdx,
TypeHash(ssl->options.hashAlgo));
/* Replace sig buffer with new one */
XFREE(ssl->buffers.digest.buffer, ssl->heap,
DYNAMIC_TYPE_DIGEST);
if(!ssl->options.dontFreeDigest) {
XFREE(ssl->buffers.digest.buffer,
ssl->heap, DYNAMIC_TYPE_DIGEST);
}
ssl->options.dontFreeDigest=0;
ssl->buffers.digest.buffer = encodedSig;
}
break;
@@ -34246,8 +34275,16 @@ static int DoSessionTicket(WOLFSSL* ssl, const byte* input, word32* inOutIdx,
SendAlert(ssl, alert_fatal, bad_certificate);
#endif
/* Digest is not allocated, so do this to prevent free */
if(ssl->buffers.digest.buffer) {
if(!ssl->options.dontFreeDigest) {
/*This should not happen*/
XFREE(ssl->buffers.digest.buffer,
ssl->heap, DYNAMIC_TYPE_DIGEST);
}
}
ssl->buffers.digest.buffer = NULL;
ssl->buffers.digest.length = 0;
ssl->options.dontFreeDigest=0;
#ifdef WOLFSSL_ASYNC_CRYPT
/* Cleanup async */

View File

@@ -4312,6 +4312,7 @@ struct Options {
word16 saveArrays:1; /* save array Memory for user get keys
or psk */
word16 weOwnRng:1; /* will be true unless CTX owns */
word16 dontFreeDigest:1; /* when true, we used SetDigest */
word16 haveEMS:1; /* using extended master secret */
#ifdef HAVE_POLY1305
word16 oldPoly:1; /* set when to use old rfc way of poly*/