blob: d84433824a24676d1bd7aab7871ef7b4502e47dd [file] [log] [blame]
Steven Valdez143e8b32016-07-11 13:19:03 -04001/* Copyright (c) 2016, Google Inc.
2 *
3 * Permission to use, copy, modify, and/or distribute this software for any
4 * purpose with or without fee is hereby granted, provided that the above
5 * copyright notice and this permission notice appear in all copies.
6 *
7 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
8 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
9 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
10 * SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
11 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
12 * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
13 * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */
14
15#include <openssl/ssl.h>
16
17#include <assert.h>
18#include <string.h>
19
20#include <openssl/bytestring.h>
21#include <openssl/digest.h>
22#include <openssl/err.h>
23#include <openssl/mem.h>
24#include <openssl/rand.h>
25#include <openssl/stack.h>
26
27#include "internal.h"
28
29
30enum server_hs_state_t {
31 state_process_client_hello = 0,
Steven Valdez5440fe02016-07-18 12:40:30 -040032 state_send_hello_retry_request,
33 state_flush_hello_retry_request,
34 state_process_second_client_hello,
Steven Valdez143e8b32016-07-11 13:19:03 -040035 state_send_server_hello,
36 state_send_encrypted_extensions,
37 state_send_certificate_request,
38 state_send_server_certificate,
39 state_send_server_certificate_verify,
40 state_complete_server_certificate_verify,
41 state_send_server_finished,
42 state_flush,
Steven Valdez143e8b32016-07-11 13:19:03 -040043 state_process_client_certificate,
44 state_process_client_certificate_verify,
45 state_process_client_finished,
46 state_done,
47};
48
Steven Valdez5440fe02016-07-18 12:40:30 -040049static const uint8_t kZeroes[EVP_MAX_MD_SIZE] = {0};
50
51static int resolve_psk_secret(SSL *ssl) {
52 SSL_HANDSHAKE *hs = ssl->s3->hs;
53
54 if (ssl->s3->tmp.new_cipher->algorithm_auth != SSL_aPSK) {
55 return tls13_advance_key_schedule(ssl, kZeroes, hs->hash_len);
56 }
57
58 /* TODO(davidben): Support PSK. */
59 OPENSSL_PUT_ERROR(SSL, ERR_R_INTERNAL_ERROR);
60 return 0;
61}
62
63static int resolve_ecdhe_secret(SSL *ssl, int *out_need_retry,
64 struct ssl_early_callback_ctx *early_ctx) {
65 *out_need_retry = 0;
66 SSL_HANDSHAKE *hs = ssl->s3->hs;
67
68 if (ssl->s3->tmp.new_cipher->algorithm_mkey != SSL_kECDHE) {
69 return tls13_advance_key_schedule(ssl, kZeroes, hs->hash_len);
70 }
71
72 const uint8_t *key_share_buf = NULL;
73 size_t key_share_len = 0;
74 CBS key_share;
75 if (!SSL_early_callback_ctx_extension_get(early_ctx, TLSEXT_TYPE_key_share,
76 &key_share_buf, &key_share_len)) {
77 OPENSSL_PUT_ERROR(SSL, SSL_R_MISSING_KEY_SHARE);
78 ssl3_send_alert(ssl, SSL3_AL_FATAL, SSL_AD_MISSING_EXTENSION);
79 return ssl_hs_error;
80 }
81
82 CBS_init(&key_share, key_share_buf, key_share_len);
83 int found_key_share;
84 uint8_t *dhe_secret;
85 size_t dhe_secret_len;
86 uint8_t alert;
Steven Valdez7259f2f2016-08-02 16:55:05 -040087 if (!ssl_ext_key_share_parse_clienthello(ssl, &found_key_share, &dhe_secret,
88 &dhe_secret_len, &alert,
89 &key_share)) {
Steven Valdez5440fe02016-07-18 12:40:30 -040090 ssl3_send_alert(ssl, SSL3_AL_FATAL, alert);
91 return 0;
92 }
93
94 if (!found_key_share) {
95 *out_need_retry = 1;
96 return 0;
97 }
98
99 int ok = tls13_advance_key_schedule(ssl, dhe_secret, dhe_secret_len);
100 OPENSSL_free(dhe_secret);
101 return ok;
102}
103
Steven Valdez143e8b32016-07-11 13:19:03 -0400104static enum ssl_hs_wait_t do_process_client_hello(SSL *ssl, SSL_HANDSHAKE *hs) {
105 if (!tls13_check_message_type(ssl, SSL3_MT_CLIENT_HELLO)) {
106 return ssl_hs_error;
107 }
108
109 struct ssl_early_callback_ctx early_ctx;
David Benjamind7573dc2016-07-20 19:05:22 +0200110 if (!ssl_early_callback_init(ssl, &early_ctx, ssl->init_msg,
111 ssl->init_num)) {
Steven Valdez143e8b32016-07-11 13:19:03 -0400112 OPENSSL_PUT_ERROR(SSL, SSL_R_CLIENTHELLO_PARSE_FAILED);
113 ssl3_send_alert(ssl, SSL3_AL_FATAL, SSL_AD_DECODE_ERROR);
114 return ssl_hs_error;
115 }
116
David Benjamind7573dc2016-07-20 19:05:22 +0200117 CBS cbs, client_random, session_id, cipher_suites, compression_methods;
118 uint16_t client_wire_version;
Steven Valdez143e8b32016-07-11 13:19:03 -0400119 CBS_init(&cbs, ssl->init_msg, ssl->init_num);
120 if (!CBS_get_u16(&cbs, &client_wire_version) ||
121 !CBS_get_bytes(&cbs, &client_random, SSL3_RANDOM_SIZE) ||
122 !CBS_get_u8_length_prefixed(&cbs, &session_id) ||
123 CBS_len(&session_id) > SSL_MAX_SSL_SESSION_ID_LENGTH) {
124 OPENSSL_PUT_ERROR(SSL, SSL_R_DECODE_ERROR);
125 ssl3_send_alert(ssl, SSL3_AL_FATAL, SSL_AD_DECODE_ERROR);
126 return ssl_hs_error;
127 }
128
129 uint16_t min_version, max_version;
130 if (!ssl_get_version_range(ssl, &min_version, &max_version)) {
131 ssl3_send_alert(ssl, SSL3_AL_FATAL, SSL_AD_INTERNAL_ERROR);
132 return ssl_hs_error;
133 }
134
135 assert(ssl->s3->have_version);
136
137 /* Load the client random. */
138 memcpy(ssl->s3->client_random, CBS_data(&client_random), SSL3_RANDOM_SIZE);
139
Steven Valdez87eab492016-06-27 16:34:59 -0400140 SSL_set_session(ssl, NULL);
Steven Valdez143e8b32016-07-11 13:19:03 -0400141 if (!ssl_get_new_session(ssl, 1 /* server */)) {
142 ssl3_send_alert(ssl, SSL3_AL_FATAL, SSL_AD_INTERNAL_ERROR);
143 return ssl_hs_error;
144 }
145
146 if (ssl->ctx->dos_protection_cb != NULL &&
147 ssl->ctx->dos_protection_cb(&early_ctx) == 0) {
148 /* Connection rejected for DOS reasons. */
149 OPENSSL_PUT_ERROR(SSL, SSL_R_CONNECTION_REJECTED);
150 ssl3_send_alert(ssl, SSL3_AL_FATAL, SSL_AD_ACCESS_DENIED);
151 return ssl_hs_error;
152 }
153
154 if (!CBS_get_u16_length_prefixed(&cbs, &cipher_suites) ||
155 CBS_len(&cipher_suites) == 0 ||
156 CBS_len(&cipher_suites) % 2 != 0 ||
157 !CBS_get_u8_length_prefixed(&cbs, &compression_methods) ||
158 CBS_len(&compression_methods) == 0) {
159 OPENSSL_PUT_ERROR(SSL, SSL_R_DECODE_ERROR);
160 ssl3_send_alert(ssl, SSL3_AL_FATAL, SSL_AD_DECODE_ERROR);
161 return ssl_hs_error;
162 }
163
164 /* TLS 1.3 requires the peer only advertise the null compression. */
165 if (CBS_len(&compression_methods) != 1 ||
166 CBS_data(&compression_methods)[0] != 0) {
167 OPENSSL_PUT_ERROR(SSL, SSL_R_INVALID_COMPRESSION_LIST);
168 ssl3_send_alert(ssl, SSL3_AL_FATAL, SSL_AD_ILLEGAL_PARAMETER);
169 return ssl_hs_error;
170 }
171
172 /* TLS extensions. */
173 if (!ssl_parse_clienthello_tlsext(ssl, &cbs)) {
174 OPENSSL_PUT_ERROR(SSL, SSL_R_PARSE_TLSEXT);
175 return ssl_hs_error;
176 }
177
178 /* There should be nothing left over in the message. */
179 if (CBS_len(&cbs) != 0) {
180 OPENSSL_PUT_ERROR(SSL, SSL_R_BAD_PACKET_LENGTH);
181 ssl3_send_alert(ssl, SSL3_AL_FATAL, SSL_AD_DECODE_ERROR);
182 return ssl_hs_error;
183 }
184
185 /* Let cert callback update server certificates if required.
186 *
187 * TODO(davidben): Can this get run earlier? */
188 if (ssl->cert->cert_cb != NULL) {
189 int rv = ssl->cert->cert_cb(ssl, ssl->cert->cert_cb_arg);
190 if (rv == 0) {
191 OPENSSL_PUT_ERROR(SSL, SSL_R_CERT_CB_ERROR);
192 ssl3_send_alert(ssl, SSL3_AL_FATAL, SSL_AD_INTERNAL_ERROR);
193 return ssl_hs_error;
194 }
195 if (rv < 0) {
196 hs->state = state_process_client_hello;
197 return ssl_hs_x509_lookup;
198 }
199 }
200
201 STACK_OF(SSL_CIPHER) *ciphers =
202 ssl_bytes_to_cipher_list(ssl, &cipher_suites, max_version);
203 if (ciphers == NULL) {
204 return ssl_hs_error;
205 }
206
207 const SSL_CIPHER *cipher =
208 ssl3_choose_cipher(ssl, ciphers, ssl_get_cipher_preferences(ssl));
209 sk_SSL_CIPHER_free(ciphers);
210 if (cipher == NULL) {
211 OPENSSL_PUT_ERROR(SSL, SSL_R_NO_SHARED_CIPHER);
212 ssl3_send_alert(ssl, SSL3_AL_FATAL, SSL_AD_HANDSHAKE_FAILURE);
213 return ssl_hs_error;
214 }
215
Steven Valdez87eab492016-06-27 16:34:59 -0400216 ssl->s3->new_session->cipher = cipher;
Steven Valdez143e8b32016-07-11 13:19:03 -0400217 ssl->s3->tmp.new_cipher = cipher;
218
David Benjamin613fe3b2016-07-22 17:39:29 +0200219 ssl->method->received_flight(ssl);
220
Steven Valdez143e8b32016-07-11 13:19:03 -0400221 /* The PRF hash is now known. Set up the key schedule and hash the
222 * ClientHello. */
Steven Valdez143e8b32016-07-11 13:19:03 -0400223 size_t hash_len =
224 EVP_MD_size(ssl_get_handshake_digest(ssl_get_algorithm_prf(ssl)));
225 if (!tls13_init_key_schedule(ssl, kZeroes, hash_len)) {
226 return ssl_hs_error;
227 }
228
229 /* Resolve PSK and incorporate it into the secret. */
Steven Valdez5440fe02016-07-18 12:40:30 -0400230 if (!resolve_psk_secret(ssl)) {
Steven Valdez143e8b32016-07-11 13:19:03 -0400231 return ssl_hs_error;
232 }
233
234 /* Resolve ECDHE and incorporate it into the secret. */
Steven Valdez5440fe02016-07-18 12:40:30 -0400235 int need_retry;
236 if (!resolve_ecdhe_secret(ssl, &need_retry, &early_ctx)) {
237 if (need_retry) {
238 hs->state = state_send_hello_retry_request;
239 return ssl_hs_ok;
Steven Valdez143e8b32016-07-11 13:19:03 -0400240 }
Steven Valdez5440fe02016-07-18 12:40:30 -0400241 return ssl_hs_error;
242 }
Steven Valdez143e8b32016-07-11 13:19:03 -0400243
Steven Valdez5440fe02016-07-18 12:40:30 -0400244 hs->state = state_send_server_hello;
245 return ssl_hs_ok;
246}
Steven Valdez143e8b32016-07-11 13:19:03 -0400247
Steven Valdez5440fe02016-07-18 12:40:30 -0400248static enum ssl_hs_wait_t do_send_hello_retry_request(SSL *ssl,
249 SSL_HANDSHAKE *hs) {
250 CBB cbb, body, extensions;
251 uint16_t group_id;
252 if (!ssl->method->init_message(ssl, &cbb, &body,
253 SSL3_MT_HELLO_RETRY_REQUEST) ||
254 !CBB_add_u16(&body, ssl->version) ||
255 !CBB_add_u16(&body, ssl_cipher_get_value(ssl->s3->tmp.new_cipher)) ||
256 !tls1_get_shared_group(ssl, &group_id) ||
257 !CBB_add_u16(&body, group_id) ||
258 !CBB_add_u16_length_prefixed(&body, &extensions) ||
259 !ssl->method->finish_message(ssl, &cbb)) {
260 CBB_cleanup(&cbb);
261 return ssl_hs_error;
262 }
263
264 hs->state = state_flush_hello_retry_request;
265 return ssl_hs_write_message;
266}
267
268static enum ssl_hs_wait_t do_flush_hello_retry_request(SSL *ssl,
269 SSL_HANDSHAKE *hs) {
270 hs->state = state_process_second_client_hello;
271 return ssl_hs_flush_and_read_message;
272}
273
274static enum ssl_hs_wait_t do_process_second_client_hello(SSL *ssl,
275 SSL_HANDSHAKE *hs) {
276 if (!tls13_check_message_type(ssl, SSL3_MT_CLIENT_HELLO)) {
277 return ssl_hs_error;
278 }
279
280 struct ssl_early_callback_ctx early_ctx;
David Benjamind7573dc2016-07-20 19:05:22 +0200281 if (!ssl_early_callback_init(ssl, &early_ctx, ssl->init_msg,
282 ssl->init_num)) {
Steven Valdez5440fe02016-07-18 12:40:30 -0400283 OPENSSL_PUT_ERROR(SSL, SSL_R_CLIENTHELLO_PARSE_FAILED);
284 ssl3_send_alert(ssl, SSL3_AL_FATAL, SSL_AD_DECODE_ERROR);
285 return ssl_hs_error;
286 }
287
288 int need_retry;
289 if (!resolve_ecdhe_secret(ssl, &need_retry, &early_ctx)) {
290 if (need_retry) {
291 /* Only send one HelloRetryRequest. */
292 ssl3_send_alert(ssl, SSL3_AL_FATAL, SSL_AD_ILLEGAL_PARAMETER);
293 OPENSSL_PUT_ERROR(SSL, SSL_R_WRONG_CURVE);
Steven Valdez143e8b32016-07-11 13:19:03 -0400294 }
Steven Valdez5440fe02016-07-18 12:40:30 -0400295 return ssl_hs_error;
296 }
297
298 if (!ssl->method->hash_current_message(ssl)) {
Steven Valdez143e8b32016-07-11 13:19:03 -0400299 return ssl_hs_error;
300 }
301
David Benjamin613fe3b2016-07-22 17:39:29 +0200302 ssl->method->received_flight(ssl);
Steven Valdez143e8b32016-07-11 13:19:03 -0400303 hs->state = state_send_server_hello;
304 return ssl_hs_ok;
305}
306
307static enum ssl_hs_wait_t do_send_server_hello(SSL *ssl, SSL_HANDSHAKE *hs) {
308 CBB cbb, body, extensions;
309 if (!ssl->method->init_message(ssl, &cbb, &body, SSL3_MT_SERVER_HELLO) ||
310 !CBB_add_u16(&body, ssl->version) ||
311 !RAND_bytes(ssl->s3->server_random, sizeof(ssl->s3->server_random)) ||
312 !CBB_add_bytes(&body, ssl->s3->server_random, SSL3_RANDOM_SIZE) ||
313 !CBB_add_u16(&body, ssl_cipher_get_value(ssl->s3->tmp.new_cipher)) ||
314 !CBB_add_u16_length_prefixed(&body, &extensions) ||
Steven Valdez7259f2f2016-08-02 16:55:05 -0400315 !ssl_ext_key_share_add_serverhello(ssl, &extensions) ||
Steven Valdez143e8b32016-07-11 13:19:03 -0400316 !ssl->method->finish_message(ssl, &cbb)) {
317 CBB_cleanup(&cbb);
318 return ssl_hs_error;
319 }
320
321 hs->state = state_send_encrypted_extensions;
322 return ssl_hs_write_message;
323}
324
325static enum ssl_hs_wait_t do_send_encrypted_extensions(SSL *ssl,
326 SSL_HANDSHAKE *hs) {
327 if (!tls13_set_handshake_traffic(ssl)) {
328 return ssl_hs_error;
329 }
330
331 CBB cbb, body;
332 if (!ssl->method->init_message(ssl, &cbb, &body,
333 SSL3_MT_ENCRYPTED_EXTENSIONS) ||
334 !ssl_add_serverhello_tlsext(ssl, &body) ||
335 !ssl->method->finish_message(ssl, &cbb)) {
336 CBB_cleanup(&cbb);
337 return ssl_hs_error;
338 }
339
340 hs->state = state_send_certificate_request;
341 return ssl_hs_write_message;
342}
343
344static enum ssl_hs_wait_t do_send_certificate_request(SSL *ssl,
345 SSL_HANDSHAKE *hs) {
346 /* Determine whether to request a client certificate. */
347 ssl->s3->tmp.cert_request = !!(ssl->verify_mode & SSL_VERIFY_PEER);
348 /* CertificateRequest may only be sent in certificate-based ciphers. */
349 if (!ssl_cipher_uses_certificate_auth(ssl->s3->tmp.new_cipher)) {
350 ssl->s3->tmp.cert_request = 0;
351 }
352
353 if (!ssl->s3->tmp.cert_request) {
354 /* Skip this state. */
355 hs->state = state_send_server_certificate;
356 return ssl_hs_ok;
357 }
358
359 CBB cbb, body, sigalgs_cbb;
360 if (!ssl->method->init_message(ssl, &cbb, &body,
361 SSL3_MT_CERTIFICATE_REQUEST) ||
362 !CBB_add_u8(&body, 0 /* no certificate_request_context. */)) {
363 goto err;
364 }
365
366 const uint16_t *sigalgs;
367 size_t sigalgs_len = tls12_get_psigalgs(ssl, &sigalgs);
368 if (!CBB_add_u16_length_prefixed(&body, &sigalgs_cbb)) {
369 goto err;
370 }
371
372 for (size_t i = 0; i < sigalgs_len; i++) {
373 if (!CBB_add_u16(&sigalgs_cbb, sigalgs[i])) {
374 goto err;
375 }
376 }
377
378 if (!ssl_add_client_CA_list(ssl, &body) ||
379 !CBB_add_u16(&body, 0 /* empty certificate_extensions. */) ||
380 !ssl->method->finish_message(ssl, &cbb)) {
381 goto err;
382 }
383
384 hs->state = state_send_server_certificate;
385 return ssl_hs_write_message;
386
387err:
388 CBB_cleanup(&cbb);
389 return ssl_hs_error;
390}
391
392static enum ssl_hs_wait_t do_send_server_certificate(SSL *ssl,
393 SSL_HANDSHAKE *hs) {
394 if (!ssl_cipher_uses_certificate_auth(ssl->s3->tmp.new_cipher)) {
395 hs->state = state_send_server_finished;
396 return ssl_hs_ok;
397 }
398
399 if (!ssl_has_certificate(ssl)) {
400 OPENSSL_PUT_ERROR(SSL, SSL_R_NO_CERTIFICATE_SET);
401 return ssl_hs_error;
402 }
403
404 if (!tls13_prepare_certificate(ssl)) {
405 return ssl_hs_error;
406 }
407
408 hs->state = state_send_server_certificate_verify;
409 return ssl_hs_write_message;
410}
411
412static enum ssl_hs_wait_t do_send_server_certificate_verify(SSL *ssl,
413 SSL_HANDSHAKE *hs,
414 int is_first_run) {
415 switch (tls13_prepare_certificate_verify(ssl, is_first_run)) {
416 case ssl_private_key_success:
417 hs->state = state_send_server_finished;
418 return ssl_hs_write_message;
419
420 case ssl_private_key_retry:
421 hs->state = state_complete_server_certificate_verify;
422 return ssl_hs_private_key_operation;
423
424 case ssl_private_key_failure:
425 return ssl_hs_error;
426 }
427
428 assert(0);
429 return ssl_hs_error;
430}
431
432static enum ssl_hs_wait_t do_send_server_finished(SSL *ssl, SSL_HANDSHAKE *hs) {
433 if (!tls13_prepare_finished(ssl)) {
434 return ssl_hs_error;
435 }
436
437 hs->state = state_flush;
438 return ssl_hs_write_message;
439}
440
441static enum ssl_hs_wait_t do_flush(SSL *ssl, SSL_HANDSHAKE *hs) {
Steven Valdez143e8b32016-07-11 13:19:03 -0400442 /* Update the secret to the master secret and derive traffic keys. */
Steven Valdez143e8b32016-07-11 13:19:03 -0400443 if (!tls13_advance_key_schedule(ssl, kZeroes, hs->hash_len) ||
444 !tls13_derive_traffic_secret_0(ssl) ||
445 !tls13_set_traffic_key(ssl, type_data, evp_aead_seal,
446 hs->traffic_secret_0, hs->hash_len)) {
447 return ssl_hs_error;
448 }
449
450 hs->state = state_process_client_certificate;
David Benjaminf2401eb2016-07-18 22:25:05 +0200451 return ssl_hs_flush_and_read_message;
Steven Valdez143e8b32016-07-11 13:19:03 -0400452}
453
454static enum ssl_hs_wait_t do_process_client_certificate(SSL *ssl,
455 SSL_HANDSHAKE *hs) {
456 if (!ssl->s3->tmp.cert_request) {
457 /* Skip this state. */
458 hs->state = state_process_client_certificate_verify;
459 return ssl_hs_ok;
460 }
461
462 if (!tls13_check_message_type(ssl, SSL3_MT_CERTIFICATE) ||
463 !tls13_process_certificate(ssl) ||
464 !ssl->method->hash_current_message(ssl)) {
465 return ssl_hs_error;
466 }
467
David Benjamin3ce43892016-08-01 19:41:34 -0400468 /* For historical reasons, the server's copy of the chain does not include the
469 * leaf while the client's does. */
470 if (sk_X509_num(ssl->s3->new_session->cert_chain) > 0) {
471 X509_free(sk_X509_shift(ssl->s3->new_session->cert_chain));
472 }
473
Steven Valdez143e8b32016-07-11 13:19:03 -0400474 hs->state = state_process_client_certificate_verify;
475 return ssl_hs_read_message;
476}
477
478static enum ssl_hs_wait_t do_process_client_certificate_verify(
479 SSL *ssl, SSL_HANDSHAKE *hs) {
Steven Valdez87eab492016-06-27 16:34:59 -0400480 if (ssl->s3->new_session->peer == NULL) {
Steven Valdez143e8b32016-07-11 13:19:03 -0400481 /* Skip this state. */
482 hs->state = state_process_client_finished;
483 return ssl_hs_ok;
484 }
485
486 if (!tls13_check_message_type(ssl, SSL3_MT_CERTIFICATE_VERIFY) ||
487 !tls13_process_certificate_verify(ssl) ||
488 !ssl->method->hash_current_message(ssl)) {
489 return 0;
490 }
491
492 hs->state = state_process_client_finished;
493 return ssl_hs_read_message;
494}
495
496static enum ssl_hs_wait_t do_process_client_finished(SSL *ssl,
497 SSL_HANDSHAKE *hs) {
498 if (!tls13_check_message_type(ssl, SSL3_MT_FINISHED) ||
499 !tls13_process_finished(ssl) ||
500 !ssl->method->hash_current_message(ssl) ||
501 /* evp_aead_seal keys have already been switched. */
502 !tls13_set_traffic_key(ssl, type_data, evp_aead_open,
503 hs->traffic_secret_0, hs->hash_len) ||
504 !tls13_finalize_keys(ssl)) {
505 return ssl_hs_error;
506 }
507
David Benjamin613fe3b2016-07-22 17:39:29 +0200508 ssl->method->received_flight(ssl);
Steven Valdez143e8b32016-07-11 13:19:03 -0400509 hs->state = state_done;
510 return ssl_hs_ok;
511}
512
513enum ssl_hs_wait_t tls13_server_handshake(SSL *ssl) {
514 SSL_HANDSHAKE *hs = ssl->s3->hs;
515
516 while (hs->state != state_done) {
517 enum ssl_hs_wait_t ret = ssl_hs_error;
518 enum server_hs_state_t state = hs->state;
519 switch (state) {
520 case state_process_client_hello:
521 ret = do_process_client_hello(ssl, hs);
522 break;
Steven Valdez5440fe02016-07-18 12:40:30 -0400523 case state_send_hello_retry_request:
524 ret = do_send_hello_retry_request(ssl, hs);
525 break;
526 case state_flush_hello_retry_request:
527 ret = do_flush_hello_retry_request(ssl, hs);
528 break;
529 case state_process_second_client_hello:
530 ret = do_process_second_client_hello(ssl, hs);
531 break;
Steven Valdez143e8b32016-07-11 13:19:03 -0400532 case state_send_server_hello:
533 ret = do_send_server_hello(ssl, hs);
534 break;
535 case state_send_encrypted_extensions:
536 ret = do_send_encrypted_extensions(ssl, hs);
537 break;
538 case state_send_certificate_request:
539 ret = do_send_certificate_request(ssl, hs);
540 break;
541 case state_send_server_certificate:
542 ret = do_send_server_certificate(ssl, hs);
543 break;
544 case state_send_server_certificate_verify:
545 ret = do_send_server_certificate_verify(ssl, hs, 1 /* first run */);
546 break;
547 case state_complete_server_certificate_verify:
548 ret = do_send_server_certificate_verify(ssl, hs, 0 /* complete */);
549 break;
550 case state_send_server_finished:
551 ret = do_send_server_finished(ssl, hs);
552 break;
553 case state_flush:
554 ret = do_flush(ssl, hs);
555 break;
Steven Valdez143e8b32016-07-11 13:19:03 -0400556 case state_process_client_certificate:
557 ret = do_process_client_certificate(ssl, hs);
558 break;
559 case state_process_client_certificate_verify:
560 ret = do_process_client_certificate_verify(ssl, hs);
561 break;
562 case state_process_client_finished:
563 ret = do_process_client_finished(ssl, hs);
564 break;
565 case state_done:
566 ret = ssl_hs_ok;
567 break;
568 }
569
570 if (ret != ssl_hs_ok) {
571 return ret;
572 }
573 }
574
575 return ssl_hs_ok;
576}