Stash the computed version range in SSL_HANDSHAKE.
Avoid dealing with that function call everywhere. Change-Id: I7de64b59c8d17e8286c18a6b20c704e8ba8b9ebe Reviewed-on: https://boringssl-review.googlesource.com/17267 Reviewed-by: Steven Valdez <svaldez@google.com>
This commit is contained in:
parent
fc08dfc4cd
commit
68161cb8ba
@ -567,9 +567,8 @@ static void ssl_get_client_disabled(SSL *ssl, uint32_t *out_mask_a,
|
||||
}
|
||||
}
|
||||
|
||||
static int ssl_write_client_cipher_list(SSL *ssl, CBB *out,
|
||||
uint16_t min_version,
|
||||
uint16_t max_version) {
|
||||
static int ssl_write_client_cipher_list(SSL_HANDSHAKE *hs, CBB *out) {
|
||||
SSL *const ssl = hs->ssl;
|
||||
uint32_t mask_a, mask_k;
|
||||
ssl_get_client_disabled(ssl, &mask_a, &mask_k);
|
||||
|
||||
@ -586,7 +585,7 @@ static int ssl_write_client_cipher_list(SSL *ssl, CBB *out,
|
||||
|
||||
/* Add TLS 1.3 ciphers. Order ChaCha20-Poly1305 relative to AES-GCM based on
|
||||
* hardware support. */
|
||||
if (max_version >= TLS1_3_VERSION) {
|
||||
if (hs->max_version >= TLS1_3_VERSION) {
|
||||
if (!EVP_has_aes_hardware() &&
|
||||
!CBB_add_u16(&child, TLS1_CK_CHACHA20_POLY1305_SHA256 & 0xffff)) {
|
||||
return 0;
|
||||
@ -601,7 +600,7 @@ static int ssl_write_client_cipher_list(SSL *ssl, CBB *out,
|
||||
}
|
||||
}
|
||||
|
||||
if (min_version < TLS1_3_VERSION) {
|
||||
if (hs->min_version < TLS1_3_VERSION) {
|
||||
STACK_OF(SSL_CIPHER) *ciphers = SSL_get_ciphers(ssl);
|
||||
int any_enabled = 0;
|
||||
for (size_t i = 0; i < sk_SSL_CIPHER_num(ciphers); i++) {
|
||||
@ -611,8 +610,8 @@ static int ssl_write_client_cipher_list(SSL *ssl, CBB *out,
|
||||
(cipher->algorithm_auth & mask_a)) {
|
||||
continue;
|
||||
}
|
||||
if (SSL_CIPHER_get_min_version(cipher) > max_version ||
|
||||
SSL_CIPHER_get_max_version(cipher) < min_version) {
|
||||
if (SSL_CIPHER_get_min_version(cipher) > hs->max_version ||
|
||||
SSL_CIPHER_get_max_version(cipher) < hs->min_version) {
|
||||
continue;
|
||||
}
|
||||
any_enabled = 1;
|
||||
@ -622,7 +621,7 @@ static int ssl_write_client_cipher_list(SSL *ssl, CBB *out,
|
||||
}
|
||||
|
||||
/* If all ciphers were disabled, return the error to the caller. */
|
||||
if (!any_enabled && max_version < TLS1_3_VERSION) {
|
||||
if (!any_enabled && hs->max_version < TLS1_3_VERSION) {
|
||||
OPENSSL_PUT_ERROR(SSL, SSL_R_NO_CIPHERS_AVAILABLE);
|
||||
return 0;
|
||||
}
|
||||
@ -630,7 +629,7 @@ static int ssl_write_client_cipher_list(SSL *ssl, CBB *out,
|
||||
|
||||
/* For SSLv3, the SCSV is added. Otherwise the renegotiation extension is
|
||||
* added. */
|
||||
if (max_version == SSL3_VERSION &&
|
||||
if (hs->max_version == SSL3_VERSION &&
|
||||
!ssl->s3->initial_handshake_complete) {
|
||||
if (!CBB_add_u16(&child, SSL3_CK_SCSV & 0xffff)) {
|
||||
return 0;
|
||||
@ -648,11 +647,6 @@ static int ssl_write_client_cipher_list(SSL *ssl, CBB *out,
|
||||
|
||||
int ssl_write_client_hello(SSL_HANDSHAKE *hs) {
|
||||
SSL *const ssl = hs->ssl;
|
||||
uint16_t min_version, max_version;
|
||||
if (!ssl_get_version_range(ssl, &min_version, &max_version)) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
CBB cbb, body;
|
||||
if (!ssl->method->init_message(ssl, &cbb, &body, SSL3_MT_CLIENT_HELLO)) {
|
||||
goto err;
|
||||
@ -681,7 +675,7 @@ int ssl_write_client_hello(SSL_HANDSHAKE *hs) {
|
||||
|
||||
size_t header_len =
|
||||
SSL_is_dtls(ssl) ? DTLS1_HM_HEADER_LENGTH : SSL3_HM_HEADER_LENGTH;
|
||||
if (!ssl_write_client_cipher_list(ssl, &body, min_version, max_version) ||
|
||||
if (!ssl_write_client_cipher_list(hs, &body) ||
|
||||
!CBB_add_u8(&body, 1 /* one compression method */) ||
|
||||
!CBB_add_u8(&body, 0 /* null compression */) ||
|
||||
!ssl_add_clienthello_tlsext(hs, &body, header_len + CBB_len(&body))) {
|
||||
@ -718,12 +712,12 @@ static int ssl3_send_client_hello(SSL_HANDSHAKE *hs) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
uint16_t min_version, max_version;
|
||||
if (!ssl_get_version_range(ssl, &min_version, &max_version)) {
|
||||
/* Freeze the version range. */
|
||||
if (!ssl_get_version_range(ssl, &hs->min_version, &hs->max_version)) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
uint16_t max_wire_version = ssl->method->version_to_wire(max_version);
|
||||
uint16_t max_wire_version = ssl->method->version_to_wire(hs->max_version);
|
||||
assert(hs->state == SSL3_ST_CW_CLNT_HELLO_A);
|
||||
if (!ssl->s3->have_version) {
|
||||
ssl->version = max_wire_version;
|
||||
@ -733,7 +727,7 @@ static int ssl3_send_client_hello(SSL_HANDSHAKE *hs) {
|
||||
* even on renegotiation. The static RSA key exchange uses this field, and
|
||||
* some servers fail when it changes across handshakes. */
|
||||
hs->client_version = max_wire_version;
|
||||
if (max_version >= TLS1_3_VERSION) {
|
||||
if (hs->max_version >= TLS1_3_VERSION) {
|
||||
hs->client_version = ssl->method->version_to_wire(TLS1_2_VERSION);
|
||||
}
|
||||
|
||||
@ -748,7 +742,8 @@ static int ssl3_send_client_hello(SSL_HANDSHAKE *hs) {
|
||||
ssl->session->session_id_length == 0) ||
|
||||
ssl->session->not_resumable ||
|
||||
!ssl_session_is_time_valid(ssl, ssl->session) ||
|
||||
session_version < min_version || session_version > max_version) {
|
||||
session_version < hs->min_version ||
|
||||
session_version > hs->max_version) {
|
||||
ssl_set_session(ssl, NULL);
|
||||
}
|
||||
}
|
||||
@ -837,10 +832,9 @@ static int ssl3_get_server_hello(SSL_HANDSHAKE *hs) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
uint16_t min_version, max_version, server_version;
|
||||
if (!ssl_get_version_range(ssl, &min_version, &max_version) ||
|
||||
!ssl->method->version_from_wire(&server_version, server_wire_version) ||
|
||||
server_version < min_version || server_version > max_version) {
|
||||
uint16_t server_version;
|
||||
if (!ssl->method->version_from_wire(&server_version, server_wire_version) ||
|
||||
server_version < hs->min_version || server_version > hs->max_version) {
|
||||
OPENSSL_PUT_ERROR(SSL, SSL_R_UNSUPPORTED_PROTOCOL);
|
||||
ssl3_send_alert(ssl, SSL3_AL_FATAL, SSL_AD_PROTOCOL_VERSION);
|
||||
return -1;
|
||||
|
@ -471,12 +471,6 @@ static int negotiate_version(SSL_HANDSHAKE *hs, uint8_t *out_alert,
|
||||
const SSL_CLIENT_HELLO *client_hello) {
|
||||
SSL *const ssl = hs->ssl;
|
||||
assert(!ssl->s3->have_version);
|
||||
uint16_t min_version, max_version;
|
||||
if (!ssl_get_version_range(ssl, &min_version, &max_version)) {
|
||||
*out_alert = SSL_AD_PROTOCOL_VERSION;
|
||||
return 0;
|
||||
}
|
||||
|
||||
uint16_t version = 0;
|
||||
/* Check supported_versions extension if it is present. */
|
||||
CBS supported_versions;
|
||||
@ -505,8 +499,8 @@ static int negotiate_version(SSL_HANDSHAKE *hs, uint8_t *out_alert,
|
||||
if (!ssl->method->version_from_wire(&ext_version, ext_version)) {
|
||||
continue;
|
||||
}
|
||||
if (min_version <= ext_version &&
|
||||
ext_version <= max_version &&
|
||||
if (hs->min_version <= ext_version &&
|
||||
ext_version <= hs->max_version &&
|
||||
(!found_version || version < ext_version)) {
|
||||
version = ext_version;
|
||||
found_version = 1;
|
||||
@ -542,11 +536,11 @@ static int negotiate_version(SSL_HANDSHAKE *hs, uint8_t *out_alert,
|
||||
}
|
||||
|
||||
/* Apply our minimum and maximum version. */
|
||||
if (version > max_version) {
|
||||
version = max_version;
|
||||
if (version > hs->max_version) {
|
||||
version = hs->max_version;
|
||||
}
|
||||
|
||||
if (version < min_version) {
|
||||
if (version < hs->min_version) {
|
||||
goto unsupported_protocol;
|
||||
}
|
||||
}
|
||||
@ -554,7 +548,7 @@ static int negotiate_version(SSL_HANDSHAKE *hs, uint8_t *out_alert,
|
||||
/* Handle FALLBACK_SCSV. */
|
||||
if (ssl_client_cipher_list_contains_cipher(client_hello,
|
||||
SSL3_CK_FALLBACK_SCSV & 0xffff) &&
|
||||
version < max_version) {
|
||||
version < hs->max_version) {
|
||||
OPENSSL_PUT_ERROR(SSL, SSL_R_INAPPROPRIATE_FALLBACK);
|
||||
*out_alert = SSL3_AD_INAPPROPRIATE_FALLBACK;
|
||||
return 0;
|
||||
@ -754,6 +748,11 @@ static int ssl3_process_client_hello(SSL_HANDSHAKE *hs) {
|
||||
}
|
||||
}
|
||||
|
||||
/* Freeze the version range after the early callback. */
|
||||
if (!ssl_get_version_range(ssl, &hs->min_version, &hs->max_version)) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
uint8_t alert = SSL_AD_DECODE_ERROR;
|
||||
if (!negotiate_version(hs, &alert, &client_hello)) {
|
||||
ssl3_send_alert(ssl, SSL3_AL_FATAL, alert);
|
||||
|
@ -950,6 +950,14 @@ struct ssl_handshake_st {
|
||||
* depend on |do_tls13_handshake| but the starting state is always zero. */
|
||||
int tls13_state;
|
||||
|
||||
/* min_version is the minimum accepted protocol version, taking account both
|
||||
* |SSL_OP_NO_*| and |SSL_CTX_set_min_proto_version| APIs. */
|
||||
uint16_t min_version;
|
||||
|
||||
/* max_version is the maximum accepted protocol version, taking account both
|
||||
* |SSL_OP_NO_*| and |SSL_CTX_set_max_proto_version| APIs. */
|
||||
uint16_t max_version;
|
||||
|
||||
size_t hash_len;
|
||||
uint8_t secret[EVP_MAX_MD_SIZE];
|
||||
uint8_t early_traffic_secret[EVP_MAX_MD_SIZE];
|
||||
|
74
ssl/t1_lib.c
74
ssl/t1_lib.c
@ -722,13 +722,8 @@ static int ext_sni_add_serverhello(SSL_HANDSHAKE *hs, CBB *out) {
|
||||
|
||||
static int ext_ri_add_clienthello(SSL_HANDSHAKE *hs, CBB *out) {
|
||||
SSL *const ssl = hs->ssl;
|
||||
uint16_t min_version, max_version;
|
||||
if (!ssl_get_version_range(ssl, &min_version, &max_version)) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Renegotiation indication is not necessary in TLS 1.3. */
|
||||
if (min_version >= TLS1_3_VERSION) {
|
||||
if (hs->min_version >= TLS1_3_VERSION) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
@ -883,13 +878,8 @@ static int ext_ri_add_serverhello(SSL_HANDSHAKE *hs, CBB *out) {
|
||||
* https://tools.ietf.org/html/rfc7627 */
|
||||
|
||||
static int ext_ems_add_clienthello(SSL_HANDSHAKE *hs, CBB *out) {
|
||||
uint16_t min_version, max_version;
|
||||
if (!ssl_get_version_range(hs->ssl, &min_version, &max_version)) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Extended master secret is not necessary in TLS 1.3. */
|
||||
if (min_version >= TLS1_3_VERSION || max_version <= SSL3_VERSION) {
|
||||
if (hs->min_version >= TLS1_3_VERSION || hs->max_version <= SSL3_VERSION) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
@ -967,13 +957,8 @@ static int ext_ems_add_serverhello(SSL_HANDSHAKE *hs, CBB *out) {
|
||||
|
||||
static int ext_ticket_add_clienthello(SSL_HANDSHAKE *hs, CBB *out) {
|
||||
SSL *const ssl = hs->ssl;
|
||||
uint16_t min_version, max_version;
|
||||
if (!ssl_get_version_range(ssl, &min_version, &max_version)) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* TLS 1.3 uses a different ticket extension. */
|
||||
if (min_version >= TLS1_3_VERSION ||
|
||||
if (hs->min_version >= TLS1_3_VERSION ||
|
||||
SSL_get_options(ssl) & SSL_OP_NO_TICKET) {
|
||||
return 1;
|
||||
}
|
||||
@ -1055,12 +1040,7 @@ static int ext_ticket_add_serverhello(SSL_HANDSHAKE *hs, CBB *out) {
|
||||
|
||||
static int ext_sigalgs_add_clienthello(SSL_HANDSHAKE *hs, CBB *out) {
|
||||
SSL *const ssl = hs->ssl;
|
||||
uint16_t min_version, max_version;
|
||||
if (!ssl_get_version_range(ssl, &min_version, &max_version)) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (max_version < TLS1_2_VERSION) {
|
||||
if (hs->max_version < TLS1_2_VERSION) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
@ -1814,13 +1794,8 @@ static int ext_ec_point_add_extension(SSL_HANDSHAKE *hs, CBB *out) {
|
||||
}
|
||||
|
||||
static int ext_ec_point_add_clienthello(SSL_HANDSHAKE *hs, CBB *out) {
|
||||
uint16_t min_version, max_version;
|
||||
if (!ssl_get_version_range(hs->ssl, &min_version, &max_version)) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* The point format extension is unneccessary in TLS 1.3. */
|
||||
if (min_version >= TLS1_3_VERSION) {
|
||||
if (hs->min_version >= TLS1_3_VERSION) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
@ -1888,13 +1863,8 @@ static int ext_ec_point_add_serverhello(SSL_HANDSHAKE *hs, CBB *out) {
|
||||
|
||||
static size_t ext_pre_shared_key_clienthello_length(SSL_HANDSHAKE *hs) {
|
||||
SSL *const ssl = hs->ssl;
|
||||
uint16_t min_version, max_version;
|
||||
if (!ssl_get_version_range(ssl, &min_version, &max_version)) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
uint16_t session_version;
|
||||
if (max_version < TLS1_3_VERSION || ssl->session == NULL ||
|
||||
if (hs->max_version < TLS1_3_VERSION || ssl->session == NULL ||
|
||||
!ssl->method->version_from_wire(&session_version,
|
||||
ssl->session->ssl_version) ||
|
||||
session_version < TLS1_3_VERSION) {
|
||||
@ -1913,13 +1883,8 @@ static size_t ext_pre_shared_key_clienthello_length(SSL_HANDSHAKE *hs) {
|
||||
|
||||
static int ext_pre_shared_key_add_clienthello(SSL_HANDSHAKE *hs, CBB *out) {
|
||||
SSL *const ssl = hs->ssl;
|
||||
uint16_t min_version, max_version;
|
||||
if (!ssl_get_version_range(ssl, &min_version, &max_version)) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
uint16_t session_version;
|
||||
if (max_version < TLS1_3_VERSION || ssl->session == NULL ||
|
||||
if (hs->max_version < TLS1_3_VERSION || ssl->session == NULL ||
|
||||
!ssl->method->version_from_wire(&session_version,
|
||||
ssl->session->ssl_version) ||
|
||||
session_version < TLS1_3_VERSION) {
|
||||
@ -2062,13 +2027,7 @@ int ssl_ext_pre_shared_key_add_serverhello(SSL_HANDSHAKE *hs, CBB *out) {
|
||||
|
||||
static int ext_psk_key_exchange_modes_add_clienthello(SSL_HANDSHAKE *hs,
|
||||
CBB *out) {
|
||||
SSL *const ssl = hs->ssl;
|
||||
uint16_t min_version, max_version;
|
||||
if (!ssl_get_version_range(ssl, &min_version, &max_version)) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (max_version < TLS1_3_VERSION) {
|
||||
if (hs->max_version < TLS1_3_VERSION) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
@ -2194,12 +2153,7 @@ static int ext_early_data_add_serverhello(SSL_HANDSHAKE *hs, CBB *out) {
|
||||
|
||||
static int ext_key_share_add_clienthello(SSL_HANDSHAKE *hs, CBB *out) {
|
||||
SSL *const ssl = hs->ssl;
|
||||
uint16_t min_version, max_version;
|
||||
if (!ssl_get_version_range(ssl, &min_version, &max_version)) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (max_version < TLS1_3_VERSION) {
|
||||
if (hs->max_version < TLS1_3_VERSION) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
@ -2404,12 +2358,7 @@ int ssl_ext_key_share_add_serverhello(SSL_HANDSHAKE *hs, CBB *out) {
|
||||
|
||||
static int ext_supported_versions_add_clienthello(SSL_HANDSHAKE *hs, CBB *out) {
|
||||
SSL *const ssl = hs->ssl;
|
||||
uint16_t min_version, max_version;
|
||||
if (!ssl_get_version_range(ssl, &min_version, &max_version)) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (max_version <= TLS1_2_VERSION) {
|
||||
if (hs->max_version <= TLS1_2_VERSION) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
@ -2426,7 +2375,8 @@ static int ext_supported_versions_add_clienthello(SSL_HANDSHAKE *hs, CBB *out) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
for (uint16_t version = max_version; version >= min_version; version--) {
|
||||
for (uint16_t version = hs->max_version; version >= hs->min_version;
|
||||
version--) {
|
||||
if (!CBB_add_u16(&versions, ssl->method->version_to_wire(version))) {
|
||||
return 0;
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user