Also simplifies the state machine a bit.
Reviewed-by: Rich Salz <rsalz@openssl.org>
(Merged from https://github.com/openssl/openssl/pull/2737)
TLS_ST_SW_KEY_UPDATE,
TLS_ST_CW_KEY_UPDATE,
TLS_ST_SR_KEY_UPDATE,
TLS_ST_SW_KEY_UPDATE,
TLS_ST_CW_KEY_UPDATE,
TLS_ST_SR_KEY_UPDATE,
+ TLS_ST_CR_KEY_UPDATE,
+ TLS_ST_CW_EARLY_DATA
} OSSL_HANDSHAKE_STATE;
/*
} OSSL_HANDSHAKE_STATE;
/*
- if (s->early_data_state == SSL_EARLY_DATA_FINISHED_WRITING
- && mt == SSL3_MT_SERVER_HELLO) {
- st->hand_state = TLS_ST_CR_SRVR_HELLO;
- return 1;
- }
if (mt == SSL3_MT_NEWSESSION_TICKET) {
st->hand_state = TLS_ST_CR_SESSION_TICKET;
return 1;
if (mt == SSL3_MT_NEWSESSION_TICKET) {
st->hand_state = TLS_ST_CR_SESSION_TICKET;
return 1;
+ case TLS_ST_CW_EARLY_DATA:
+ /*
+ * We've not actually selected TLSv1.3 yet, but we have sent early
+ * data. The only thing allowed now is a ServerHello or a
+ * HelloRetryRequest.
+ */
+ if (mt == SSL3_MT_SERVER_HELLO) {
+ st->hand_state = TLS_ST_CR_SRVR_HELLO;
+ return 1;
+ }
+ if (mt == SSL3_MT_HELLO_RETRY_REQUEST) {
+ st->hand_state = TLS_ST_CR_HELLO_RETRY_REQUEST;
+ return 1;
+ }
+ break;
+
case TLS_ST_CR_SRVR_HELLO:
if (s->hit) {
if (s->ext.ticket_expected) {
case TLS_ST_CR_SRVR_HELLO:
if (s->hit) {
if (s->ext.ticket_expected) {
- if (s->early_data_state == SSL_EARLY_DATA_FINISHED_WRITING) {
- /*
- * We've not actually selected TLSv1.3 yet, but we have sent early
- * data. The only thing allowed now is a ServerHello or a
- * HelloRetryRequest.
- */
- if (mt == SSL3_MT_SERVER_HELLO) {
- st->hand_state = TLS_ST_CR_SRVR_HELLO;
- return 1;
- }
- if (mt == SSL3_MT_HELLO_RETRY_REQUEST) {
- st->hand_state = TLS_ST_CR_HELLO_RETRY_REQUEST;
- return 1;
- }
- } else if (mt == SSL3_MT_HELLO_REQUEST) {
+ if (mt == SSL3_MT_HELLO_REQUEST) {
st->hand_state = TLS_ST_CR_HELLO_REQ;
return 1;
}
st->hand_state = TLS_ST_CR_HELLO_REQ;
return 1;
}
case TLS_ST_CR_SESSION_TICKET:
case TLS_ST_CW_FINISHED:
st->hand_state = TLS_ST_OK;
case TLS_ST_CR_SESSION_TICKET:
case TLS_ST_CW_FINISHED:
st->hand_state = TLS_ST_OK;
- ossl_statem_set_in_init(s, 0);
return WRITE_TRAN_CONTINUE;
case TLS_ST_OK:
return WRITE_TRAN_CONTINUE;
case TLS_ST_OK:
return WRITE_TRAN_ERROR;
case TLS_ST_OK:
return WRITE_TRAN_ERROR;
case TLS_ST_OK:
- if (s->early_data_state == SSL_EARLY_DATA_FINISHED_WRITING) {
- /*
- * We are assuming this is a TLSv1.3 connection, although we haven't
- * actually selected a version yet.
- */
- return WRITE_TRAN_FINISHED;
- }
if (!s->renegotiate) {
/*
* We haven't requested a renegotiation ourselves so we must have
if (!s->renegotiate) {
/*
* We haven't requested a renegotiation ourselves so we must have
* We are assuming this is a TLSv1.3 connection, although we haven't
* actually selected a version yet.
*/
* We are assuming this is a TLSv1.3 connection, although we haven't
* actually selected a version yet.
*/
- st->hand_state = TLS_ST_OK;
- ossl_statem_set_in_init(s, 0);
+ st->hand_state = TLS_ST_CW_EARLY_DATA;
return WRITE_TRAN_CONTINUE;
}
/*
return WRITE_TRAN_CONTINUE;
}
/*
*/
return WRITE_TRAN_FINISHED;
*/
return WRITE_TRAN_FINISHED;
+ case TLS_ST_CW_EARLY_DATA:
+ return WRITE_TRAN_FINISHED;
+
case DTLS_ST_CR_HELLO_VERIFY_REQUEST:
st->hand_state = TLS_ST_CW_CLNT_HELLO;
return WRITE_TRAN_CONTINUE;
case DTLS_ST_CR_HELLO_VERIFY_REQUEST:
st->hand_state = TLS_ST_CW_CLNT_HELLO;
return WRITE_TRAN_CONTINUE;
case TLS_ST_CW_CHANGE:
#if defined(OPENSSL_NO_NEXTPROTONEG)
case TLS_ST_CW_CHANGE:
#if defined(OPENSSL_NO_NEXTPROTONEG)
- st->hand_state = TLS_ST_CW_FINISHED;
+ st->
+ hand_state = TLS_ST_CW_FINISHED;
#else
if (!SSL_IS_DTLS(s) && s->s3->npn_seen)
st->hand_state = TLS_ST_CW_NEXT_PROTO;
#else
if (!SSL_IS_DTLS(s) && s->s3->npn_seen)
st->hand_state = TLS_ST_CW_NEXT_PROTO;
case TLS_ST_CW_FINISHED:
if (s->hit) {
st->hand_state = TLS_ST_OK;
case TLS_ST_CW_FINISHED:
if (s->hit) {
st->hand_state = TLS_ST_OK;
- ossl_statem_set_in_init(s, 0);
return WRITE_TRAN_CONTINUE;
} else {
return WRITE_TRAN_FINISHED;
return WRITE_TRAN_CONTINUE;
} else {
return WRITE_TRAN_FINISHED;
return WRITE_TRAN_CONTINUE;
} else {
st->hand_state = TLS_ST_OK;
return WRITE_TRAN_CONTINUE;
} else {
st->hand_state = TLS_ST_OK;
- ossl_statem_set_in_init(s, 0);
return WRITE_TRAN_CONTINUE;
}
return WRITE_TRAN_CONTINUE;
}
return WRITE_TRAN_CONTINUE;
}
st->hand_state = TLS_ST_OK;
return WRITE_TRAN_CONTINUE;
}
st->hand_state = TLS_ST_OK;
- ossl_statem_set_in_init(s, 0);
return WRITE_TRAN_CONTINUE;
}
}
return WRITE_TRAN_CONTINUE;
}
}
+ case TLS_ST_CW_EARLY_DATA:
case TLS_ST_OK:
return tls_finish_handshake(s, wst, 1);
}
case TLS_ST_OK:
return tls_finish_handshake(s, wst, 1);
}
if (!clearbufs)
return WORK_FINISHED_CONTINUE;
if (!clearbufs)
return WORK_FINISHED_CONTINUE;
+ ossl_statem_set_in_init(s, 0);
return WORK_FINISHED_STOP;
}
return WORK_FINISHED_STOP;
}
case TLS_ST_SW_FINISHED:
if (s->early_data_state == SSL_EARLY_DATA_ACCEPTING) {
st->hand_state = TLS_ST_OK;
case TLS_ST_SW_FINISHED:
if (s->early_data_state == SSL_EARLY_DATA_ACCEPTING) {
st->hand_state = TLS_ST_OK;
- ossl_statem_set_in_init(s, 0);
return WRITE_TRAN_CONTINUE;
}
return WRITE_TRAN_FINISHED;
return WRITE_TRAN_CONTINUE;
}
return WRITE_TRAN_FINISHED;
case TLS_ST_SW_KEY_UPDATE:
case TLS_ST_SW_SESSION_TICKET:
st->hand_state = TLS_ST_OK;
case TLS_ST_SW_KEY_UPDATE:
case TLS_ST_SW_SESSION_TICKET:
st->hand_state = TLS_ST_OK;
- ossl_statem_set_in_init(s, 0);
return WRITE_TRAN_CONTINUE;
}
}
return WRITE_TRAN_CONTINUE;
}
}
case TLS_ST_SW_HELLO_REQ:
st->hand_state = TLS_ST_OK;
case TLS_ST_SW_HELLO_REQ:
st->hand_state = TLS_ST_OK;
- ossl_statem_set_in_init(s, 0);
return WRITE_TRAN_CONTINUE;
case TLS_ST_SR_CLNT_HELLO:
return WRITE_TRAN_CONTINUE;
case TLS_ST_SR_CLNT_HELLO:
case TLS_ST_SR_FINISHED:
if (s->hit) {
st->hand_state = TLS_ST_OK;
case TLS_ST_SR_FINISHED:
if (s->hit) {
st->hand_state = TLS_ST_OK;
- ossl_statem_set_in_init(s, 0);
return WRITE_TRAN_CONTINUE;
} else if (s->ext.ticket_expected) {
st->hand_state = TLS_ST_SW_SESSION_TICKET;
return WRITE_TRAN_CONTINUE;
} else if (s->ext.ticket_expected) {
st->hand_state = TLS_ST_SW_SESSION_TICKET;
return WRITE_TRAN_FINISHED;
}
st->hand_state = TLS_ST_OK;
return WRITE_TRAN_FINISHED;
}
st->hand_state = TLS_ST_OK;
- ossl_statem_set_in_init(s, 0);
return WRITE_TRAN_CONTINUE;
}
}
return WRITE_TRAN_CONTINUE;
}
}