diff options
Diffstat (limited to 'src/lib/libssl/tls13_client.c')
| -rw-r--r-- | src/lib/libssl/tls13_client.c | 87 |
1 files changed, 81 insertions, 6 deletions
diff --git a/src/lib/libssl/tls13_client.c b/src/lib/libssl/tls13_client.c index 5b4ecdb47d..1729401505 100644 --- a/src/lib/libssl/tls13_client.c +++ b/src/lib/libssl/tls13_client.c | |||
| @@ -1,4 +1,4 @@ | |||
| 1 | /* $OpenBSD: tls13_client.c,v 1.14 2019/03/25 17:21:18 jsing Exp $ */ | 1 | /* $OpenBSD: tls13_client.c,v 1.15 2019/04/04 16:53:57 jsing Exp $ */ |
| 2 | /* | 2 | /* |
| 3 | * Copyright (c) 2018, 2019 Joel Sing <jsing@openbsd.org> | 3 | * Copyright (c) 2018, 2019 Joel Sing <jsing@openbsd.org> |
| 4 | * | 4 | * |
| @@ -81,12 +81,56 @@ tls13_legacy_connect(SSL *ssl) | |||
| 81 | 81 | ||
| 82 | S3I(ssl)->hs.state = SSL_ST_CONNECT; | 82 | S3I(ssl)->hs.state = SSL_ST_CONNECT; |
| 83 | 83 | ||
| 84 | if ((ret = tls13_connect(ctx)) == TLS13_IO_SUCCESS) | 84 | ret = tls13_connect(ctx); |
| 85 | if (ret == TLS13_IO_USE_LEGACY) | ||
| 86 | return ssl->method->internal->ssl_connect(ssl); | ||
| 87 | if (ret == TLS13_IO_SUCCESS) | ||
| 85 | S3I(ssl)->hs.state = SSL_ST_OK; | 88 | S3I(ssl)->hs.state = SSL_ST_OK; |
| 86 | 89 | ||
| 87 | return tls13_legacy_return_code(ssl, ret); | 90 | return tls13_legacy_return_code(ssl, ret); |
| 88 | } | 91 | } |
| 89 | 92 | ||
| 93 | int | ||
| 94 | tls13_use_legacy_client(struct tls13_ctx *ctx) | ||
| 95 | { | ||
| 96 | SSL *s = ctx->ssl; | ||
| 97 | CBS cbs; | ||
| 98 | |||
| 99 | s->method = tls_legacy_client_method(); | ||
| 100 | s->client_version = s->version = s->method->internal->max_version; | ||
| 101 | |||
| 102 | if (!ssl3_setup_init_buffer(s)) | ||
| 103 | goto err; | ||
| 104 | if (!ssl3_setup_buffers(s)) | ||
| 105 | goto err; | ||
| 106 | if (!ssl_init_wbio_buffer(s, 0)) | ||
| 107 | goto err; | ||
| 108 | |||
| 109 | if (s->bbio != s->wbio) | ||
| 110 | s->wbio = BIO_push(s->bbio, s->wbio); | ||
| 111 | |||
| 112 | if (!tls13_handshake_msg_content(ctx->hs_msg, &cbs)) | ||
| 113 | goto err; | ||
| 114 | |||
| 115 | if (!BUF_MEM_grow_clean(s->internal->init_buf, CBS_len(&cbs) + 4)) | ||
| 116 | goto err; | ||
| 117 | |||
| 118 | if (!CBS_write_bytes(&cbs, s->internal->init_buf->data + 4, | ||
| 119 | s->internal->init_buf->length - 4, NULL)) | ||
| 120 | goto err; | ||
| 121 | |||
| 122 | S3I(s)->tmp.reuse_message = 1; | ||
| 123 | S3I(s)->tmp.message_type = tls13_handshake_msg_type(ctx->hs_msg); | ||
| 124 | S3I(s)->tmp.message_size = CBS_len(&cbs); | ||
| 125 | |||
| 126 | S3I(s)->hs.state = SSL3_ST_CR_SRVR_HELLO_A; | ||
| 127 | |||
| 128 | return 1; | ||
| 129 | |||
| 130 | err: | ||
| 131 | return 0; | ||
| 132 | } | ||
| 133 | |||
| 90 | static int | 134 | static int |
| 91 | tls13_client_hello_build(SSL *s, CBB *cbb) | 135 | tls13_client_hello_build(SSL *s, CBB *cbb) |
| 92 | { | 136 | { |
| @@ -156,6 +200,35 @@ static const uint8_t tls13_hello_retry_request_hash[] = { | |||
| 156 | }; | 200 | }; |
| 157 | 201 | ||
| 158 | static int | 202 | static int |
| 203 | tls13_server_hello_is_legacy(CBS *cbs) | ||
| 204 | { | ||
| 205 | CBS extensions_block, extensions, extension_data; | ||
| 206 | uint16_t selected_version = 0; | ||
| 207 | uint16_t type; | ||
| 208 | |||
| 209 | CBS_dup(cbs, &extensions_block); | ||
| 210 | |||
| 211 | if (!CBS_get_u16_length_prefixed(&extensions_block, &extensions)) | ||
| 212 | return 1; | ||
| 213 | |||
| 214 | while (CBS_len(&extensions) > 0) { | ||
| 215 | if (!CBS_get_u16(&extensions, &type)) | ||
| 216 | return 1; | ||
| 217 | if (!CBS_get_u16_length_prefixed(&extensions, &extension_data)) | ||
| 218 | return 1; | ||
| 219 | |||
| 220 | if (type != TLSEXT_TYPE_supported_versions) | ||
| 221 | continue; | ||
| 222 | if (!CBS_get_u16(&extension_data, &selected_version)) | ||
| 223 | return 1; | ||
| 224 | if (CBS_len(&extension_data) != 0) | ||
| 225 | return 1; | ||
| 226 | } | ||
| 227 | |||
| 228 | return (selected_version < TLS1_3_VERSION); | ||
| 229 | } | ||
| 230 | |||
| 231 | static int | ||
| 159 | tls13_server_hello_process(struct tls13_ctx *ctx, CBS *cbs) | 232 | tls13_server_hello_process(struct tls13_ctx *ctx, CBS *cbs) |
| 160 | { | 233 | { |
| 161 | CBS server_random, session_id; | 234 | CBS server_random, session_id; |
| @@ -176,6 +249,9 @@ tls13_server_hello_process(struct tls13_ctx *ctx, CBS *cbs) | |||
| 176 | if (!CBS_get_u8(cbs, &compression_method)) | 249 | if (!CBS_get_u8(cbs, &compression_method)) |
| 177 | goto err; | 250 | goto err; |
| 178 | 251 | ||
| 252 | if (tls13_server_hello_is_legacy(cbs)) | ||
| 253 | return tls13_use_legacy_client(ctx); | ||
| 254 | |||
| 179 | if (!tlsext_client_parse(s, cbs, &alert, SSL_TLSEXT_MSG_SH)) | 255 | if (!tlsext_client_parse(s, cbs, &alert, SSL_TLSEXT_MSG_SH)) |
| 180 | goto err; | 256 | goto err; |
| 181 | 257 | ||
| @@ -259,10 +335,9 @@ tls13_server_hello_recv(struct tls13_ctx *ctx) | |||
| 259 | if (!tls13_server_hello_process(ctx, &cbs)) | 335 | if (!tls13_server_hello_process(ctx, &cbs)) |
| 260 | goto err; | 336 | goto err; |
| 261 | 337 | ||
| 262 | if (ctx->hs->server_version < TLS1_3_VERSION) { | 338 | /* See if we switched back to the legacy client method. */ |
| 263 | /* XXX - switch back to legacy client. */ | 339 | if (s->method->internal->version < TLS1_3_VERSION) |
| 264 | goto err; | 340 | return 1; |
| 265 | } | ||
| 266 | 341 | ||
| 267 | if (ctx->handshake_stage.hs_type & WITH_HRR) | 342 | if (ctx->handshake_stage.hs_type & WITH_HRR) |
| 268 | return 1; | 343 | return 1; |
