/*
* Copyright 1995-2018 The OpenSSL Project Authors. All Rights Reserved.
*
- * Licensed under the OpenSSL license (the "License"). You may not use
+ * Licensed under the Apache License 2.0 (the "License"). You may not use
* this file except in compliance with the License. You can obtain a copy
* in the file LICENSE in the source distribution or at
* https://www.openssl.org/source/license.html
#include "../ssl_locl.h"
#include "internal/constant_time_locl.h"
+#include <openssl/trace.h>
#include <openssl/rand.h>
#include "record_locl.h"
#include "internal/cryptlib.h"
int early_data_count_ok(SSL *s, size_t length, size_t overhead, int send)
{
- uint32_t max_early_data = s->max_early_data;
+ uint32_t max_early_data;
SSL_SESSION *sess = s->session;
/*
}
sess = s->psksession;
}
- if (!s->server
- || (s->hit && sess->ext.max_early_data < s->max_early_data))
+
+ if (!s->server)
max_early_data = sess->ext.max_early_data;
+ else if (s->ext.early_data != SSL_EARLY_DATA_ACCEPTED)
+ max_early_data = s->recv_max_early_data;
+ else
+ max_early_data = s->recv_max_early_data < sess->ext.max_early_data
+ ? s->recv_max_early_data : sess->ext.max_early_data;
if (max_early_data == 0) {
SSLfatal(s, send ? SSL_AD_INTERNAL_ERROR : SSL_AD_UNEXPECTED_MESSAGE,
size_t num_recs = 0, max_recs, j;
PACKET pkt, sslv2pkt;
size_t first_rec_len;
+ int is_ktls_left;
rr = RECORD_LAYER_get_rrec(&s->rlayer);
rbuf = RECORD_LAYER_get_rbuf(&s->rlayer);
+ is_ktls_left = (rbuf->left > 0);
max_recs = s->max_pipelines;
if (max_recs == 0)
max_recs = 1;
rret = ssl3_read_n(s, SSL3_RT_HEADER_LENGTH,
SSL3_BUFFER_get_len(rbuf), 0,
num_recs == 0 ? 1 : 0, &n);
- if (rret <= 0)
- return rret; /* error or non-blocking */
+ if (rret <= 0) {
+#ifndef OPENSSL_NO_KTLS
+ if (!BIO_get_ktls_recv(s->rbio))
+ return rret; /* error or non-blocking */
+ switch (errno) {
+ case EBADMSG:
+ SSLfatal(s, SSL_AD_BAD_RECORD_MAC,
+ SSL_F_SSL3_GET_RECORD,
+ SSL_R_DECRYPTION_FAILED_OR_BAD_RECORD_MAC);
+ break;
+ case EMSGSIZE:
+ SSLfatal(s, SSL_AD_RECORD_OVERFLOW,
+ SSL_F_SSL3_GET_RECORD,
+ SSL_R_PACKET_LENGTH_TOO_LONG);
+ break;
+ case EINVAL:
+ SSLfatal(s, SSL_AD_PROTOCOL_VERSION,
+ SSL_F_SSL3_GET_RECORD,
+ SSL_R_WRONG_VERSION_NUMBER);
+ break;
+ default:
+ break;
+ }
+#endif
+ return rret;
+ }
RECORD_LAYER_set_rstate(&s->rlayer, SSL_ST_READ_BODY);
p = RECORD_LAYER_get_packet(&s->rlayer);
thisrr->rec_version = version;
/*
- * Lets check version. In TLSv1.3 we ignore this field. For the
+ * Lets check version. In TLSv1.3 we only check this field
+ * when encryption is occurring (see later check). For the
* ServerHello after an HRR we haven't actually selected TLSv1.3
* yet, but we still treat it as TLSv1.3, so we must check for
* that explicitly
}
}
- if (SSL_IS_TLS13(s)
- && s->enc_read_ctx != NULL
- && thisrr->type != SSL3_RT_APPLICATION_DATA
- && (thisrr->type != SSL3_RT_CHANGE_CIPHER_SPEC
- || !SSL_IS_FIRST_HANDSHAKE(s))) {
- SSLfatal(s, SSL_AD_UNEXPECTED_MESSAGE,
- SSL_F_SSL3_GET_RECORD, SSL_R_BAD_RECORD_TYPE);
- return -1;
+ if (SSL_IS_TLS13(s) && s->enc_read_ctx != NULL) {
+ if (thisrr->type != SSL3_RT_APPLICATION_DATA
+ && (thisrr->type != SSL3_RT_CHANGE_CIPHER_SPEC
+ || !SSL_IS_FIRST_HANDSHAKE(s))
+ && (thisrr->type != SSL3_RT_ALERT
+ || s->statem.enc_read_state
+ != ENC_READ_STATE_ALLOW_PLAIN_ALERTS)) {
+ SSLfatal(s, SSL_AD_UNEXPECTED_MESSAGE,
+ SSL_F_SSL3_GET_RECORD, SSL_R_BAD_RECORD_TYPE);
+ return -1;
+ }
+ if (thisrr->rec_version != TLS1_2_VERSION) {
+ SSLfatal(s, SSL_AD_DECODE_ERROR, SSL_F_SSL3_GET_RECORD,
+ SSL_R_WRONG_VERSION_NUMBER);
+ return -1;
+ }
}
if (thisrr->length >
len -= SSL3_RT_MAX_COMPRESSED_OVERHEAD;
#endif
- if (thisrr->length > len) {
+ if (thisrr->length > len && !BIO_get_ktls_recv(s->rbio)) {
SSLfatal(s, SSL_AD_RECORD_OVERFLOW, SSL_F_SSL3_GET_RECORD,
SSL_R_ENCRYPTED_LENGTH_TOO_LONG);
return -1;
} else {
more = thisrr->length;
}
+
if (more > 0) {
/* now s->packet_length == SSL3_RT_HEADER_LENGTH */
return 1;
}
+ /*
+ * KTLS reads full records. If there is any data left,
+ * then it is from before enabling ktls
+ */
+ if (BIO_get_ktls_recv(s->rbio) && !is_ktls_left)
+ goto skip_decryption;
+
/*
* If in encrypt-then-mac mode calculate mac from encrypted record. All
* the details below are public so no timing details can leak.
SSL_R_BLOCK_CIPHER_PAD_IS_WRONG);
return -1;
}
-#ifdef SSL_DEBUG
- printf("dec %"OSSLzu"\n", rr[0].length);
- {
- size_t z;
- for (z = 0; z < rr[0].length; z++)
- printf("%02X%c", rr[0].data[z], ((z + 1) % 16) ? ' ' : '\n');
- }
- printf("\n");
-#endif
+ OSSL_TRACE_BEGIN(TLS) {
+ BIO_printf(trc_out, "dec %lu\n", (unsigned long)rr[0].length);
+ BIO_dump_indent(trc_out, rr[0].data, rr[0].length, 4);
+ } OSSL_TRACE_END(TLS);
/* r->length is now the compressed data plus mac */
if ((sess != NULL) &&
return -1;
}
+ skip_decryption:
+
for (j = 0; j < num_recs; j++) {
thisrr = &rr[j];
}
}
- if (SSL_IS_TLS13(s) && s->enc_read_ctx != NULL) {
+ if (SSL_IS_TLS13(s)
+ && s->enc_read_ctx != NULL
+ && thisrr->type != SSL3_RT_ALERT) {
size_t end;
if (thisrr->length == 0
return -1;
}
- if (thisrr->length > SSL3_RT_MAX_PLAIN_LENGTH) {
+ if (thisrr->length > SSL3_RT_MAX_PLAIN_LENGTH && !BIO_get_ktls_recv(s->rbio)) {
SSLfatal(s, SSL_AD_RECORD_OVERFLOW, SSL_F_SSL3_GET_RECORD,
SSL_R_DATA_LENGTH_TOO_LONG);
return -1;
/* If received packet overflows current Max Fragment Length setting */
if (s->session != NULL && USE_MAX_FRAGMENT_LENGTH_EXT(s->session)
- && thisrr->length > GET_MAX_FRAGMENT_LENGTH(s->session)) {
+ && thisrr->length > GET_MAX_FRAGMENT_LENGTH(s->session)
+ && !BIO_get_ktls_recv(s->rbio)) {
SSLfatal(s, SSL_AD_RECORD_OVERFLOW, SSL_F_SSL3_GET_RECORD,
SSL_R_DATA_LENGTH_TOO_LONG);
return -1;
SSLfatal(s, SSL_AD_INTERNAL_ERROR, SSL_F_TLS1_ENC,
ERR_R_INTERNAL_ERROR);
return -1;
- } else if (ssl_randbytes(s, recs[ctr].input, ivlen) <= 0) {
+ } else if (RAND_bytes(recs[ctr].input, ivlen) <= 0) {
SSLfatal(s, SSL_AD_INTERNAL_ERROR, SSL_F_TLS1_ENC,
ERR_R_INTERNAL_ERROR);
return -1;
|| EVP_DigestUpdate(md_ctx, ssl3_pad_2, npad) <= 0
|| EVP_DigestUpdate(md_ctx, md, md_size) <= 0
|| EVP_DigestFinal_ex(md_ctx, md, &md_size_u) <= 0) {
- EVP_MD_CTX_reset(md_ctx);
+ EVP_MD_CTX_free(md_ctx);
return 0;
}
mac_ctx = hash;
} else {
hmac = EVP_MD_CTX_new();
- if (hmac == NULL || !EVP_MD_CTX_copy(hmac, hash))
+ if (hmac == NULL || !EVP_MD_CTX_copy(hmac, hash)) {
+ EVP_MD_CTX_free(hmac);
return 0;
+ }
mac_ctx = hmac;
}
EVP_MD_CTX_free(hmac);
-#ifdef SSL_DEBUG
- fprintf(stderr, "seq=");
- {
- int z;
- for (z = 0; z < 8; z++)
- fprintf(stderr, "%02X ", seq[z]);
- fprintf(stderr, "\n");
- }
- fprintf(stderr, "rec=");
- {
- size_t z;
- for (z = 0; z < rec->length; z++)
- fprintf(stderr, "%02X ", rec->data[z]);
- fprintf(stderr, "\n");
- }
-#endif
+ OSSL_TRACE_BEGIN(TLS) {
+ BIO_printf(trc_out, "seq:\n");
+ BIO_dump_indent(trc_out, seq, 8, 4);
+ BIO_printf(trc_out, "rec:\n");
+ BIO_dump_indent(trc_out, rec->data, rec->length, 4);
+ } OSSL_TRACE_END(TLS);
if (!SSL_IS_DTLS(ssl)) {
for (i = 7; i >= 0; i--) {
break;
}
}
-#ifdef SSL_DEBUG
- {
- unsigned int z;
- for (z = 0; z < md_size; z++)
- fprintf(stderr, "%02X ", md[z]);
- fprintf(stderr, "\n");
- }
-#endif
+ OSSL_TRACE_BEGIN(TLS) {
+ BIO_printf(trc_out, "md:\n");
+ BIO_dump_indent(trc_out, md, md_size, 4);
+ } OSSL_TRACE_END(TLS);
return 1;
}
RECORD_LAYER_reset_packet_length(&s->rlayer);
return 0;
}
-#ifdef SSL_DEBUG
- printf("dec %ld\n", rr->length);
- {
- size_t z;
- for (z = 0; z < rr->length; z++)
- printf("%02X%c", rr->data[z], ((z + 1) % 16) ? ' ' : '\n');
- }
- printf("\n");
-#endif
+ OSSL_TRACE_BEGIN(TLS) {
+ BIO_printf(trc_out, "dec %ld\n", rr->length);
+ BIO_dump_indent(trc_out, rr->data, rr->length, 4);
+ } OSSL_TRACE_END(TLS);
/* r->length is now the compressed data plus mac */
if ((sess != NULL) && !SSL_READ_ETM(s) &&
p += 6;
n2s(p, rr->length);
+ rr->read = 0;
/*
* Lets check the version. We tolerate alerts that don't have the exact
if (version != s->version) {
/* unexpected version, silently discard */
rr->length = 0;
+ rr->read = 1;
RECORD_LAYER_reset_packet_length(&s->rlayer);
goto again;
}
if ((version & 0xff00) != (s->version & 0xff00)) {
/* wrong version, silently discard record */
rr->length = 0;
+ rr->read = 1;
RECORD_LAYER_reset_packet_length(&s->rlayer);
goto again;
}
if (rr->length > SSL3_RT_MAX_ENCRYPTED_LENGTH) {
/* record too long, silently discard it */
rr->length = 0;
+ rr->read = 1;
RECORD_LAYER_reset_packet_length(&s->rlayer);
goto again;
}
&& rr->length > GET_MAX_FRAGMENT_LENGTH(s->session)) {
/* record too long, silently discard it */
rr->length = 0;
+ rr->read = 1;
RECORD_LAYER_reset_packet_length(&s->rlayer);
goto again;
}
return -1;
}
rr->length = 0;
+ rr->read = 1;
RECORD_LAYER_reset_packet_length(&s->rlayer);
goto again;
}
*/
if (!dtls1_record_replay_check(s, bitmap)) {
rr->length = 0;
+ rr->read = 1;
RECORD_LAYER_reset_packet_length(&s->rlayer); /* dump this record */
goto again; /* get another record */
}
#endif
/* just read a 0 length packet */
- if (rr->length == 0)
+ if (rr->length == 0) {
+ rr->read = 1;
goto again;
+ }
/*
* If this record is from the next epoch (either HM or ALERT), and a
}
}
rr->length = 0;
+ rr->read = 1;
RECORD_LAYER_reset_packet_length(&s->rlayer);
goto again;
}
return -1;
}
rr->length = 0;
+ rr->read = 1;
RECORD_LAYER_reset_packet_length(&s->rlayer); /* dump this record */
goto again; /* get another record */
}
return 1;
}
+
+int dtls_buffer_listen_record(SSL *s, size_t len, unsigned char *seq, size_t off)
+{
+ SSL3_RECORD *rr;
+
+ rr = RECORD_LAYER_get_rrec(&s->rlayer);
+ memset(rr, 0, sizeof(SSL3_RECORD));
+
+ rr->length = len;
+ rr->type = SSL3_RT_HANDSHAKE;
+ memcpy(rr->seq_num, seq, sizeof(rr->seq_num));
+ rr->off = off;
+
+ s->rlayer.packet = RECORD_LAYER_get_rbuf(&s->rlayer)->buf;
+ s->rlayer.packet_length = DTLS1_RT_HEADER_LENGTH + len;
+ rr->data = s->rlayer.packet + DTLS1_RT_HEADER_LENGTH;
+
+ if (dtls1_buffer_record(s, &(s->rlayer.d->processed_rcds),
+ SSL3_RECORD_get_seq_num(s->rlayer.rrec)) <= 0) {
+ /* SSLfatal() already called */
+ return 0;
+ }
+
+ return 1;
+}