summaryrefslogtreecommitdiff
path: root/src/lib
diff options
context:
space:
mode:
authorjsing <>2018-09-05 16:48:11 +0000
committerjsing <>2018-09-05 16:48:11 +0000
commit3dd336e6ff4073ca34d5f248d90afd65c6e3f27f (patch)
tree7285548c994d450785c9af93c1936fef8e5ee489 /src/lib
parent500c35c4f020d87efbd1b5f638d51d78cce1b5ea (diff)
downloadopenbsd-3dd336e6ff4073ca34d5f248d90afd65c6e3f27f.tar.gz
openbsd-3dd336e6ff4073ca34d5f248d90afd65c6e3f27f.tar.bz2
openbsd-3dd336e6ff4073ca34d5f248d90afd65c6e3f27f.zip
Correctly clear the current cipher state, when changing cipher state.
When a renegotiation results in a change of cipher suite, the renegotation would fail if it switched from AEAD to non-AEAD or vice versa. This is due to the fact that the previous EVP_AEAD or EVP_CIPHER state remained, resulting in incorrect logic that caused MAC failures. Rename ssl_clear_cipher_ctx() to ssl_clear_cipher_state() and split it into separate read/write components, then call these functions from the appropriate places when a ChangeCipherSpec message is being processed. Also, remove the separate ssl_clear_hash_ctx() calls and fold these into the ssl_clear_cipher_{read,write}_state() functions. Issue reported by Bernard Spil, who also tested this diff. ok tb@
Diffstat (limited to 'src/lib')
-rw-r--r--src/lib/libssl/ssl_lib.c52
-rw-r--r--src/lib/libssl/ssl_locl.h7
-rw-r--r--src/lib/libssl/t1_enc.c19
3 files changed, 37 insertions, 41 deletions
diff --git a/src/lib/libssl/ssl_lib.c b/src/lib/libssl/ssl_lib.c
index 938139e18e..44d11d4b16 100644
--- a/src/lib/libssl/ssl_lib.c
+++ b/src/lib/libssl/ssl_lib.c
@@ -1,4 +1,4 @@
1/* $OpenBSD: ssl_lib.c,v 1.187 2018/08/30 16:56:16 jsing Exp $ */ 1/* $OpenBSD: ssl_lib.c,v 1.188 2018/09/05 16:48:11 jsing Exp $ */
2/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) 2/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
3 * All rights reserved. 3 * All rights reserved.
4 * 4 *
@@ -191,9 +191,7 @@ SSL_clear(SSL *s)
191 BUF_MEM_free(s->internal->init_buf); 191 BUF_MEM_free(s->internal->init_buf);
192 s->internal->init_buf = NULL; 192 s->internal->init_buf = NULL;
193 193
194 ssl_clear_cipher_ctx(s); 194 ssl_clear_cipher_state(s);
195 ssl_clear_hash_ctx(&s->read_hash);
196 ssl_clear_hash_ctx(&s->internal->write_hash);
197 195
198 s->internal->first_packet = 0; 196 s->internal->first_packet = 0;
199 197
@@ -534,9 +532,7 @@ SSL_free(SSL *s)
534 SSL_SESSION_free(s->session); 532 SSL_SESSION_free(s->session);
535 } 533 }
536 534
537 ssl_clear_cipher_ctx(s); 535 ssl_clear_cipher_state(s);
538 ssl_clear_hash_ctx(&s->read_hash);
539 ssl_clear_hash_ctx(&s->internal->write_hash);
540 536
541 ssl_cert_free(s->cert); 537 ssl_cert_free(s->cert);
542 538
@@ -2431,10 +2427,7 @@ SSL_set_accept_state(SSL *s)
2431 s->internal->shutdown = 0; 2427 s->internal->shutdown = 0;
2432 S3I(s)->hs.state = SSL_ST_ACCEPT|SSL_ST_BEFORE; 2428 S3I(s)->hs.state = SSL_ST_ACCEPT|SSL_ST_BEFORE;
2433 s->internal->handshake_func = s->method->internal->ssl_accept; 2429 s->internal->handshake_func = s->method->internal->ssl_accept;
2434 /* clear the current cipher */ 2430 ssl_clear_cipher_state(s);
2435 ssl_clear_cipher_ctx(s);
2436 ssl_clear_hash_ctx(&s->read_hash);
2437 ssl_clear_hash_ctx(&s->internal->write_hash);
2438} 2431}
2439 2432
2440void 2433void
@@ -2444,10 +2437,7 @@ SSL_set_connect_state(SSL *s)
2444 s->internal->shutdown = 0; 2437 s->internal->shutdown = 0;
2445 S3I(s)->hs.state = SSL_ST_CONNECT|SSL_ST_BEFORE; 2438 S3I(s)->hs.state = SSL_ST_CONNECT|SSL_ST_BEFORE;
2446 s->internal->handshake_func = s->method->internal->ssl_connect; 2439 s->internal->handshake_func = s->method->internal->ssl_connect;
2447 /* clear the current cipher */ 2440 ssl_clear_cipher_state(s);
2448 ssl_clear_cipher_ctx(s);
2449 ssl_clear_hash_ctx(&s->read_hash);
2450 ssl_clear_hash_ctx(&s->internal->write_hash);
2451} 2441}
2452 2442
2453int 2443int
@@ -2623,24 +2613,40 @@ SSL_dup(SSL *s)
2623} 2613}
2624 2614
2625void 2615void
2626ssl_clear_cipher_ctx(SSL *s) 2616ssl_clear_cipher_state(SSL *s)
2617{
2618 ssl_clear_cipher_read_state(s);
2619 ssl_clear_cipher_write_state(s);
2620}
2621
2622void
2623ssl_clear_cipher_read_state(SSL *s)
2627{ 2624{
2628 EVP_CIPHER_CTX_free(s->enc_read_ctx); 2625 EVP_CIPHER_CTX_free(s->enc_read_ctx);
2629 s->enc_read_ctx = NULL; 2626 s->enc_read_ctx = NULL;
2630 EVP_CIPHER_CTX_free(s->internal->enc_write_ctx); 2627 EVP_MD_CTX_destroy(s->read_hash);
2631 s->internal->enc_write_ctx = NULL; 2628 s->read_hash = NULL;
2632 2629
2633 if (s->internal->aead_read_ctx != NULL) { 2630 if (s->internal->aead_read_ctx != NULL) {
2634 EVP_AEAD_CTX_cleanup(&s->internal->aead_read_ctx->ctx); 2631 EVP_AEAD_CTX_cleanup(&s->internal->aead_read_ctx->ctx);
2635 free(s->internal->aead_read_ctx); 2632 free(s->internal->aead_read_ctx);
2636 s->internal->aead_read_ctx = NULL; 2633 s->internal->aead_read_ctx = NULL;
2637 } 2634 }
2635}
2636
2637void
2638ssl_clear_cipher_write_state(SSL *s)
2639{
2640 EVP_CIPHER_CTX_free(s->internal->enc_write_ctx);
2641 s->internal->enc_write_ctx = NULL;
2642 EVP_MD_CTX_destroy(s->internal->write_hash);
2643 s->internal->write_hash = NULL;
2644
2638 if (s->internal->aead_write_ctx != NULL) { 2645 if (s->internal->aead_write_ctx != NULL) {
2639 EVP_AEAD_CTX_cleanup(&s->internal->aead_write_ctx->ctx); 2646 EVP_AEAD_CTX_cleanup(&s->internal->aead_write_ctx->ctx);
2640 free(s->internal->aead_write_ctx); 2647 free(s->internal->aead_write_ctx);
2641 s->internal->aead_write_ctx = NULL; 2648 s->internal->aead_write_ctx = NULL;
2642 } 2649 }
2643
2644} 2650}
2645 2651
2646/* Fix this function so that it takes an optional type parameter */ 2652/* Fix this function so that it takes an optional type parameter */
@@ -3021,14 +3027,6 @@ SSL_set_msg_callback(SSL *ssl, void (*cb)(int write_p, int version,
3021} 3027}
3022 3028
3023void 3029void
3024ssl_clear_hash_ctx(EVP_MD_CTX **hash)
3025{
3026 if (*hash)
3027 EVP_MD_CTX_destroy(*hash);
3028 *hash = NULL;
3029}
3030
3031void
3032SSL_set_debug(SSL *s, int debug) 3030SSL_set_debug(SSL *s, int debug)
3033{ 3031{
3034 s->internal->debug = debug; 3032 s->internal->debug = debug;
diff --git a/src/lib/libssl/ssl_locl.h b/src/lib/libssl/ssl_locl.h
index b6d71492fd..a4e831577d 100644
--- a/src/lib/libssl/ssl_locl.h
+++ b/src/lib/libssl/ssl_locl.h
@@ -1,4 +1,4 @@
1/* $OpenBSD: ssl_locl.h,v 1.212 2018/08/30 16:56:16 jsing Exp $ */ 1/* $OpenBSD: ssl_locl.h,v 1.213 2018/09/05 16:48:11 jsing Exp $ */
2/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) 2/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
3 * All rights reserved. 3 * All rights reserved.
4 * 4 *
@@ -1039,7 +1039,9 @@ extern SSL3_ENC_METHOD TLSv1_enc_data;
1039extern SSL3_ENC_METHOD TLSv1_1_enc_data; 1039extern SSL3_ENC_METHOD TLSv1_1_enc_data;
1040extern SSL3_ENC_METHOD TLSv1_2_enc_data; 1040extern SSL3_ENC_METHOD TLSv1_2_enc_data;
1041 1041
1042void ssl_clear_cipher_ctx(SSL *s); 1042void ssl_clear_cipher_state(SSL *s);
1043void ssl_clear_cipher_read_state(SSL *s);
1044void ssl_clear_cipher_write_state(SSL *s);
1043int ssl_clear_bad_session(SSL *s); 1045int ssl_clear_bad_session(SSL *s);
1044CERT *ssl_cert_new(void); 1046CERT *ssl_cert_new(void);
1045CERT *ssl_cert_dup(CERT *cert); 1047CERT *ssl_cert_dup(CERT *cert);
@@ -1279,7 +1281,6 @@ int tls12_get_sigid(const EVP_PKEY *pk);
1279int tls12_get_hashandsig(CBB *cbb, const EVP_PKEY *pk, const EVP_MD *md); 1281int tls12_get_hashandsig(CBB *cbb, const EVP_PKEY *pk, const EVP_MD *md);
1280const EVP_MD *tls12_get_hash(unsigned char hash_alg); 1282const EVP_MD *tls12_get_hash(unsigned char hash_alg);
1281 1283
1282void ssl_clear_hash_ctx(EVP_MD_CTX **hash);
1283long ssl_get_algorithm2(SSL *s); 1284long ssl_get_algorithm2(SSL *s);
1284int tls1_process_sigalgs(SSL *s, CBS *cbs); 1285int tls1_process_sigalgs(SSL *s, CBS *cbs);
1285void tls12_get_req_sig_algs(SSL *s, unsigned char **sigalgs, 1286void tls12_get_req_sig_algs(SSL *s, unsigned char **sigalgs,
diff --git a/src/lib/libssl/t1_enc.c b/src/lib/libssl/t1_enc.c
index 24fc8ede68..39f542215b 100644
--- a/src/lib/libssl/t1_enc.c
+++ b/src/lib/libssl/t1_enc.c
@@ -1,4 +1,4 @@
1/* $OpenBSD: t1_enc.c,v 1.110 2018/08/31 18:31:34 jsing Exp $ */ 1/* $OpenBSD: t1_enc.c,v 1.111 2018/09/05 16:48:11 jsing Exp $ */
2/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) 2/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
3 * All rights reserved. 3 * All rights reserved.
4 * 4 *
@@ -397,10 +397,13 @@ tls1_change_cipher_state_aead(SSL *s, char is_read, const unsigned char *key,
397 SSL_AEAD_CTX *aead_ctx; 397 SSL_AEAD_CTX *aead_ctx;
398 398
399 if (is_read) { 399 if (is_read) {
400 ssl_clear_cipher_read_state(s);
400 if (!tls1_aead_ctx_init(&s->internal->aead_read_ctx)) 401 if (!tls1_aead_ctx_init(&s->internal->aead_read_ctx))
401 return 0; 402 return 0;
402 aead_ctx = s->internal->aead_read_ctx; 403 aead_ctx = s->internal->aead_read_ctx;
403 } else { 404 } else {
405 /* XXX - Need to correctly handle DTLS. */
406 ssl_clear_cipher_write_state(s);
404 if (!tls1_aead_ctx_init(&s->internal->aead_write_ctx)) 407 if (!tls1_aead_ctx_init(&s->internal->aead_write_ctx))
405 return 0; 408 return 0;
406 aead_ctx = s->internal->aead_write_ctx; 409 aead_ctx = s->internal->aead_write_ctx;
@@ -468,10 +471,7 @@ tls1_change_cipher_state_cipher(SSL *s, char is_read,
468 else 471 else
469 s->internal->mac_flags &= ~SSL_MAC_FLAG_READ_MAC_STREAM; 472 s->internal->mac_flags &= ~SSL_MAC_FLAG_READ_MAC_STREAM;
470 473
471 EVP_CIPHER_CTX_free(s->enc_read_ctx); 474 ssl_clear_cipher_read_state(s);
472 s->enc_read_ctx = NULL;
473 EVP_MD_CTX_destroy(s->read_hash);
474 s->read_hash = NULL;
475 475
476 if ((cipher_ctx = EVP_CIPHER_CTX_new()) == NULL) 476 if ((cipher_ctx = EVP_CIPHER_CTX_new()) == NULL)
477 goto err; 477 goto err;
@@ -492,12 +492,9 @@ tls1_change_cipher_state_cipher(SSL *s, char is_read,
492 * contexts that are used for DTLS - these are instead freed 492 * contexts that are used for DTLS - these are instead freed
493 * by DTLS when its frees a ChangeCipherSpec fragment. 493 * by DTLS when its frees a ChangeCipherSpec fragment.
494 */ 494 */
495 if (!SSL_IS_DTLS(s)) { 495 if (!SSL_IS_DTLS(s))
496 EVP_CIPHER_CTX_free(s->internal->enc_write_ctx); 496 ssl_clear_cipher_write_state(s);
497 s->internal->enc_write_ctx = NULL; 497
498 EVP_MD_CTX_destroy(s->internal->write_hash);
499 s->internal->write_hash = NULL;
500 }
501 if ((cipher_ctx = EVP_CIPHER_CTX_new()) == NULL) 498 if ((cipher_ctx = EVP_CIPHER_CTX_new()) == NULL)
502 goto err; 499 goto err;
503 s->internal->enc_write_ctx = cipher_ctx; 500 s->internal->enc_write_ctx = cipher_ctx;