diff options
-rw-r--r-- | ssl/record/rec_layer_s3.c | 22 |
1 files changed, 14 insertions, 8 deletions
diff --git a/ssl/record/rec_layer_s3.c b/ssl/record/rec_layer_s3.c index a267889a51..a36ae8d03c 100644 --- a/ssl/record/rec_layer_s3.c +++ b/ssl/record/rec_layer_s3.c @@ -16,6 +16,7 @@ #include <openssl/rand.h> #include "record_local.h" #include "internal/packet.h" +#include "internal/cryptlib.h" #if defined(OPENSSL_SMALL_FOOTPRINT) || \ !( defined(AES_ASM) && ( \ @@ -676,6 +677,14 @@ int ssl3_write_bytes(SSL *s, int type, const void *buf_, size_t len, } } +/* + * Encryption growth may result from padding in CBC ciphersuites (never more + * than SSL_RT_MAX_CIPHER_BLOCK_SIZE bytes), or from an AEAD tag (never more + * than EVP_MAX_MD_SIZE bytes). In the case of stitched ciphersuites growth can + * come from both of these. + */ +#define MAX_ENCRYPTION_GROWTH (EVP_MAX_MD_SIZE + SSL_RT_MAX_CIPHER_BLOCK_SIZE) + int do_ssl3_write(SSL *s, int type, const unsigned char *buf, size_t *pipelens, size_t numpipes, int create_empty_fragment, size_t *written) @@ -1014,15 +1023,9 @@ int do_ssl3_write(SSL *s, int type, const unsigned char *buf, } } - /* - * Reserve some bytes for any growth that may occur during encryption. - * This will be at most one cipher block or the tag length if using - * AEAD. SSL_RT_MAX_CIPHER_BLOCK_SIZE covers either case. - */ + /* Reserve some bytes for any growth that may occur during encryption. */ if (!BIO_get_ktls_send(s->wbio)) { - if (!WPACKET_reserve_bytes(thispkt, - SSL_RT_MAX_CIPHER_BLOCK_SIZE, - NULL) + if (!WPACKET_reserve_bytes(thispkt, MAX_ENCRYPTION_GROWTH, NULL) /* * We also need next the amount of bytes written to this * sub-packet @@ -1074,6 +1077,9 @@ int do_ssl3_write(SSL *s, int type, const unsigned char *buf, /* Allocate bytes for the encryption overhead */ if (!WPACKET_get_length(thispkt, &origlen) + /* Check we allowed enough room for the encryption growth */ + || !ossl_assert(origlen + MAX_ENCRYPTION_GROWTH + >= thiswr->length) /* Encryption should never shrink the data! */ || origlen > thiswr->length || (thiswr->length > origlen |