From b8a56f112f9a1963654796ce76ea3fd9a1e3336f Mon Sep 17 00:00:00 2001 From: David Benjamin Date: Tue, 23 Dec 2014 11:41:02 -0500 Subject: [PATCH] Remove dead code from EVP_CIPHER codepaths. Everything is an AEAD now. Change-Id: Ib47638e128843fc8299c3dbf9bd60c01eb5afa16 Reviewed-on: https://boringssl-review.googlesource.com/2700 Reviewed-by: Adam Langley --- include/openssl/ssl.h | 15 +- include/openssl/ssl3.h | 3 - ssl/CMakeLists.txt | 1 - ssl/d1_lib.c | 2 - ssl/d1_pkt.c | 92 +------ ssl/s3_cbc.c | 601 ---------------------------------------- ssl/s3_lib.c | 1 - ssl/s3_pkt.c | 90 +----- ssl/ssl_ciph.c | 105 ------- ssl/ssl_lib.c | 41 --- ssl/ssl_locl.h | 24 -- ssl/t1_enc.c | 604 ++++++++++------------------------------- ssl/t1_lib.c | 3 - 13 files changed, 155 insertions(+), 1427 deletions(-) delete mode 100644 ssl/s3_cbc.c diff --git a/include/openssl/ssl.h b/include/openssl/ssl.h index 1404be09..e9540381 100644 --- a/include/openssl/ssl.h +++ b/include/openssl/ssl.h @@ -1259,19 +1259,8 @@ struct ssl_st struct ssl_cipher_preference_list_st *cipher_list; STACK_OF(SSL_CIPHER) *cipher_list_by_id; - /* These are the ones being used, the ones in SSL_SESSION are - * the ones to be 'copied' into these ones */ - SSL_AEAD_CTX *aead_read_ctx; /* AEAD context. If non-NULL, then - |enc_read_ctx| and |read_hash| are - ignored. */ - EVP_CIPHER_CTX *enc_read_ctx; /* cryptographic state */ - EVP_MD_CTX *read_hash; /* used for mac generation */ - - SSL_AEAD_CTX *aead_write_ctx; /* AEAD context. If non-NULL, then - |enc_write_ctx| and |write_hash| are - ignored. */ - EVP_CIPHER_CTX *enc_write_ctx; /* cryptographic state */ - EVP_MD_CTX *write_hash; /* used for mac generation */ + SSL_AEAD_CTX *aead_read_ctx; + SSL_AEAD_CTX *aead_write_ctx; /* session info */ diff --git a/include/openssl/ssl3.h b/include/openssl/ssl3.h index ae6c52c4..c502b5a8 100644 --- a/include/openssl/ssl3.h +++ b/include/openssl/ssl3.h @@ -464,10 +464,7 @@ typedef struct ssl3_state_st int key_block_length; unsigned char *key_block; - const EVP_CIPHER *new_sym_enc; const EVP_AEAD *new_aead; - const EVP_MD *new_hash; - int new_mac_pkey_type; uint8_t new_mac_secret_len; uint8_t new_fixed_iv_len; uint8_t new_variable_iv_len; diff --git a/ssl/CMakeLists.txt b/ssl/CMakeLists.txt index 3852d20f..954418b0 100644 --- a/ssl/CMakeLists.txt +++ b/ssl/CMakeLists.txt @@ -14,7 +14,6 @@ add_library( d1_srtp.c d1_srvr.c s3_both.c - s3_cbc.c s3_clnt.c s3_enc.c s3_lib.c diff --git a/ssl/d1_lib.c b/ssl/d1_lib.c index e4928a51..9fcc0501 100644 --- a/ssl/d1_lib.c +++ b/ssl/d1_lib.c @@ -78,7 +78,6 @@ static int dtls1_handshake_write(SSL *s); const SSL3_ENC_METHOD DTLSv1_enc_data = { tls1_enc, - tls1_mac, tls1_prf, tls1_setup_key_block, tls1_generate_master_secret, @@ -98,7 +97,6 @@ const SSL3_ENC_METHOD DTLSv1_enc_data = { const SSL3_ENC_METHOD DTLSv1_2_enc_data = { tls1_enc, - tls1_mac, tls1_prf, tls1_setup_key_block, tls1_generate_master_secret, diff --git a/ssl/d1_pkt.c b/ssl/d1_pkt.c index 85bd3056..451a3c24 100644 --- a/ssl/d1_pkt.c +++ b/ssl/d1_pkt.c @@ -328,15 +328,11 @@ static int dtls1_process_buffered_records(SSL *s) { } static int dtls1_process_record(SSL *s) { - int i, al; + int al; int enc_err; - SSL_SESSION *sess; SSL3_RECORD *rr; - unsigned int mac_size, orig_len; - unsigned char md[EVP_MAX_MD_SIZE]; rr = &(s->s3->rrec); - sess = s->session; /* At this point, s->packet_length == SSL3_RT_HEADER_LNGTH + rr->length, and * we have that many bytes in s->packet. */ @@ -372,55 +368,6 @@ static int dtls1_process_record(SSL *s) { s->packet_length = 0; goto err; } - - /* r->length is now the compressed data plus mac */ - if ((sess != NULL) && (s->enc_read_ctx != NULL) && - (EVP_MD_CTX_md(s->read_hash) != NULL)) { - /* s->read_hash != NULL => mac_size != -1 */ - uint8_t *mac = NULL; - uint8_t mac_tmp[EVP_MAX_MD_SIZE]; - mac_size = EVP_MD_CTX_size(s->read_hash); - assert(mac_size <= EVP_MAX_MD_SIZE); - - /* kludge: *_cbc_remove_padding passes padding length in rr->type */ - orig_len = rr->length + ((unsigned int)rr->type >> 8); - - /* orig_len is the length of the record before any padding was removed. - * This is public information, as is the MAC in use, therefore we can - * safely process the record in a different amount of time if it's too - * short to possibly contain a MAC. */ - if (orig_len < mac_size || - /* CBC records must have a padding length byte too. */ - (EVP_CIPHER_CTX_mode(s->enc_read_ctx) == EVP_CIPH_CBC_MODE && - orig_len < mac_size + 1)) { - al = SSL_AD_DECODE_ERROR; - OPENSSL_PUT_ERROR(SSL, dtls1_process_record, SSL_R_LENGTH_TOO_SHORT); - goto f_err; - } - - if (EVP_CIPHER_CTX_mode(s->enc_read_ctx) == EVP_CIPH_CBC_MODE) { - /* We update the length so that the TLS header bytes can be constructed - * correctly but we need to extract the MAC in constant time from within - * the record, without leaking the contents of the padding bytes. */ - mac = mac_tmp; - ssl3_cbc_copy_mac(mac_tmp, rr, mac_size, orig_len); - rr->length -= mac_size; - } else { - /* In this case there's no padding, so |orig_len| equals |rec->length| - * and we checked that there's enough bytes for |mac_size| above. */ - rr->length -= mac_size; - mac = &rr->data[rr->length]; - } - - i = s->enc_method->mac(s, md, 0 /* not send */); - if (i < 0 || mac == NULL || CRYPTO_memcmp(md, mac, (size_t)mac_size) != 0) { - enc_err = -1; - } - if (rr->length > SSL3_RT_MAX_COMPRESSED_LENGTH + mac_size) { - enc_err = -1; - } - } - if (enc_err < 0) { /* decryption failed, silently discard message */ rr->length = 0; @@ -761,7 +708,9 @@ start: /* make sure that we are not getting application data when we * are doing a handshake for the first time */ if (SSL_in_init(s) && (type == SSL3_RT_APPLICATION_DATA) && - (s->enc_read_ctx == NULL)) { + (s->aead_read_ctx == NULL)) { + /* TODO(davidben): Is this check redundant with the handshake_func + * check? */ al = SSL_AD_UNEXPECTED_MESSAGE; OPENSSL_PUT_ERROR(SSL, dtls1_read_bytes, SSL_R_APP_DATA_IN_HANDSHAKE); goto f_err; @@ -1151,12 +1100,11 @@ int dtls1_write_bytes(SSL *s, int type, const void *buf, int len) { static int do_dtls1_write(SSL *s, int type, const uint8_t *buf, unsigned int len) { uint8_t *p, *pseq; - int i, mac_size = 0; + int i; int prefix_len = 0; int eivlen = 0; SSL3_RECORD *wr; SSL3_BUFFER *wb; - SSL_SESSION *sess; /* first check if there is a SSL3_BUFFER still being written * out. This will happen with non blocking IO */ @@ -1180,15 +1128,6 @@ static int do_dtls1_write(SSL *s, int type, const uint8_t *buf, wr = &(s->s3->wrec); wb = &(s->s3->wbuf); - sess = s->session; - - if (sess != NULL && s->enc_write_ctx != NULL && - EVP_MD_CTX_md(s->write_hash) != NULL) { - mac_size = EVP_MD_CTX_size(s->write_hash); - if (mac_size < 0) { - goto err; - } - } p = wb->buf + prefix_len; @@ -1212,15 +1151,9 @@ static int do_dtls1_write(SSL *s, int type, const uint8_t *buf, pseq = p; p += 10; - /* Explicit IV length, block ciphers appropriate version flag */ - if (s->enc_write_ctx && SSL_USE_EXPLICIT_IV(s) && - EVP_CIPHER_CTX_mode(s->enc_write_ctx) == EVP_CIPH_CBC_MODE) { - eivlen = EVP_CIPHER_CTX_iv_length(s->enc_write_ctx); - if (eivlen <= 1) { - eivlen = 0; - } - } else if (s->aead_write_ctx != NULL && - s->aead_write_ctx->variable_nonce_included_in_record) { + /* Leave room for the variable nonce for AEADs which specify it explicitly. */ + if (s->aead_write_ctx != NULL && + s->aead_write_ctx->variable_nonce_included_in_record) { eivlen = s->aead_write_ctx->variable_nonce_len; } @@ -1233,15 +1166,6 @@ static int do_dtls1_write(SSL *s, int type, const uint8_t *buf, memcpy(wr->data, wr->input, wr->length); wr->input = wr->data; - /* we should still have the output to wr->data and the input from wr->input. - * Length should be wr->length. wr->data still points in the wb->buf */ - if (mac_size != 0) { - if (s->enc_method->mac(s, &(p[wr->length + eivlen]), 1) < 0) { - goto err; - } - wr->length += mac_size; - } - /* this is true regardless of mac size */ wr->input = p; wr->data = p; diff --git a/ssl/s3_cbc.c b/ssl/s3_cbc.c deleted file mode 100644 index 418a04fe..00000000 --- a/ssl/s3_cbc.c +++ /dev/null @@ -1,601 +0,0 @@ -/* ==================================================================== - * Copyright (c) 2012 The OpenSSL Project. All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in - * the documentation and/or other materials provided with the - * distribution. - * - * 3. All advertising materials mentioning features or use of this - * software must display the following acknowledgment: - * "This product includes software developed by the OpenSSL Project - * for use in the OpenSSL Toolkit. (http://www.openssl.org/)" - * - * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to - * endorse or promote products derived from this software without - * prior written permission. For written permission, please contact - * openssl-core@openssl.org. - * - * 5. Products derived from this software may not be called "OpenSSL" - * nor may "OpenSSL" appear in their names without prior written - * permission of the OpenSSL Project. - * - * 6. Redistributions of any form whatsoever must retain the following - * acknowledgment: - * "This product includes software developed by the OpenSSL Project - * for use in the OpenSSL Toolkit (http://www.openssl.org/)" - * - * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY - * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR - * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE OpenSSL PROJECT OR - * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, - * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT - * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; - * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, - * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) - * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED - * OF THE POSSIBILITY OF SUCH DAMAGE. - * ==================================================================== - * - * This product includes cryptographic software written by Eric Young - * (eay@cryptsoft.com). This product includes software written by Tim - * Hudson (tjh@cryptsoft.com). */ - -#include - -#include -#include - -#include "../crypto/internal.h" -#include "ssl_locl.h" - - -/* MAX_HASH_BIT_COUNT_BYTES is the maximum number of bytes in the hash's length - * field. (SHA-384/512 have 128-bit length.) */ -#define MAX_HASH_BIT_COUNT_BYTES 16 - -/* MAX_HASH_BLOCK_SIZE is the maximum hash block size that we'll support. - * Currently SHA-384/512 has a 128-byte block size and that's the largest - * supported by TLS.) */ -#define MAX_HASH_BLOCK_SIZE 128 - -/* ssl3_cbc_remove_padding removes padding from the decrypted, SSLv3, CBC - * record in |rec| by updating |rec->length| in constant time. - * - * block_size: the block size of the cipher used to encrypt the record. - * returns: - * 0: (in non-constant time) if the record is publicly invalid. - * 1: if the padding was valid - * -1: otherwise. */ -int ssl3_cbc_remove_padding(const SSL *s, SSL3_RECORD *rec, unsigned block_size, - unsigned mac_size) { - unsigned padding_length, good; - const unsigned overhead = 1 /* padding length byte */ + mac_size; - - /* These lengths are all public so we can test them in non-constant - * time. */ - if (overhead > rec->length) { - return 0; - } - - padding_length = rec->data[rec->length - 1]; - good = constant_time_ge(rec->length, padding_length + overhead); - /* SSLv3 requires that the padding is minimal. */ - good &= constant_time_ge(block_size, padding_length + 1); - padding_length = good & (padding_length + 1); - rec->length -= padding_length; - rec->type |= padding_length << 8; /* kludge: pass padding length */ - return constant_time_select_int(good, 1, -1); -} - -/* tls1_cbc_remove_padding removes the CBC padding from the decrypted, TLS, CBC - * record in |rec| in constant time and returns 1 if the padding is valid and - * -1 otherwise. It also removes any explicit IV from the start of the record - * without leaking any timing about whether there was enough space after the - * padding was removed. - * - * block_size: the block size of the cipher used to encrypt the record. - * returns: - * 0: (in non-constant time) if the record is publicly invalid. - * 1: if the padding was valid - * -1: otherwise. */ -int tls1_cbc_remove_padding(const SSL *s, SSL3_RECORD *rec, unsigned block_size, - unsigned mac_size) { - unsigned padding_length, good, to_check, i; - const unsigned overhead = 1 /* padding length byte */ + mac_size; - - /* Check if version requires explicit IV */ - if (SSL_USE_EXPLICIT_IV(s)) { - /* These lengths are all public so we can test them in - * non-constant time. */ - if (overhead + block_size > rec->length) { - return 0; - } - /* We can now safely skip explicit IV */ - rec->data += block_size; - rec->input += block_size; - rec->length -= block_size; - } else if (overhead > rec->length) { - return 0; - } - - padding_length = rec->data[rec->length - 1]; - - good = constant_time_ge(rec->length, overhead + padding_length); - /* The padding consists of a length byte at the end of the record and - * then that many bytes of padding, all with the same value as the - * length byte. Thus, with the length byte included, there are i+1 - * bytes of padding. - * - * We can't check just |padding_length+1| bytes because that leaks - * decrypted information. Therefore we always have to check the maximum - * amount of padding possible. (Again, the length of the record is - * public information so we can use it.) */ - to_check = 256; /* maximum amount of padding, inc length byte. */ - if (to_check > rec->length) { - to_check = rec->length; - } - - for (i = 0; i < to_check; i++) { - unsigned char mask = constant_time_ge_8(padding_length, i); - unsigned char b = rec->data[rec->length - 1 - i]; - /* The final |padding_length+1| bytes should all have the value - * |padding_length|. Therefore the XOR should be zero. */ - good &= ~(mask & (padding_length ^ b)); - } - - /* If any of the final |padding_length+1| bytes had the wrong value, - * one or more of the lower eight bits of |good| will be cleared. */ - good = constant_time_eq(0xff, good & 0xff); - - padding_length = good & (padding_length + 1); - rec->length -= padding_length; - rec->type |= padding_length << 8; /* kludge: pass padding length */ - - return constant_time_select_int(good, 1, -1); -} - -/* ssl3_cbc_copy_mac copies |md_size| bytes from the end of |rec| to |out| in - * constant time (independent of the concrete value of rec->length, which may - * vary within a 256-byte window). - * - * ssl3_cbc_remove_padding or tls1_cbc_remove_padding must be called prior to - * this function. - * - * On entry: - * rec->orig_len >= md_size - * md_size <= EVP_MAX_MD_SIZE - * - * If CBC_MAC_ROTATE_IN_PLACE is defined then the rotation is performed with - * variable accesses in a 64-byte-aligned buffer. Assuming that this fits into - * a single or pair of cache-lines, then the variable memory accesses don't - * actually affect the timing. CPUs with smaller cache-lines [if any] are - * not multi-core and are not considered vulnerable to cache-timing attacks. - */ -#define CBC_MAC_ROTATE_IN_PLACE - -void ssl3_cbc_copy_mac(unsigned char *out, const SSL3_RECORD *rec, - unsigned md_size, unsigned orig_len) { -#if defined(CBC_MAC_ROTATE_IN_PLACE) - unsigned char rotated_mac_buf[64 + EVP_MAX_MD_SIZE]; - unsigned char *rotated_mac; -#else - unsigned char rotated_mac[EVP_MAX_MD_SIZE]; -#endif - - /* mac_end is the index of |rec->data| just after the end of the MAC. */ - unsigned mac_end = rec->length; - unsigned mac_start = mac_end - md_size; - /* scan_start contains the number of bytes that we can ignore because - * the MAC's position can only vary by 255 bytes. */ - unsigned scan_start = 0; - unsigned i, j; - unsigned div_spoiler; - unsigned rotate_offset; - - assert(orig_len >= md_size); - assert(md_size <= EVP_MAX_MD_SIZE); - -#if defined(CBC_MAC_ROTATE_IN_PLACE) - rotated_mac = rotated_mac_buf + ((0 - (size_t)rotated_mac_buf) & 63); -#endif - - /* This information is public so it's safe to branch based on it. */ - if (orig_len > md_size + 255 + 1) { - scan_start = orig_len - (md_size + 255 + 1); - } - /* div_spoiler contains a multiple of md_size that is used to cause the - * modulo operation to be constant time. Without this, the time varies - * based on the amount of padding when running on Intel chips at least. - * - * The aim of right-shifting md_size is so that the compiler doesn't - * figure out that it can remove div_spoiler as that would require it - * to prove that md_size is always even, which I hope is beyond it. */ - div_spoiler = md_size >> 1; - div_spoiler <<= (sizeof(div_spoiler) - 1) * 8; - rotate_offset = (div_spoiler + mac_start - scan_start) % md_size; - - memset(rotated_mac, 0, md_size); - for (i = scan_start, j = 0; i < orig_len; i++) { - unsigned char mac_started = constant_time_ge_8(i, mac_start); - unsigned char mac_ended = constant_time_ge_8(i, mac_end); - unsigned char b = rec->data[i]; - rotated_mac[j++] |= b & mac_started & ~mac_ended; - j &= constant_time_lt(j, md_size); - } - -/* Now rotate the MAC */ -#if defined(CBC_MAC_ROTATE_IN_PLACE) - j = 0; - for (i = 0; i < md_size; i++) { - /* in case cache-line is 32 bytes, touch second line */ - ((volatile unsigned char *)rotated_mac)[rotate_offset ^ 32]; - out[j++] = rotated_mac[rotate_offset++]; - rotate_offset &= constant_time_lt(rotate_offset, md_size); - } -#else - memset(out, 0, md_size); - rotate_offset = md_size - rotate_offset; - rotate_offset &= constant_time_lt(rotate_offset, md_size); - for (i = 0; i < md_size; i++) { - for (j = 0; j < md_size; j++) { - out[j] |= rotated_mac[i] & constant_time_eq_8(j, rotate_offset); - } - rotate_offset++; - rotate_offset &= constant_time_lt(rotate_offset, md_size); - } -#endif -} - -/* u32toLE serialises an unsigned, 32-bit number (n) as four bytes at (p) in - * little-endian order. The value of p is advanced by four. */ -#define u32toLE(n, p) \ - (*((p)++)=(unsigned char)(n), \ - *((p)++)=(unsigned char)(n>>8), \ - *((p)++)=(unsigned char)(n>>16), \ - *((p)++)=(unsigned char)(n>>24)) - -/* These functions serialize the state of a hash and thus perform the standard - * "final" operation without adding the padding and length that such a function - * typically does. */ -static void tls1_sha1_final_raw(void *ctx, unsigned char *md_out) { - SHA_CTX *sha1 = ctx; - l2n(sha1->h0, md_out); - l2n(sha1->h1, md_out); - l2n(sha1->h2, md_out); - l2n(sha1->h3, md_out); - l2n(sha1->h4, md_out); -} -#define LARGEST_DIGEST_CTX SHA_CTX - -static void tls1_sha256_final_raw(void *ctx, unsigned char *md_out) { - SHA256_CTX *sha256 = ctx; - unsigned i; - - for (i = 0; i < 8; i++) { - l2n(sha256->h[i], md_out); - } -} -#undef LARGEST_DIGEST_CTX -#define LARGEST_DIGEST_CTX SHA256_CTX - -static void tls1_sha512_final_raw(void *ctx, unsigned char *md_out) { - SHA512_CTX *sha512 = ctx; - unsigned i; - - for (i = 0; i < 8; i++) { - l2n8(sha512->h[i], md_out); - } -} -#undef LARGEST_DIGEST_CTX -#define LARGEST_DIGEST_CTX SHA512_CTX - -/* ssl3_cbc_record_digest_supported returns 1 iff |ctx| uses a hash function - * which ssl3_cbc_digest_record supports. */ -char ssl3_cbc_record_digest_supported(const EVP_MD_CTX *ctx) { - switch (EVP_MD_CTX_type(ctx)) { - case NID_sha1: - case NID_sha256: - case NID_sha384: - return 1; - - default: - return 0; - } -} - -/* ssl3_cbc_digest_record computes the MAC of a decrypted, padded SSLv3/TLS - * record. - * - * ctx: the EVP_MD_CTX from which we take the hash function. - * ssl3_cbc_record_digest_supported must return true for this EVP_MD_CTX. - * md_out: the digest output. At most EVP_MAX_MD_SIZE bytes will be written. - * md_out_size: the number of output bytes is written here. - * header: the 13-byte, TLS record header. - * data: the record data itself, less any preceeding explicit IV. - * data_plus_mac_size: the secret, reported length of the data and MAC - * once the padding has been removed. - * data_plus_mac_plus_padding_size: the public length of the whole - * record, including padding. - * is_sslv3: non-zero if we are to use SSLv3. Otherwise, TLS. - * - * On entry: by virtue of having been through one of the remove_padding - * functions, above, we know that data_plus_mac_size is large enough to contain - * a padding byte and MAC. (If the padding was invalid, it might contain the - * padding too. ) */ -int ssl3_cbc_digest_record(const EVP_MD_CTX *ctx, unsigned char *md_out, - size_t *md_out_size, const unsigned char header[13], - const unsigned char *data, size_t data_plus_mac_size, - size_t data_plus_mac_plus_padding_size, - const unsigned char *mac_secret, - unsigned mac_secret_length, char is_sslv3) { - union { - double align; - unsigned char c[sizeof(LARGEST_DIGEST_CTX)]; - } md_state; - void (*md_final_raw)(void *ctx, unsigned char *md_out); - void (*md_transform)(void *ctx, const unsigned char *block); - unsigned md_size, md_block_size = 64; - unsigned sslv3_pad_length = 40, header_length, variance_blocks, len, - max_mac_bytes, num_blocks, num_starting_blocks, k, mac_end_offset, c, - index_a, index_b; - unsigned int bits; /* at most 18 bits */ - unsigned char length_bytes[MAX_HASH_BIT_COUNT_BYTES]; - /* hmac_pad is the masked HMAC key. */ - unsigned char hmac_pad[MAX_HASH_BLOCK_SIZE]; - unsigned char first_block[MAX_HASH_BLOCK_SIZE]; - unsigned char mac_out[EVP_MAX_MD_SIZE]; - unsigned i, j, md_out_size_u; - EVP_MD_CTX md_ctx; - /* mdLengthSize is the number of bytes in the length field that terminates - * the hash. */ - unsigned md_length_size = 8; - - /* This is a, hopefully redundant, check that allows us to forget about - * many possible overflows later in this function. */ - assert(data_plus_mac_plus_padding_size < 1024 * 1024); - - switch (EVP_MD_CTX_type(ctx)) { - case NID_sha1: - SHA1_Init((SHA_CTX *)md_state.c); - md_final_raw = tls1_sha1_final_raw; - md_transform = - (void (*)(void *ctx, const unsigned char *block))SHA1_Transform; - md_size = 20; - break; - - case NID_sha256: - SHA256_Init((SHA256_CTX *)md_state.c); - md_final_raw = tls1_sha256_final_raw; - md_transform = - (void (*)(void *ctx, const unsigned char *block))SHA256_Transform; - md_size = 32; - break; - - case NID_sha384: - SHA384_Init((SHA512_CTX *)md_state.c); - md_final_raw = tls1_sha512_final_raw; - md_transform = - (void (*)(void *ctx, const unsigned char *block))SHA512_Transform; - md_size = 384 / 8; - md_block_size = 128; - md_length_size = 16; - break; - - default: - /* ssl3_cbc_record_digest_supported should have been - * called first to check that the hash function is - * supported. */ - assert(0); - *md_out_size = 0; - return 0; - } - - assert(md_length_size <= MAX_HASH_BIT_COUNT_BYTES); - assert(md_block_size <= MAX_HASH_BLOCK_SIZE); - assert(md_size <= EVP_MAX_MD_SIZE); - - header_length = 13; - if (is_sslv3) { - header_length = mac_secret_length + sslv3_pad_length + - 8 /* sequence number */ + 1 /* record type */ + - 2 /* record length */; - } - - /* variance_blocks is the number of blocks of the hash that we have to - * calculate in constant time because they could be altered by the - * padding value. - * - * In SSLv3, the padding must be minimal so the end of the plaintext - * varies by, at most, 15+20 = 35 bytes. (We conservatively assume that - * the MAC size varies from 0..20 bytes.) In case the 9 bytes of hash - * termination (0x80 + 64-bit length) don't fit in the final block, we - * say that the final two blocks can vary based on the padding. - * - * TLSv1 has MACs up to 48 bytes long (SHA-384) and the padding is not - * required to be minimal. Therefore we say that the final six blocks - * can vary based on the padding. - * - * Later in the function, if the message is short and there obviously - * cannot be this many blocks then variance_blocks can be reduced. */ - variance_blocks = is_sslv3 ? 2 : 6; - /* From now on we're dealing with the MAC, which conceptually has 13 - * bytes of `header' before the start of the data (TLS) or 71/75 bytes - * (SSLv3) */ - len = data_plus_mac_plus_padding_size + header_length; - /* max_mac_bytes contains the maximum bytes of bytes in the MAC, including - * |header|, assuming that there's no padding. */ - max_mac_bytes = len - md_size - 1; - /* num_blocks is the maximum number of hash blocks. */ - num_blocks = - (max_mac_bytes + 1 + md_length_size + md_block_size - 1) / md_block_size; - /* In order to calculate the MAC in constant time we have to handle - * the final blocks specially because the padding value could cause the - * end to appear somewhere in the final |variance_blocks| blocks and we - * can't leak where. However, |num_starting_blocks| worth of data can - * be hashed right away because no padding value can affect whether - * they are plaintext. */ - num_starting_blocks = 0; - /* k is the starting byte offset into the conceptual header||data where - * we start processing. */ - k = 0; - /* mac_end_offset is the index just past the end of the data to be - * MACed. */ - mac_end_offset = data_plus_mac_size + header_length - md_size; - /* c is the index of the 0x80 byte in the final hash block that - * contains application data. */ - c = mac_end_offset % md_block_size; - /* index_a is the hash block number that contains the 0x80 terminating - * value. */ - index_a = mac_end_offset / md_block_size; - /* index_b is the hash block number that contains the 64-bit hash - * length, in bits. */ - index_b = (mac_end_offset + md_length_size) / md_block_size; - /* bits is the hash-length in bits. It includes the additional hash - * block for the masked HMAC key, or whole of |header| in the case of - * SSLv3. */ - - /* For SSLv3, if we're going to have any starting blocks then we need - * at least two because the header is larger than a single block. */ - if (num_blocks > variance_blocks + (is_sslv3 ? 1 : 0)) { - num_starting_blocks = num_blocks - variance_blocks; - k = md_block_size * num_starting_blocks; - } - - bits = 8 * mac_end_offset; - if (!is_sslv3) { - /* Compute the initial HMAC block. For SSLv3, the padding and - * secret bytes are included in |header| because they take more - * than a single block. */ - bits += 8 * md_block_size; - memset(hmac_pad, 0, md_block_size); - assert(mac_secret_length <= sizeof(hmac_pad)); - memcpy(hmac_pad, mac_secret, mac_secret_length); - for (i = 0; i < md_block_size; i++) { - hmac_pad[i] ^= 0x36; - } - - md_transform(md_state.c, hmac_pad); - } - - memset(length_bytes, 0, md_length_size - 4); - length_bytes[md_length_size - 4] = (unsigned char)(bits >> 24); - length_bytes[md_length_size - 3] = (unsigned char)(bits >> 16); - length_bytes[md_length_size - 2] = (unsigned char)(bits >> 8); - length_bytes[md_length_size - 1] = (unsigned char)bits; - - if (k > 0) { - if (is_sslv3) { - /* The SSLv3 header is larger than a single block. - * overhang is the number of bytes beyond a single - * block that the header consumes: 7 bytes (SHA1). */ - unsigned overhang = header_length - md_block_size; - md_transform(md_state.c, header); - memcpy(first_block, header + md_block_size, overhang); - memcpy(first_block + overhang, data, md_block_size - overhang); - md_transform(md_state.c, first_block); - for (i = 1; i < k / md_block_size - 1; i++) { - md_transform(md_state.c, data + md_block_size * i - overhang); - } - } else { - /* k is a multiple of md_block_size. */ - memcpy(first_block, header, 13); - memcpy(first_block + 13, data, md_block_size - 13); - md_transform(md_state.c, first_block); - for (i = 1; i < k / md_block_size; i++) { - md_transform(md_state.c, data + md_block_size * i - 13); - } - } - } - - memset(mac_out, 0, sizeof(mac_out)); - - /* We now process the final hash blocks. For each block, we construct - * it in constant time. If the |i==index_a| then we'll include the 0x80 - * bytes and zero pad etc. For each block we selectively copy it, in - * constant time, to |mac_out|. */ - for (i = num_starting_blocks; i <= num_starting_blocks + variance_blocks; - i++) { - unsigned char block[MAX_HASH_BLOCK_SIZE]; - unsigned char is_block_a = constant_time_eq_8(i, index_a); - unsigned char is_block_b = constant_time_eq_8(i, index_b); - for (j = 0; j < md_block_size; j++) { - unsigned char b = 0, is_past_c, is_past_cp1; - if (k < header_length) { - b = header[k]; - } else if (k < data_plus_mac_plus_padding_size + header_length) { - b = data[k - header_length]; - } - k++; - - is_past_c = is_block_a & constant_time_ge_8(j, c); - is_past_cp1 = is_block_a & constant_time_ge_8(j, c + 1); - /* If this is the block containing the end of the - * application data, and we are at the offset for the - * 0x80 value, then overwrite b with 0x80. */ - b = constant_time_select_8(is_past_c, 0x80, b); - /* If this the the block containing the end of the - * application data and we're past the 0x80 value then - * just write zero. */ - b = b & ~is_past_cp1; - /* If this is index_b (the final block), but not - * index_a (the end of the data), then the 64-bit - * length didn't fit into index_a and we're having to - * add an extra block of zeros. */ - b &= ~is_block_b | is_block_a; - - /* The final bytes of one of the blocks contains the - * length. */ - if (j >= md_block_size - md_length_size) { - /* If this is index_b, write a length byte. */ - b = constant_time_select_8( - is_block_b, length_bytes[j - (md_block_size - md_length_size)], b); - } - block[j] = b; - } - - md_transform(md_state.c, block); - md_final_raw(md_state.c, block); - /* If this is index_b, copy the hash value to |mac_out|. */ - for (j = 0; j < md_size; j++) { - mac_out[j] |= block[j] & is_block_b; - } - } - - EVP_MD_CTX_init(&md_ctx); - if (!EVP_DigestInit_ex(&md_ctx, ctx->digest, NULL /* engine */)) { - EVP_MD_CTX_cleanup(&md_ctx); - return 0; - } - - if (is_sslv3) { - /* We repurpose |hmac_pad| to contain the SSLv3 pad2 block. */ - memset(hmac_pad, 0x5c, sslv3_pad_length); - - EVP_DigestUpdate(&md_ctx, mac_secret, mac_secret_length); - EVP_DigestUpdate(&md_ctx, hmac_pad, sslv3_pad_length); - EVP_DigestUpdate(&md_ctx, mac_out, md_size); - } else { - /* Complete the HMAC in the standard manner. */ - for (i = 0; i < md_block_size; i++) { - hmac_pad[i] ^= 0x6a; - } - - EVP_DigestUpdate(&md_ctx, hmac_pad, md_block_size); - EVP_DigestUpdate(&md_ctx, mac_out, md_size); - } - EVP_DigestFinal(&md_ctx, md_out, &md_out_size_u); - *md_out_size = md_out_size_u; - EVP_MD_CTX_cleanup(&md_ctx); - - return 1; -} diff --git a/ssl/s3_lib.c b/ssl/s3_lib.c index 27bcc12b..69a78e78 100644 --- a/ssl/s3_lib.c +++ b/ssl/s3_lib.c @@ -558,7 +558,6 @@ const SSL_CIPHER ssl3_ciphers[] = { const SSL3_ENC_METHOD SSLv3_enc_data = { tls1_enc, - tls1_mac, ssl3_prf, tls1_setup_key_block, tls1_generate_master_secret, diff --git a/ssl/s3_pkt.c b/ssl/s3_pkt.c index 95737a73..f51e8295 100644 --- a/ssl/s3_pkt.c +++ b/ssl/s3_pkt.c @@ -270,16 +270,12 @@ static int ssl3_get_record(SSL *s) { int ssl_major, ssl_minor, al; int enc_err, n, i, ret = -1; SSL3_RECORD *rr; - SSL_SESSION *sess; uint8_t *p; - uint8_t md[EVP_MAX_MD_SIZE]; short version; - unsigned mac_size, orig_len; size_t extra; unsigned empty_record_count = 0; rr = &s->s3->rrec; - sess = s->session; if (s->options & SSL_OP_MICROSOFT_BIG_SSLV3_BUFFER) { extra = SSL3_RT_MAX_EXTRA; @@ -387,55 +383,6 @@ again: OPENSSL_PUT_ERROR(SSL, ssl3_get_record, SSL_R_BLOCK_CIPHER_PAD_IS_WRONG); goto f_err; } - - /* |r->length| is now the compressed data plus MAC. */ - if (sess != NULL && s->enc_read_ctx != NULL && - EVP_MD_CTX_md(s->read_hash) != NULL) { - /* s->read_hash != NULL => mac_size != -1 */ - uint8_t *mac = NULL; - uint8_t mac_tmp[EVP_MAX_MD_SIZE]; - mac_size = EVP_MD_CTX_size(s->read_hash); - assert(mac_size <= EVP_MAX_MD_SIZE); - - /* kludge: *_cbc_remove_padding passes padding length in rr->type */ - orig_len = rr->length + ((unsigned int)rr->type >> 8); - - /* orig_len is the length of the record before any padding was removed. - * This is public information, as is the MAC in use, therefore we can - * safely process the record in a different amount of time if it's too - * short to possibly contain a MAC. */ - if (orig_len < mac_size || - /* CBC records must have a padding length byte too. */ - (EVP_CIPHER_CTX_mode(s->enc_read_ctx) == EVP_CIPH_CBC_MODE && - orig_len < mac_size + 1)) { - al = SSL_AD_DECODE_ERROR; - OPENSSL_PUT_ERROR(SSL, ssl3_get_record, SSL_R_LENGTH_TOO_SHORT); - goto f_err; - } - - if (EVP_CIPHER_CTX_mode(s->enc_read_ctx) == EVP_CIPH_CBC_MODE) { - /* We update the length so that the TLS header bytes can be constructed - * correctly but we need to extract the MAC in constant time from within - * the record, without leaking the contents of the padding bytes. */ - mac = mac_tmp; - ssl3_cbc_copy_mac(mac_tmp, rr, mac_size, orig_len); - rr->length -= mac_size; - } else { - /* In this case there's no padding, so |orig_len| equals |rec->length| - * and we checked that there's enough bytes for |mac_size| above. */ - rr->length -= mac_size; - mac = &rr->data[rr->length]; - } - - i = s->enc_method->mac(s, md, 0 /* not send */); - if (i < 0 || mac == NULL || CRYPTO_memcmp(md, mac, (size_t)mac_size) != 0) { - enc_err = -1; - } - if (rr->length > SSL3_RT_MAX_COMPRESSED_LENGTH + extra + mac_size) { - enc_err = -1; - } - } - if (enc_err < 0) { /* A separate 'decryption_failed' alert was introduced with TLS 1.0, SSL * 3.0 only has 'bad_record_mac'. But unless a decryption failure is @@ -570,13 +517,12 @@ int ssl3_write_bytes(SSL *s, int type, const void *buf_, int len) { static int do_ssl3_write(SSL *s, int type, const uint8_t *buf, unsigned int len, char fragment, char is_fragment) { uint8_t *p, *plen; - int i, mac_size; + int i; int prefix_len = 0; int eivlen = 0; long align = 0; SSL3_RECORD *wr; SSL3_BUFFER *wb = &(s->s3->wbuf); - SSL_SESSION *sess; /* first check if there is a SSL3_BUFFER still being written out. This will * happen with non blocking IO */ @@ -602,17 +548,6 @@ static int do_ssl3_write(SSL *s, int type, const uint8_t *buf, unsigned int len, } wr = &s->s3->wrec; - sess = s->session; - - if (sess == NULL || s->enc_write_ctx == NULL || - EVP_MD_CTX_md(s->write_hash) == NULL) { - mac_size = 0; - } else { - mac_size = EVP_MD_CTX_size(s->write_hash); - if (mac_size < 0) { - goto err; - } - } if (fragment) { /* countermeasure against known-IV weakness in CBC ciphersuites (see @@ -667,15 +602,9 @@ static int do_ssl3_write(SSL *s, int type, const uint8_t *buf, unsigned int len, plen = p; p += 2; - /* Explicit IV length, block ciphers appropriate version flag */ - if (s->enc_write_ctx && SSL_USE_EXPLICIT_IV(s) && - EVP_CIPHER_CTX_mode(s->enc_write_ctx) == EVP_CIPH_CBC_MODE) { - eivlen = EVP_CIPHER_CTX_iv_length(s->enc_write_ctx); - if (eivlen <= 1) { - eivlen = 0; - } - } else if (s->aead_write_ctx != NULL && - s->aead_write_ctx->variable_nonce_included_in_record) { + /* Leave room for the variable nonce for AEADs which specify it explicitly. */ + if (s->aead_write_ctx != NULL && + s->aead_write_ctx->variable_nonce_included_in_record) { eivlen = s->aead_write_ctx->variable_nonce_len; } @@ -692,13 +621,6 @@ static int do_ssl3_write(SSL *s, int type, const uint8_t *buf, unsigned int len, /* we should still have the output to wr->data and the input from wr->input. * Length should be wr->length. wr->data still points in the wb->buf */ - if (mac_size != 0) { - if (s->enc_method->mac(s, &(p[wr->length + eivlen]), 1) < 0) { - goto err; - } - wr->length += mac_size; - } - wr->input = p; wr->data = p; wr->length += eivlen; @@ -930,7 +852,9 @@ start: /* make sure that we are not getting application data when we are doing a * handshake for the first time */ if (SSL_in_init(s) && type == SSL3_RT_APPLICATION_DATA && - s->enc_read_ctx == NULL) { + s->aead_read_ctx == NULL) { + /* TODO(davidben): Is this check redundant with the handshake_func + * check? */ al = SSL_AD_UNEXPECTED_MESSAGE; OPENSSL_PUT_ERROR(SSL, ssl3_read_bytes, SSL_R_APP_DATA_IN_HANDSHAKE); goto f_err; diff --git a/ssl/ssl_ciph.c b/ssl/ssl_ciph.c index 3f164bd7..55323d47 100644 --- a/ssl/ssl_ciph.c +++ b/ssl/ssl_ciph.c @@ -360,111 +360,6 @@ int ssl_cipher_get_evp_aead(const EVP_AEAD **out_aead, } } -int ssl_cipher_get_evp(const SSL_SESSION *s, const EVP_CIPHER **enc, - const EVP_MD **md, int *mac_pkey_type, - size_t *mac_secret_size) { - const SSL_CIPHER *c; - - c = s->cipher; - if (c == NULL || - /* This function doesn't deal with EVP_AEAD. See - * |ssl_cipher_get_aead_evp|. */ - (c->algorithm2 & SSL_CIPHER_ALGORITHM2_AEAD) || - enc == NULL || - md == NULL) { - return 0; - } - - switch (c->algorithm_enc) { - case SSL_3DES: - *enc = EVP_des_ede3_cbc(); - break; - - case SSL_RC4: - *enc = EVP_rc4(); - break; - - case SSL_AES128: - *enc = EVP_aes_128_cbc(); - break; - - case SSL_AES256: - *enc = EVP_aes_256_cbc(); - break; - - default: - return 0; - } - - if (!ssl_cipher_get_mac(s, md, mac_pkey_type, mac_secret_size)) { - return 0; - } - - assert(*enc != NULL && *md != NULL); - -/* TODO(fork): enable the stitched cipher modes. */ -#if 0 - if (s->ssl_version>>8 != TLS1_VERSION_MAJOR || - s->ssl_version < TLS1_VERSION) - return 1; - - if (c->algorithm_enc == SSL_RC4 && - c->algorithm_mac == SSL_MD5 && - (evp=EVP_get_cipherbyname("RC4-HMAC-MD5"))) - *enc = evp, *md = NULL; - else if (c->algorithm_enc == SSL_AES128 && - c->algorithm_mac == SSL_SHA1 && - (evp=EVP_get_cipherbyname("AES-128-CBC-HMAC-SHA1"))) - *enc = evp, *md = NULL; - else if (c->algorithm_enc == SSL_AES256 && - c->algorithm_mac == SSL_SHA1 && - (evp=EVP_get_cipherbyname("AES-256-CBC-HMAC-SHA1"))) - *enc = evp, *md = NULL; -#endif - - return 1; -} - -int ssl_cipher_get_mac(const SSL_SESSION *s, const EVP_MD **md, - int *mac_pkey_type, size_t *mac_secret_size) { - const SSL_CIPHER *c; - - c = s->cipher; - if (c == NULL) { - return 0; - } - - switch (c->algorithm_mac) { - case SSL_MD5: - *md = EVP_md5(); - break; - - case SSL_SHA1: - *md = EVP_sha1(); - break; - - case SSL_SHA256: - *md = EVP_sha256(); - break; - - case SSL_SHA384: - *md = EVP_sha384(); - break; - - default: - return 0; - } - - if (mac_pkey_type != NULL) { - *mac_pkey_type = EVP_PKEY_HMAC; - } - if (mac_secret_size != NULL) { - *mac_secret_size = EVP_MD_size(*md); - } - - return 1; -} - int ssl_get_handshake_digest(size_t idx, long *mask, const EVP_MD **md) { if (idx >= SSL_MAX_DIGEST) { return 0; diff --git a/ssl/ssl_lib.c b/ssl/ssl_lib.c index 9e5af760..d179dc85 100644 --- a/ssl/ssl_lib.c +++ b/ssl/ssl_lib.c @@ -208,8 +208,6 @@ int SSL_clear(SSL *s) { s->packet_length = 0; ssl_clear_cipher_ctx(s); - ssl_clear_hash_ctx(&s->read_hash); - ssl_clear_hash_ctx(&s->write_hash); if (s->next_proto_negotiated) { OPENSSL_free(s->next_proto_negotiated); @@ -607,8 +605,6 @@ void SSL_free(SSL *s) { } ssl_clear_cipher_ctx(s); - ssl_clear_hash_ctx(&s->read_hash); - ssl_clear_hash_ctx(&s->write_hash); if (s->cert != NULL) { ssl_cert_free(s->cert); @@ -2365,8 +2361,6 @@ void SSL_set_accept_state(SSL *s) { s->handshake_func = s->method->ssl_accept; /* clear the current cipher */ ssl_clear_cipher_ctx(s); - ssl_clear_hash_ctx(&s->read_hash); - ssl_clear_hash_ctx(&s->write_hash); } void SSL_set_connect_state(SSL *s) { @@ -2376,8 +2370,6 @@ void SSL_set_connect_state(SSL *s) { s->handshake_func = s->method->ssl_connect; /* clear the current cipher */ ssl_clear_cipher_ctx(s); - ssl_clear_hash_ctx(&s->read_hash); - ssl_clear_hash_ctx(&s->write_hash); } int ssl_undefined_function(SSL *s) { @@ -2426,18 +2418,6 @@ const char *SSL_SESSION_get_version(const SSL_SESSION *sess) { } void ssl_clear_cipher_ctx(SSL *s) { - if (s->enc_read_ctx != NULL) { - EVP_CIPHER_CTX_cleanup(s->enc_read_ctx); - OPENSSL_free(s->enc_read_ctx); - s->enc_read_ctx = NULL; - } - - if (s->enc_write_ctx != NULL) { - EVP_CIPHER_CTX_cleanup(s->enc_write_ctx); - OPENSSL_free(s->enc_write_ctx); - s->enc_write_ctx = NULL; - } - if (s->aead_read_ctx != NULL) { EVP_AEAD_CTX_cleanup(&s->aead_read_ctx->ctx); OPENSSL_free(s->aead_read_ctx); @@ -3186,27 +3166,6 @@ uint16_t ssl3_version_from_wire(SSL *s, uint16_t wire_version) { return version; } -/* Allocates new EVP_MD_CTX and sets pointer to it into given pointer vairable, - * freeing EVP_MD_CTX previously stored in that variable, if any. If EVP_MD - * pointer is passed, initializes ctx with this md Returns newly allocated - * ctx. */ -EVP_MD_CTX *ssl_replace_hash(EVP_MD_CTX **hash, const EVP_MD *md) { - ssl_clear_hash_ctx(hash); - *hash = EVP_MD_CTX_create(); - if (md != NULL && *hash != NULL && !EVP_DigestInit_ex(*hash, md, NULL)) { - EVP_MD_CTX_destroy(*hash); - *hash = NULL; - } - return *hash; -} - -void ssl_clear_hash_ctx(EVP_MD_CTX **hash) { - if (*hash) { - EVP_MD_CTX_destroy(*hash); - } - *hash = NULL; -} - int SSL_cache_hit(SSL *s) { return s->hit; } int SSL_is_server(SSL *s) { return s->server; } diff --git a/ssl/ssl_locl.h b/ssl/ssl_locl.h index dd51e9ee..b8e77e2a 100644 --- a/ssl/ssl_locl.h +++ b/ssl/ssl_locl.h @@ -577,7 +577,6 @@ struct ssl_protocol_method_st { * of a mess of functions, but hell, think of it as an opaque structure. */ struct ssl3_enc_method { int (*enc)(SSL *, int); - int (*mac)(SSL *, uint8_t *, int); int (*prf)(SSL *, uint8_t *, size_t, const uint8_t *, size_t, const char *, size_t, const uint8_t *, size_t, const uint8_t *, size_t); int (*setup_key_block)(SSL *); @@ -694,11 +693,6 @@ int ssl_cipher_get_evp_aead(const EVP_AEAD **out_aead, size_t *out_fixed_iv_len, const SSL_CIPHER *cipher, uint16_t version); -int ssl_cipher_get_evp(const SSL_SESSION *s, const EVP_CIPHER **enc, - const EVP_MD **md, int *mac_pkey_type, - size_t *mac_secret_size); -int ssl_cipher_get_mac(const SSL_SESSION *s, const EVP_MD **md, - int *mac_pkey_type, size_t *mac_secret_size); int ssl_get_handshake_digest(size_t i, long *mask, const EVP_MD **md); int ssl_cipher_get_cert_index(const SSL_CIPHER *c); int ssl_cipher_has_server_public_key(const SSL_CIPHER *cipher); @@ -913,7 +907,6 @@ int tls1_enc(SSL *s, int snd); int tls1_handshake_digest(SSL *s, uint8_t *out, size_t out_len); int tls1_final_finish_mac(SSL *s, const char *str, int slen, uint8_t *p); int tls1_cert_verify_mac(SSL *s, int md_nid, uint8_t *p); -int tls1_mac(SSL *ssl, uint8_t *md, int snd); int tls1_generate_master_secret(SSL *s, uint8_t *out, const uint8_t *premaster, size_t premaster_len); int tls1_export_keying_material(SSL *s, uint8_t *out, size_t olen, @@ -1030,8 +1023,6 @@ int ssl3_is_version_enabled(SSL *s, uint16_t version); * the wire version except at API boundaries. */ uint16_t ssl3_version_from_wire(SSL *s, uint16_t wire_version); -EVP_MD_CTX *ssl_replace_hash(EVP_MD_CTX **hash, const EVP_MD *md); -void ssl_clear_hash_ctx(EVP_MD_CTX **hash); int ssl_add_serverhello_renegotiate_ext(SSL *s, uint8_t *p, int *len, int maxlen); int ssl_parse_serverhello_renegotiate_ext(SSL *s, CBS *cbs, int *out_alert); @@ -1055,19 +1046,4 @@ int ssl_parse_clienthello_use_srtp_ext(SSL *s, CBS *cbs, int *out_alert); int ssl_add_serverhello_use_srtp_ext(SSL *s, uint8_t *p, int *len, int maxlen); int ssl_parse_serverhello_use_srtp_ext(SSL *s, CBS *cbs, int *out_alert); -/* s3_cbc.c */ -void ssl3_cbc_copy_mac(uint8_t *out, const SSL3_RECORD *rec, unsigned md_size, - unsigned orig_len); -int ssl3_cbc_remove_padding(const SSL *s, SSL3_RECORD *rec, unsigned block_size, - unsigned mac_size); -int tls1_cbc_remove_padding(const SSL *s, SSL3_RECORD *rec, unsigned block_size, - unsigned mac_size); -char ssl3_cbc_record_digest_supported(const EVP_MD_CTX *ctx); -int ssl3_cbc_digest_record(const EVP_MD_CTX *ctx, uint8_t *md_out, - size_t *md_out_size, const uint8_t header[13], - const uint8_t *data, size_t data_plus_mac_size, - size_t data_plus_mac_plus_padding_size, - const uint8_t *mac_secret, - unsigned mac_secret_length, char is_sslv3); - #endif diff --git a/ssl/t1_enc.c b/ssl/t1_enc.c index e4e99074..10d940fe 100644 --- a/ssl/t1_enc.c +++ b/ssl/t1_enc.c @@ -307,20 +307,6 @@ static int tls1_aead_ctx_init(SSL_AEAD_CTX **aead_ctx) { return 1; } -static void tls1_cleanup_enc_ctx(EVP_CIPHER_CTX **ctx) { - if (*ctx != NULL) { - EVP_CIPHER_CTX_free(*ctx); - } - *ctx = NULL; -} - -static void tls1_cleanup_hash_ctx(EVP_MD_CTX **ctx) { - if (*ctx != NULL) { - EVP_MD_CTX_destroy(*ctx); - } - *ctx = NULL; -} - static int tls1_change_cipher_state_aead(SSL *s, char is_read, const uint8_t *key, unsigned key_len, const uint8_t *iv, unsigned iv_len, @@ -332,14 +318,6 @@ static int tls1_change_cipher_state_aead(SSL *s, char is_read, * simulates pre-AEAD cipher suites. */ uint8_t merged_key[EVP_AEAD_MAX_KEY_LENGTH]; - if (is_read) { - tls1_cleanup_enc_ctx(&s->enc_read_ctx); - tls1_cleanup_hash_ctx(&s->read_hash); - } else { - tls1_cleanup_enc_ctx(&s->enc_write_ctx); - tls1_cleanup_hash_ctx(&s->write_hash); - } - if (mac_secret_len > 0) { /* This is a "stateful" AEAD (for compatibility with pre-AEAD cipher * suites). */ @@ -422,120 +400,6 @@ static int tls1_change_cipher_state_aead(SSL *s, char is_read, return 1; } -static void tls1_cleanup_aead_ctx(SSL_AEAD_CTX **ctx) { - if (*ctx != NULL) { - EVP_AEAD_CTX_cleanup(&(*ctx)->ctx); - OPENSSL_free(*ctx); - } - *ctx = NULL; -} - -/* tls1_change_cipher_state_cipher performs the work needed to switch cipher - * states when using EVP_CIPHER. The argument |is_read| is true iff this - * function is being called due to reading, as opposed to writing, a - * ChangeCipherSpec message. In order to support export ciphersuites, - * use_client_keys indicates whether the key material provided is in the - * "client write" direction. */ -static int tls1_change_cipher_state_cipher(SSL *s, char is_read, - char use_client_keys, - const uint8_t *mac_secret, - unsigned mac_secret_len, - const uint8_t *key, unsigned key_len, - const uint8_t *iv, unsigned iv_len) { - const EVP_CIPHER *cipher = s->s3->tmp.new_sym_enc; - EVP_CIPHER_CTX *cipher_ctx; - EVP_MD_CTX *mac_ctx; - - if (is_read) { - tls1_cleanup_aead_ctx(&s->aead_read_ctx); - } else { - /* When updating the cipher state for DTLS, we do not wish to free the old - * ones because DTLS stores pointers to them in order to implement - * retransmission. See dtls1_hm_fragment_free. - * - * TODO(davidben): Simplify aead_write_ctx ownership, probably by just - * forbidding DTLS renego. */ - if (!SSL_IS_DTLS(s)) { - tls1_cleanup_aead_ctx(&s->aead_write_ctx); - } else { - s->aead_write_ctx = NULL; - } - } - - if (is_read) { - if (s->enc_read_ctx != NULL && !SSL_IS_DTLS(s)) { - EVP_CIPHER_CTX_cleanup(s->enc_read_ctx); - } else if ((s->enc_read_ctx = EVP_CIPHER_CTX_new()) == NULL) { - goto err; - } - - cipher_ctx = s->enc_read_ctx; - mac_ctx = ssl_replace_hash(&s->read_hash, NULL); - if (mac_ctx == NULL) { - goto err; - } - - memcpy(s->s3->read_mac_secret, mac_secret, mac_secret_len); - s->s3->read_mac_secret_size = mac_secret_len; - } else { - /* When updating the write contexts for DTLS, we do not wish to free the - * old ones because DTLS stores pointers to them in order to implement - * retransmission. */ - - if (s->enc_write_ctx != NULL && !SSL_IS_DTLS(s)) { - EVP_CIPHER_CTX_cleanup(s->enc_write_ctx); - } else { - s->enc_write_ctx = OPENSSL_malloc(sizeof(EVP_CIPHER_CTX)); - if (s->enc_write_ctx == NULL) { - goto err; - } - } - EVP_CIPHER_CTX_init(s->enc_write_ctx); - - cipher_ctx = s->enc_write_ctx; - if (SSL_IS_DTLS(s)) { - /* This is the same as ssl_replace_hash, but doesn't - * free the old |s->write_hash|. */ - mac_ctx = EVP_MD_CTX_create(); - if (!mac_ctx) { - goto err; - } - s->write_hash = mac_ctx; - } else { - mac_ctx = ssl_replace_hash(&s->write_hash, NULL); - if (mac_ctx == NULL) { - goto err; - } - } - - memcpy(s->s3->write_mac_secret, mac_secret, mac_secret_len); - s->s3->write_mac_secret_size = mac_secret_len; - } - - EVP_PKEY *mac_key = EVP_PKEY_new_mac_key(s->s3->tmp.new_mac_pkey_type, NULL, - mac_secret, mac_secret_len); - if (!mac_key) { - return 0; - } - - if (!EVP_DigestSignInit(mac_ctx, NULL, s->s3->tmp.new_hash, NULL, mac_key)) { - EVP_PKEY_free(mac_key); - goto err; - } - EVP_PKEY_free(mac_key); - - if (!EVP_CipherInit_ex(cipher_ctx, cipher, NULL /* engine */, key, iv, - !is_read)) { - goto err; - } - - return 1; - -err: - OPENSSL_PUT_ERROR(SSL, tls1_change_cipher_state_cipher, ERR_R_MALLOC_FAILURE); - return 0; -} - int tls1_change_cipher_state(SSL *s, int which) { /* is_read is true if we have just read a ChangeCipherSpec message - i.e. we * need to update the read cipherspec. Otherwise we have just written one. */ @@ -548,7 +412,6 @@ int tls1_change_cipher_state(SSL *s, int which) { const uint8_t *client_write_mac_secret, *server_write_mac_secret, *mac_secret; const uint8_t *client_write_key, *server_write_key, *key; const uint8_t *client_write_iv, *server_write_iv, *iv; - const EVP_CIPHER *cipher = s->s3->tmp.new_sym_enc; const EVP_AEAD *aead = s->s3->tmp.new_aead; size_t key_len, iv_len, mac_secret_len; const uint8_t *key_data; @@ -561,20 +424,21 @@ int tls1_change_cipher_state(SSL *s, int which) { mac_secret_len = s->s3->tmp.new_mac_secret_len; iv_len = s->s3->tmp.new_fixed_iv_len; - if (aead != NULL) { - key_len = EVP_AEAD_key_length(aead); - if (mac_secret_len > 0) { - /* For "stateful" AEADs (i.e. compatibility with pre-AEAD cipher suites) - * the key length reported by |EVP_AEAD_key_length| will include the MAC - * and IV key bytes. */ - if (key_len < mac_secret_len + iv_len) { - OPENSSL_PUT_ERROR(SSL, tls1_change_cipher_state, ERR_R_INTERNAL_ERROR); - return 0; - } - key_len -= mac_secret_len + iv_len; + if (aead == NULL) { + OPENSSL_PUT_ERROR(SSL, tls1_change_cipher_state, ERR_R_INTERNAL_ERROR); + return 0; + } + + key_len = EVP_AEAD_key_length(aead); + if (mac_secret_len > 0) { + /* For "stateful" AEADs (i.e. compatibility with pre-AEAD cipher + * suites) the key length reported by |EVP_AEAD_key_length| will + * include the MAC and IV key bytes. */ + if (key_len < mac_secret_len + iv_len) { + OPENSSL_PUT_ERROR(SSL, tls1_change_cipher_state, ERR_R_INTERNAL_ERROR); + return 0; } - } else { - key_len = EVP_CIPHER_key_length(cipher); + key_len -= mac_secret_len + iv_len; } key_data = s->s3->tmp.key_block; @@ -606,33 +470,17 @@ int tls1_change_cipher_state(SSL *s, int which) { return 0; } - if (aead != NULL) { - if (!tls1_change_cipher_state_aead(s, is_read, key, key_len, iv, iv_len, - mac_secret, mac_secret_len)) { - return 0; - } - } else { - if (!tls1_change_cipher_state_cipher(s, is_read, use_client_keys, - mac_secret, mac_secret_len, key, - key_len, iv, iv_len)) { - return 0; - } - } - - return 1; + return tls1_change_cipher_state_aead(s, is_read, key, key_len, iv, iv_len, + mac_secret, mac_secret_len); } int tls1_setup_key_block(SSL *s) { uint8_t *p; - const EVP_CIPHER *c = NULL; - const EVP_MD *hash = NULL; const EVP_AEAD *aead = NULL; - int mac_type = NID_undef; int ret = 0; size_t mac_secret_len, fixed_iv_len, variable_iv_len, key_len; size_t key_block_len; - if (s->s3->tmp.key_block_length != 0) { return 1; } @@ -641,40 +489,29 @@ int tls1_setup_key_block(SSL *s) { goto cipher_unavailable_err; } - /* TODO(davidben): Prune away dead code. To be done in follow-up commit. */ - if (1) { - if (!ssl_cipher_get_evp_aead(&aead, &mac_secret_len, &fixed_iv_len, - s->session->cipher, - ssl3_version_from_wire(s, s->version))) { - goto cipher_unavailable_err; - } - key_len = EVP_AEAD_key_length(aead); - variable_iv_len = EVP_AEAD_nonce_length(aead); - if (mac_secret_len > 0) { - /* For "stateful" AEADs (i.e. compatibility with pre-AEAD cipher suites) - * the key length reported by |EVP_AEAD_key_length| will include the MAC - * key bytes and initial implicit IV. */ - if (key_len < mac_secret_len + fixed_iv_len) { - OPENSSL_PUT_ERROR(SSL, tls1_setup_key_block, ERR_R_INTERNAL_ERROR); - return 0; - } - key_len -= mac_secret_len + fixed_iv_len; - } else { - /* The nonce is split into a fixed portion and a variable portion. */ - if (variable_iv_len < fixed_iv_len) { - OPENSSL_PUT_ERROR(SSL, tls1_setup_key_block, ERR_R_INTERNAL_ERROR); - return 0; - } - variable_iv_len -= fixed_iv_len; + if (!ssl_cipher_get_evp_aead(&aead, &mac_secret_len, &fixed_iv_len, + s->session->cipher, + ssl3_version_from_wire(s, s->version))) { + goto cipher_unavailable_err; + } + key_len = EVP_AEAD_key_length(aead); + variable_iv_len = EVP_AEAD_nonce_length(aead); + if (mac_secret_len > 0) { + /* For "stateful" AEADs (i.e. compatibility with pre-AEAD cipher suites) the + * key length reported by |EVP_AEAD_key_length| will include the MAC key + * bytes and initial implicit IV. */ + if (key_len < mac_secret_len + fixed_iv_len) { + OPENSSL_PUT_ERROR(SSL, tls1_setup_key_block, ERR_R_INTERNAL_ERROR); + return 0; } + key_len -= mac_secret_len + fixed_iv_len; } else { - if (!ssl_cipher_get_evp(s->session, &c, &hash, &mac_type, - &mac_secret_len)) { - goto cipher_unavailable_err; + /* The nonce is split into a fixed portion and a variable portion. */ + if (variable_iv_len < fixed_iv_len) { + OPENSSL_PUT_ERROR(SSL, tls1_setup_key_block, ERR_R_INTERNAL_ERROR); + return 0; } - key_len = EVP_CIPHER_key_length(c); - fixed_iv_len = EVP_CIPHER_iv_length(c); - variable_iv_len = 0; + variable_iv_len -= fixed_iv_len; } assert(mac_secret_len < 256); @@ -682,9 +519,6 @@ int tls1_setup_key_block(SSL *s) { assert(variable_iv_len < 256); s->s3->tmp.new_aead = aead; - s->s3->tmp.new_sym_enc = c; - s->s3->tmp.new_hash = hash; - s->s3->tmp.new_mac_pkey_type = mac_type; s->s3->tmp.new_mac_secret_len = (uint8_t)mac_secret_len; s->s3->tmp.new_fixed_iv_len = (uint8_t)fixed_iv_len; s->s3->tmp.new_variable_iv_len = (uint8_t)variable_iv_len; @@ -741,10 +575,6 @@ cipher_unavailable_err: * an internal error occured. */ int tls1_enc(SSL *s, int send) { SSL3_RECORD *rec; - EVP_CIPHER_CTX *ds; - unsigned long l; - int bs, i, j, k, pad = 0, ret, mac_size = 0; - const EVP_CIPHER *enc; const SSL_AEAD_CTX *aead; if (send) { @@ -755,215 +585,140 @@ int tls1_enc(SSL *s, int send) { aead = s->aead_read_ctx; } - if (aead) { - uint8_t ad[13], *seq, *in, *out, nonce[EVP_AEAD_MAX_NONCE_LENGTH]; - unsigned nonce_used; - size_t n, ad_len; + if (s->session == NULL || aead == NULL) { + memmove(rec->data, rec->input, rec->length); + rec->input = rec->data; + return 1; + } - seq = send ? s->s3->write_sequence : s->s3->read_sequence; + uint8_t ad[13], *seq, *in, *out, nonce[EVP_AEAD_MAX_NONCE_LENGTH]; + unsigned nonce_used; + size_t n, ad_len; - if (SSL_IS_DTLS(s)) { - uint8_t dtlsseq[9], *p = dtlsseq; + seq = send ? s->s3->write_sequence : s->s3->read_sequence; - s2n(send ? s->d1->w_epoch : s->d1->r_epoch, p); - memcpy(p, &seq[2], 6); - memcpy(ad, dtlsseq, 8); - } else { - memcpy(ad, seq, 8); - for (i = 7; i >= 0; i--) { - ++seq[i]; - if (seq[i] != 0) { - break; - } - } - } + if (SSL_IS_DTLS(s)) { + uint8_t dtlsseq[9], *p = dtlsseq; - ad[8] = rec->type; - ad_len = 9; - if (!aead->omit_version_in_ad) { - ad[ad_len++] = (uint8_t)(s->version >> 8); - ad[ad_len++] = (uint8_t)(s->version); + s2n(send ? s->d1->w_epoch : s->d1->r_epoch, p); + memcpy(p, &seq[2], 6); + memcpy(ad, dtlsseq, 8); + } else { + int i; + memcpy(ad, seq, 8); + for (i = 7; i >= 0; i--) { + ++seq[i]; + if (seq[i] != 0) { + break; + } } + } - if (aead->fixed_nonce_len + aead->variable_nonce_len > sizeof(nonce)) { - OPENSSL_PUT_ERROR(SSL, tls1_enc, ERR_R_INTERNAL_ERROR); - return -1; /* internal error - should never happen. */ - } + ad[8] = rec->type; + ad_len = 9; + if (!aead->omit_version_in_ad) { + ad[ad_len++] = (uint8_t)(s->version >> 8); + ad[ad_len++] = (uint8_t)(s->version); + } - memcpy(nonce, aead->fixed_nonce, aead->fixed_nonce_len); - nonce_used = aead->fixed_nonce_len; - - if (send) { - size_t len = rec->length; - size_t eivlen = 0; - in = rec->input; - out = rec->data; - - uint8_t *variable_nonce = nonce + nonce_used; - if (aead->random_variable_nonce) { - assert(aead->variable_nonce_included_in_record); - if (!RAND_bytes(nonce + nonce_used, aead->variable_nonce_len)) { - return -1; - } - } else { - /* When sending we use the sequence number as the variable part of the - * nonce. */ - if (aead->variable_nonce_len != 8) { - OPENSSL_PUT_ERROR(SSL, tls1_enc, ERR_R_INTERNAL_ERROR); - return -1; - } - memcpy(nonce + nonce_used, ad, aead->variable_nonce_len); - } - nonce_used += aead->variable_nonce_len; - - /* in do_ssl3_write, rec->input is moved forward by variable_nonce_len in - * order to leave space for the variable nonce. Thus we can copy the - * sequence number bytes into place without overwriting any of the - * plaintext. */ - if (aead->variable_nonce_included_in_record) { - memcpy(out, variable_nonce, aead->variable_nonce_len); - len -= aead->variable_nonce_len; - eivlen = aead->variable_nonce_len; - } + if (aead->fixed_nonce_len + aead->variable_nonce_len > sizeof(nonce)) { + OPENSSL_PUT_ERROR(SSL, tls1_enc, ERR_R_INTERNAL_ERROR); + return -1; /* internal error - should never happen. */ + } - if (!aead->omit_length_in_ad) { - ad[ad_len++] = len >> 8; - ad[ad_len++] = len & 0xff; - } + memcpy(nonce, aead->fixed_nonce, aead->fixed_nonce_len); + nonce_used = aead->fixed_nonce_len; - if (!EVP_AEAD_CTX_seal(&aead->ctx, out + eivlen, &n, len + aead->tag_len, - nonce, nonce_used, in + eivlen, len, ad, ad_len)) { + if (send) { + size_t len = rec->length; + size_t eivlen = 0; + in = rec->input; + out = rec->data; + + uint8_t *variable_nonce = nonce + nonce_used; + if (aead->random_variable_nonce) { + assert(aead->variable_nonce_included_in_record); + if (!RAND_bytes(nonce + nonce_used, aead->variable_nonce_len)) { return -1; } - - if (aead->variable_nonce_included_in_record) { - n += aead->variable_nonce_len; - } } else { - /* receive */ - size_t len = rec->length; - - if (rec->data != rec->input) { + /* When sending we use the sequence number as the variable part of the + * nonce. */ + if (aead->variable_nonce_len != 8) { OPENSSL_PUT_ERROR(SSL, tls1_enc, ERR_R_INTERNAL_ERROR); - return -1; /* internal error - should never happen. */ - } - out = in = rec->input; - - if (len < aead->variable_nonce_len) { - return 0; - } - memcpy(nonce + nonce_used, - aead->variable_nonce_included_in_record ? in : ad, - aead->variable_nonce_len); - nonce_used += aead->variable_nonce_len; - - if (aead->variable_nonce_included_in_record) { - in += aead->variable_nonce_len; - len -= aead->variable_nonce_len; - out += aead->variable_nonce_len; - } - - if (!aead->omit_length_in_ad) { - if (len < aead->tag_len) { - return 0; - } - size_t plaintext_len = len - aead->tag_len; - - ad[ad_len++] = plaintext_len >> 8; - ad[ad_len++] = plaintext_len & 0xff; - } - - if (!EVP_AEAD_CTX_open(&aead->ctx, out, &n, rec->length, nonce, nonce_used, in, - len, ad, ad_len)) { return -1; } - - rec->data = rec->input = out; + memcpy(nonce + nonce_used, ad, aead->variable_nonce_len); + } + nonce_used += aead->variable_nonce_len; + + /* in do_ssl3_write, rec->input is moved forward by variable_nonce_len in + * order to leave space for the variable nonce. Thus we can copy the + * sequence number bytes into place without overwriting any of the + * plaintext. */ + if (aead->variable_nonce_included_in_record) { + memcpy(out, variable_nonce, aead->variable_nonce_len); + len -= aead->variable_nonce_len; + eivlen = aead->variable_nonce_len; } - rec->length = n; - return 1; - } - - if (send) { - ds = s->enc_write_ctx; - rec = &(s->s3->wrec); - if (s->enc_write_ctx == NULL) { - enc = NULL; - } else { - int ivlen; - enc = EVP_CIPHER_CTX_cipher(s->enc_write_ctx); - /* For TLSv1.1 and later explicit IV */ - if (SSL_USE_EXPLICIT_IV(s) && EVP_CIPHER_mode(enc) == EVP_CIPH_CBC_MODE) { - ivlen = EVP_CIPHER_iv_length(enc); - } else { - ivlen = 0; - } - - if (ivlen > 1) { - if (rec->data != rec->input) { - /* we can't write into the input stream: - * Can this ever happen?? (steve) - */ - fprintf(stderr, "%s:%d: rec->data != rec->input\n", __FILE__, - __LINE__); - } else if (!RAND_bytes(rec->input, ivlen)) { - return -1; - } - } + if (!aead->omit_length_in_ad) { + ad[ad_len++] = len >> 8; + ad[ad_len++] = len & 0xff; } - } else { - ds = s->enc_read_ctx; - rec = &(s->s3->rrec); - if (s->enc_read_ctx == NULL) { - enc = NULL; - } else { - enc = EVP_CIPHER_CTX_cipher(s->enc_read_ctx); + + if (!EVP_AEAD_CTX_seal(&aead->ctx, out + eivlen, &n, len + aead->tag_len, + nonce, nonce_used, in + eivlen, len, ad, ad_len)) { + return -1; } - } - if (s->session == NULL || ds == NULL || enc == NULL) { - memmove(rec->data, rec->input, rec->length); - rec->input = rec->data; - ret = 1; + if (aead->variable_nonce_included_in_record) { + n += aead->variable_nonce_len; + } } else { - l = rec->length; - bs = EVP_CIPHER_block_size(ds->cipher); - - if (bs != 1 && send) { - i = bs - ((int)l % bs); + /* receive */ + size_t len = rec->length; - /* Add weird padding of upto 256 bytes */ - /* we need to add 'i' padding bytes of value j */ - j = i - 1; - for (k = (int)l; k < (int)(l + i); k++) { - rec->input[k] = j; - } - l += i; - rec->length += i; + if (rec->data != rec->input) { + OPENSSL_PUT_ERROR(SSL, tls1_enc, ERR_R_INTERNAL_ERROR); + return -1; /* internal error - should never happen. */ } + out = in = rec->input; - if (!send && (l == 0 || l % bs != 0)) { + if (len < aead->variable_nonce_len) { return 0; } - - if (!EVP_Cipher(ds, rec->data, rec->input, l)) { - return -1; + memcpy(nonce + nonce_used, + aead->variable_nonce_included_in_record ? in : ad, + aead->variable_nonce_len); + nonce_used += aead->variable_nonce_len; + + if (aead->variable_nonce_included_in_record) { + in += aead->variable_nonce_len; + len -= aead->variable_nonce_len; + out += aead->variable_nonce_len; } - ret = 1; - if (EVP_MD_CTX_md(s->read_hash) != NULL) { - mac_size = EVP_MD_CTX_size(s->read_hash); - } + if (!aead->omit_length_in_ad) { + if (len < aead->tag_len) { + return 0; + } + size_t plaintext_len = len - aead->tag_len; - if (bs != 1 && !send) { - ret = tls1_cbc_remove_padding(s, rec, bs, mac_size); + ad[ad_len++] = plaintext_len >> 8; + ad[ad_len++] = plaintext_len & 0xff; } - if (pad && !send) { - rec->length -= pad; + + if (!EVP_AEAD_CTX_open(&aead->ctx, out, &n, rec->length, nonce, nonce_used, in, + len, ad, ad_len)) { + return -1; } + + rec->data = rec->input = out; } - return ret; + + rec->length = n; + return 1; } int tls1_cert_verify_mac(SSL *s, int md_nid, uint8_t *out) { @@ -1072,89 +827,6 @@ int tls1_final_finish_mac(SSL *s, const char *str, int slen, uint8_t *out) { } } -int tls1_mac(SSL *ssl, uint8_t *md, int send) { - SSL3_RECORD *rec; - uint8_t *seq; - EVP_MD_CTX *hash; - size_t md_size, orig_len; - int i, ok; - EVP_MD_CTX hmac, *mac_ctx; - uint8_t header[13]; - int t; - - if (send) { - rec = &ssl->s3->wrec; - seq = &ssl->s3->write_sequence[0]; - hash = ssl->write_hash; - } else { - rec = &ssl->s3->rrec; - seq = &ssl->s3->read_sequence[0]; - hash = ssl->read_hash; - } - - t = EVP_MD_CTX_size(hash); - assert(t >= 0); - md_size = t; - - mac_ctx = &hmac; - if (!EVP_MD_CTX_copy(mac_ctx, hash)) { - return -1; - } - - if (SSL_IS_DTLS(ssl)) { - uint8_t dtlsseq[8], *p = dtlsseq; - - s2n(send ? ssl->d1->w_epoch : ssl->d1->r_epoch, p); - memcpy(p, &seq[2], 6); - - memcpy(header, dtlsseq, 8); - } else { - memcpy(header, seq, 8); - } - - /* kludge: tls1_cbc_remove_padding passes padding length in rec->type */ - orig_len = rec->length + md_size + ((unsigned int)rec->type >> 8); - rec->type &= 0xff; - - header[8] = rec->type; - header[9] = (uint8_t)(ssl->version >> 8); - header[10] = (uint8_t)(ssl->version); - header[11] = (rec->length) >> 8; - header[12] = (rec->length) & 0xff; - - if (!send && EVP_CIPHER_CTX_mode(ssl->enc_read_ctx) == EVP_CIPH_CBC_MODE && - ssl3_cbc_record_digest_supported(mac_ctx)) { - /* This is a CBC-encrypted record. We must avoid leaking any timing-side - * channel information about how many blocks of data we are hashing because - * that gives an attacker a timing-oracle. */ - ok = ssl3_cbc_digest_record( - mac_ctx, md, &md_size, header, rec->input, rec->length + md_size, - orig_len, ssl->s3->read_mac_secret, ssl->s3->read_mac_secret_size, - 0 /* not SSLv3 */); - } else { - EVP_DigestSignUpdate(mac_ctx, header, sizeof(header)); - EVP_DigestSignUpdate(mac_ctx, rec->input, rec->length); - ok = EVP_DigestSignFinal(mac_ctx, md, &md_size); - } - - EVP_MD_CTX_cleanup(mac_ctx); - - if (!ok) { - return -1; - } - - if (!SSL_IS_DTLS(ssl)) { - for (i = 7; i >= 0; i--) { - ++seq[i]; - if (seq[i] != 0) { - break; - } - } - } - - return md_size; -} - int tls1_generate_master_secret(SSL *s, uint8_t *out, const uint8_t *premaster, size_t premaster_len) { if (s->s3->tmp.extended_master_secret) { diff --git a/ssl/t1_lib.c b/ssl/t1_lib.c index 9b212a53..a420989c 100644 --- a/ssl/t1_lib.c +++ b/ssl/t1_lib.c @@ -128,7 +128,6 @@ static int ssl_check_serverhello_tlsext(SSL *s); const SSL3_ENC_METHOD TLSv1_enc_data = { tls1_enc, - tls1_mac, tls1_prf, tls1_setup_key_block, tls1_generate_master_secret, @@ -148,7 +147,6 @@ const SSL3_ENC_METHOD TLSv1_enc_data = { const SSL3_ENC_METHOD TLSv1_1_enc_data = { tls1_enc, - tls1_mac, tls1_prf, tls1_setup_key_block, tls1_generate_master_secret, @@ -168,7 +166,6 @@ const SSL3_ENC_METHOD TLSv1_1_enc_data = { const SSL3_ENC_METHOD TLSv1_2_enc_data = { tls1_enc, - tls1_mac, tls1_prf, tls1_setup_key_block, tls1_generate_master_secret,