Push Span down a layer.
Change-Id: I893292b140d033a5aed7e08f928a6c32996bb983
Reviewed-on: https://boringssl-review.googlesource.com/21287
Commit-Queue: Steven Valdez <svaldez@google.com>
Reviewed-by: Steven Valdez <svaldez@google.com>
CQ-Verified: CQ bot account: commit-bot@chromium.org <commit-bot@chromium.org>
diff --git a/ssl/d1_both.cc b/ssl/d1_both.cc
index c2f6479..66f59a4 100644
--- a/ssl/d1_both.cc
+++ b/ssl/d1_both.cc
@@ -344,7 +344,7 @@
// Flag the ChangeCipherSpec for later.
ssl->d1->has_change_cipher_spec = true;
ssl_do_msg_callback(ssl, 0 /* read */, SSL3_RT_CHANGE_CIPHER_SPEC,
- rr->data, rr->length);
+ MakeSpan(rr->data, rr->length));
rr->length = 0;
ssl_read_buffer_discard(ssl);
@@ -433,8 +433,9 @@
CBS_init(&out->raw, frag->data, DTLS1_HM_HEADER_LENGTH + frag->msg_len);
out->is_v2_hello = false;
if (!ssl->s3->has_message) {
- ssl_do_msg_callback(ssl, 0 /* read */, SSL3_RT_HANDSHAKE, frag->data,
- frag->msg_len + DTLS1_HM_HEADER_LENGTH);
+ ssl_do_msg_callback(
+ ssl, 0 /* read */, SSL3_RT_HANDSHAKE,
+ MakeSpan(frag->data, frag->msg_len + DTLS1_HM_HEADER_LENGTH));
ssl->s3->has_message = true;
}
return true;
@@ -673,7 +674,7 @@
}
ssl_do_msg_callback(ssl, 1 /* write */, SSL3_RT_CHANGE_CIPHER_SPEC,
- kChangeCipherSpec, sizeof(kChangeCipherSpec));
+ kChangeCipherSpec);
return seal_success;
}
@@ -716,7 +717,8 @@
return seal_error;
}
- ssl_do_msg_callback(ssl, 1 /* write */, SSL3_RT_HANDSHAKE, frag, frag_len);
+ ssl_do_msg_callback(ssl, 1 /* write */, SSL3_RT_HANDSHAKE,
+ MakeSpan(frag, frag_len));
if (!dtls_seal_record(ssl, out, out_len, max_out, SSL3_RT_HANDSHAKE,
out + prefix, frag_len, use_epoch)) {
diff --git a/ssl/d1_pkt.cc b/ssl/d1_pkt.cc
index 91fc647..d9496d9 100644
--- a/ssl/d1_pkt.cc
+++ b/ssl/d1_pkt.cc
@@ -141,7 +141,7 @@
}
// Read a new packet if there is no unconsumed one.
- if (ssl_read_buffer_len(ssl) == 0) {
+ if (ssl_read_buffer(ssl).empty()) {
int read_ret = ssl_read_buffer_extend_to(ssl, 0 /* unused */);
if (read_ret < 0 && dtls1_is_timer_expired(ssl)) {
// Historically, timeouts were handled implicitly if the caller did not
@@ -159,14 +159,13 @@
return read_ret;
}
}
- assert(ssl_read_buffer_len(ssl) > 0);
+ assert(!ssl_read_buffer(ssl).empty());
- CBS body;
+ Span<uint8_t> body;
uint8_t type, alert;
size_t consumed;
- enum ssl_open_record_t open_ret =
- dtls_open_record(ssl, &type, &body, &consumed, &alert,
- ssl_read_buffer(ssl), ssl_read_buffer_len(ssl));
+ enum ssl_open_record_t open_ret = dtls_open_record(
+ ssl, &type, &body, &consumed, &alert, ssl_read_buffer(ssl));
ssl_read_buffer_consume(ssl, consumed);
switch (open_ret) {
case ssl_open_record_partial:
@@ -174,15 +173,15 @@
break;
case ssl_open_record_success: {
- if (CBS_len(&body) > 0xffff) {
+ if (body.size() > 0xffff) {
OPENSSL_PUT_ERROR(SSL, ERR_R_OVERFLOW);
return -1;
}
SSL3_RECORD *rr = &ssl->s3->rrec;
rr->type = type;
- rr->length = (uint16_t)CBS_len(&body);
- rr->data = (uint8_t *)CBS_data(&body);
+ rr->length = static_cast<uint16_t>(body.size());
+ rr->data = body.data();
return 1;
}
@@ -368,8 +367,7 @@
BIO_flush(ssl->wbio);
}
- ssl_do_msg_callback(ssl, 1 /* write */, SSL3_RT_ALERT, ssl->s3->send_alert,
- 2);
+ ssl_do_msg_callback(ssl, 1 /* write */, SSL3_RT_ALERT, ssl->s3->send_alert);
int alert = (ssl->s3->send_alert[0] << 8) | ssl->s3->send_alert[1];
ssl_do_info_callback(ssl, SSL_CB_WRITE_ALERT, alert);
diff --git a/ssl/dtls_record.cc b/ssl/dtls_record.cc
index 5009f04..71b5e3b 100644
--- a/ssl/dtls_record.cc
+++ b/ssl/dtls_record.cc
@@ -174,14 +174,13 @@
}
}
-enum ssl_open_record_t dtls_open_record(SSL *ssl, uint8_t *out_type, CBS *out,
+enum ssl_open_record_t dtls_open_record(SSL *ssl, uint8_t *out_type,
+ Span<uint8_t> *out,
size_t *out_consumed,
- uint8_t *out_alert, uint8_t *in,
- size_t in_len) {
+ uint8_t *out_alert, Span<uint8_t> in) {
*out_consumed = 0;
- CBS cbs;
- CBS_init(&cbs, in, in_len);
+ CBS cbs = CBS(in);
// Decode the record.
uint8_t type;
@@ -194,7 +193,7 @@
!CBS_get_u16_length_prefixed(&cbs, &body) ||
CBS_len(&body) > SSL3_RT_MAX_ENCRYPTED_LENGTH) {
// The record header was incomplete or malformed. Drop the entire packet.
- *out_consumed = in_len;
+ *out_consumed = in.size();
return ssl_open_record_discard;
}
@@ -209,12 +208,12 @@
if (!version_ok) {
// The record header was incomplete or malformed. Drop the entire packet.
- *out_consumed = in_len;
+ *out_consumed = in.size();
return ssl_open_record_discard;
}
- ssl_do_msg_callback(ssl, 0 /* read */, SSL3_RT_HEADER, in,
- DTLS1_RT_HEADER_LENGTH);
+ ssl_do_msg_callback(ssl, 0 /* read */, SSL3_RT_HEADER,
+ in.subspan(0, DTLS1_RT_HEADER_LENGTH));
uint16_t epoch = (((uint16_t)sequence[0]) << 8) | sequence[1];
if (epoch != ssl->d1->r_epoch ||
@@ -223,14 +222,14 @@
// |epoch| is the next epoch, the record could be buffered for later. For
// simplicity, drop it and expect retransmit to handle it later; DTLS must
// handle packet loss anyway.
- *out_consumed = in_len - CBS_len(&cbs);
+ *out_consumed = in.size() - CBS_len(&cbs);
return ssl_open_record_discard;
}
- // Decrypt the body in-place.
- if (!ssl->s3->aead_read_ctx->Open(out, type, version, sequence,
- (uint8_t *)CBS_data(&body),
- CBS_len(&body))) {
+ // discard the body in-place.
+ if (!ssl->s3->aead_read_ctx->Open(
+ out, type, version, sequence,
+ MakeSpan(const_cast<uint8_t *>(CBS_data(&body)), CBS_len(&body)))) {
// Bad packets are silently dropped in DTLS. See section 4.2.1 of RFC 6347.
// Clear the error queue of any errors decryption may have added. Drop the
// entire packet as it must not have come from the peer.
@@ -238,13 +237,13 @@
// TODO(davidben): This doesn't distinguish malloc failures from encryption
// failures.
ERR_clear_error();
- *out_consumed = in_len - CBS_len(&cbs);
+ *out_consumed = in.size() - CBS_len(&cbs);
return ssl_open_record_discard;
}
- *out_consumed = in_len - CBS_len(&cbs);
+ *out_consumed = in.size() - CBS_len(&cbs);
// Check the plaintext length.
- if (CBS_len(out) > SSL3_RT_MAX_PLAIN_LENGTH) {
+ if (out->size() > SSL3_RT_MAX_PLAIN_LENGTH) {
OPENSSL_PUT_ERROR(SSL, SSL_R_DATA_LENGTH_TOO_LONG);
*out_alert = SSL_AD_RECORD_OVERFLOW;
return ssl_open_record_error;
@@ -256,7 +255,7 @@
// useful if we also limit discarded packets.
if (type == SSL3_RT_ALERT) {
- return ssl_process_alert(ssl, out_alert, CBS_data(out), CBS_len(out));
+ return ssl_process_alert(ssl, out_alert, *out);
}
ssl->s3->warning_alert_count = 0;
@@ -338,8 +337,8 @@
*out_len = DTLS1_RT_HEADER_LENGTH + ciphertext_len;
- ssl_do_msg_callback(ssl, 1 /* write */, SSL3_RT_HEADER, out,
- DTLS1_RT_HEADER_LENGTH);
+ ssl_do_msg_callback(ssl, 1 /* write */, SSL3_RT_HEADER,
+ MakeSpan(out, DTLS1_RT_HEADER_LENGTH));
return 1;
}
diff --git a/ssl/internal.h b/ssl/internal.h
index b9a597c..36d3390 100644
--- a/ssl/internal.h
+++ b/ssl/internal.h
@@ -657,12 +657,11 @@
bool SuffixLen(size_t *out_suffix_len, size_t in_len,
size_t extra_in_len) const;
- // Open authenticates and decrypts |in_len| bytes from |in| in-place. On
- // success, it sets |*out| to the plaintext in |in| and returns true.
- // Otherwise, it returns false. The output will always be |ExplicitNonceLen|
- // bytes ahead of |in|.
- bool Open(CBS *out, uint8_t type, uint16_t record_version,
- const uint8_t seqnum[8], uint8_t *in, size_t in_len);
+ // Open authenticates and decrypts |in| in-place. On success, it sets |*out|
+ // to the plaintext in |in| and returns true. Otherwise, it returns
+ // false. The output will always be |ExplicitNonceLen| bytes ahead of |in|.
+ bool Open(Span<uint8_t> *out, uint8_t type, uint16_t record_version,
+ const uint8_t seqnum[8], Span<uint8_t> in);
// Seal encrypts and authenticates |in_len| bytes from |in| and writes the
// result to |out|. It returns true on success and false on error.
@@ -790,16 +789,16 @@
//
// On failure or fatal alert, it returns |ssl_open_record_error| and sets
// |*out_alert| to an alert to emit, or zero if no alert should be emitted.
-enum ssl_open_record_t tls_open_record(SSL *ssl, uint8_t *out_type, CBS *out,
- size_t *out_consumed, uint8_t *out_alert,
- uint8_t *in, size_t in_len);
+enum ssl_open_record_t tls_open_record(SSL *ssl, uint8_t *out_type,
+ Span<uint8_t> *out, size_t *out_consumed,
+ uint8_t *out_alert, Span<uint8_t> in);
// dtls_open_record implements |tls_open_record| for DTLS. It never returns
// |ssl_open_record_partial| but otherwise behaves analogously.
-enum ssl_open_record_t dtls_open_record(SSL *ssl, uint8_t *out_type, CBS *out,
+enum ssl_open_record_t dtls_open_record(SSL *ssl, uint8_t *out_type,
+ Span<uint8_t> *out,
size_t *out_consumed,
- uint8_t *out_alert, uint8_t *in,
- size_t in_len);
+ uint8_t *out_alert, Span<uint8_t> in);
// ssl_seal_align_prefix_len returns the length of the prefix before the start
// of the bulk of the ciphertext when sealing a record with |ssl|. Callers may
@@ -853,7 +852,7 @@
// |ssl_open_record_close_notify|, or |ssl_open_record_fatal_alert| as
// appropriate.
enum ssl_open_record_t ssl_process_alert(SSL *ssl, uint8_t *out_alert,
- const uint8_t *in, size_t in_len);
+ Span<const uint8_t> in);
// Private key operations.
@@ -1013,16 +1012,13 @@
// ssl_do_msg_callback calls |ssl|'s message callback, if set.
void ssl_do_msg_callback(SSL *ssl, int is_write, int content_type,
- const void *buf, size_t len);
+ Span<const uint8_t> in);
// Transport buffers.
-// ssl_read_buffer returns a pointer to contents of the read buffer.
-uint8_t *ssl_read_buffer(SSL *ssl);
-
-// ssl_read_buffer_len returns the length of the read buffer.
-size_t ssl_read_buffer_len(const SSL *ssl);
+// ssl_read_buffer returns the current read buffer.
+Span<uint8_t> ssl_read_buffer(SSL *ssl);
// ssl_read_buffer_extend_to extends the read buffer to the desired length. For
// TLS, it reads to the end of the buffer until the buffer is |len| bytes
diff --git a/ssl/s3_both.cc b/ssl/s3_both.cc
index 65e2089..d63d133 100644
--- a/ssl/s3_both.cc
+++ b/ssl/s3_both.cc
@@ -194,8 +194,7 @@
}
} while (!rest.empty());
- ssl_do_msg_callback(ssl, 1 /* write */, SSL3_RT_HANDSHAKE, msg.data(),
- msg.size());
+ ssl_do_msg_callback(ssl, 1 /* write */, SSL3_RT_HANDSHAKE, msg);
// TODO(svaldez): Move this up a layer to fix abstraction for SSLTranscript on
// hs.
if (ssl->s3->hs != NULL &&
@@ -214,7 +213,7 @@
}
ssl_do_msg_callback(ssl, 1 /* write */, SSL3_RT_CHANGE_CIPHER_SPEC,
- kChangeCipherSpec, sizeof(kChangeCipherSpec));
+ kChangeCipherSpec);
return 1;
}
@@ -224,7 +223,7 @@
return 0;
}
- ssl_do_msg_callback(ssl, 1 /* write */, SSL3_RT_ALERT, alert, sizeof(alert));
+ ssl_do_msg_callback(ssl, 1 /* write */, SSL3_RT_ALERT, alert);
ssl_do_info_callback(ssl, SSL_CB_WRITE_ALERT, ((int)level << 8) | desc);
return 1;
}
@@ -359,7 +358,7 @@
if (ret <= 0) {
return ret;
}
- const uint8_t *p = ssl_read_buffer(ssl);
+ const uint8_t *p = ssl_read_buffer(ssl).data();
// Some dedicated error codes for protocol mixups should the application wish
// to interpret them differently. (These do not overlap with ClientHello or
@@ -402,9 +401,7 @@
return ret;
}
- CBS v2_client_hello;
- CBS_init(&v2_client_hello, ssl_read_buffer(ssl) + 2, msg_length);
-
+ CBS v2_client_hello = CBS(ssl_read_buffer(ssl).subspan(2, msg_length));
// The V2ClientHello without the length is incorporated into the handshake
// hash. This is only ever called at the start of the handshake, so hs is
// guaranteed to be non-NULL.
@@ -414,7 +411,7 @@
}
ssl_do_msg_callback(ssl, 0 /* read */, 0 /* V2ClientHello */,
- CBS_data(&v2_client_hello), CBS_len(&v2_client_hello));
+ v2_client_hello);
uint8_t msg_type;
uint16_t version, cipher_spec_length, session_id_length, challenge_length;
@@ -530,8 +527,7 @@
out->is_v2_hello = ssl->s3->is_v2_hello;
if (!ssl->s3->has_message) {
if (!out->is_v2_hello) {
- ssl_do_msg_callback(ssl, 0 /* read */, SSL3_RT_HANDSHAKE,
- CBS_data(&out->raw), CBS_len(&out->raw));
+ ssl_do_msg_callback(ssl, 0 /* read */, SSL3_RT_HANDSHAKE, out->raw);
}
ssl->s3->has_message = true;
}
diff --git a/ssl/s3_pkt.cc b/ssl/s3_pkt.cc
index 5334145..48de23f 100644
--- a/ssl/s3_pkt.cc
+++ b/ssl/s3_pkt.cc
@@ -141,12 +141,11 @@
return 0;
}
- CBS body;
+ Span<uint8_t> body;
uint8_t type, alert = SSL_AD_DECODE_ERROR;
size_t consumed;
- enum ssl_open_record_t open_ret =
- tls_open_record(ssl, &type, &body, &consumed, &alert,
- ssl_read_buffer(ssl), ssl_read_buffer_len(ssl));
+ enum ssl_open_record_t open_ret = tls_open_record(
+ ssl, &type, &body, &consumed, &alert, ssl_read_buffer(ssl));
if (open_ret != ssl_open_record_partial) {
ssl_read_buffer_consume(ssl, consumed);
}
@@ -160,15 +159,15 @@
}
case ssl_open_record_success: {
- if (CBS_len(&body) > 0xffff) {
+ if (body.size() > 0xffff) {
OPENSSL_PUT_ERROR(SSL, ERR_R_OVERFLOW);
return -1;
}
SSL3_RECORD *rr = &ssl->s3->rrec;
rr->type = type;
- rr->length = (uint16_t)CBS_len(&body);
- rr->data = (uint8_t *)CBS_data(&body);
+ rr->length = static_cast<uint16_t>(body.size());
+ rr->data = body.data();
return 1;
}
@@ -483,8 +482,8 @@
return -1;
}
- ssl_do_msg_callback(ssl, 0 /* read */, SSL3_RT_CHANGE_CIPHER_SPEC, rr->data,
- rr->length);
+ ssl_do_msg_callback(ssl, 0 /* read */, SSL3_RT_CHANGE_CIPHER_SPEC,
+ MakeSpan(rr->data, rr->length));
rr->length = 0;
ssl_read_buffer_discard(ssl);
@@ -575,8 +574,7 @@
BIO_flush(ssl->wbio);
}
- ssl_do_msg_callback(ssl, 1 /* write */, SSL3_RT_ALERT, ssl->s3->send_alert,
- 2);
+ ssl_do_msg_callback(ssl, 1 /* write */, SSL3_RT_ALERT, ssl->s3->send_alert);
int alert = (ssl->s3->send_alert[0] << 8) | ssl->s3->send_alert[1];
ssl_do_info_callback(ssl, SSL_CB_WRITE_ALERT, alert);
diff --git a/ssl/ssl_aead_ctx.cc b/ssl/ssl_aead_ctx.cc
index 8856f74..775827c 100644
--- a/ssl/ssl_aead_ctx.cc
+++ b/ssl/ssl_aead_ctx.cc
@@ -225,11 +225,12 @@
return len;
}
-bool SSLAEADContext::Open(CBS *out, uint8_t type, uint16_t record_version,
- const uint8_t seqnum[8], uint8_t *in, size_t in_len) {
+bool SSLAEADContext::Open(Span<uint8_t> *out, uint8_t type,
+ uint16_t record_version, const uint8_t seqnum[8],
+ Span<uint8_t> in) {
if (is_null_cipher() || FUZZER_MODE) {
// Handle the initial NULL cipher.
- CBS_init(out, in, in_len);
+ *out = in;
return true;
}
@@ -238,12 +239,12 @@
size_t plaintext_len = 0;
if (!omit_length_in_ad_) {
size_t overhead = MaxOverhead();
- if (in_len < overhead) {
+ if (in.size() < overhead) {
// Publicly invalid.
OPENSSL_PUT_ERROR(SSL, SSL_R_BAD_PACKET_LENGTH);
return false;
}
- plaintext_len = in_len - overhead;
+ plaintext_len = in.size() - overhead;
}
uint8_t ad[13];
size_t ad_len =
@@ -264,14 +265,13 @@
// Add the variable nonce.
if (variable_nonce_included_in_record_) {
- if (in_len < variable_nonce_len_) {
+ if (in.size() < variable_nonce_len_) {
// Publicly invalid.
OPENSSL_PUT_ERROR(SSL, SSL_R_BAD_PACKET_LENGTH);
return false;
}
- OPENSSL_memcpy(nonce + nonce_len, in, variable_nonce_len_);
- in += variable_nonce_len_;
- in_len -= variable_nonce_len_;
+ OPENSSL_memcpy(nonce + nonce_len, in.data(), variable_nonce_len_);
+ in = in.subspan(variable_nonce_len_);
} else {
assert(variable_nonce_len_ == 8);
OPENSSL_memcpy(nonce + nonce_len, seqnum, variable_nonce_len_);
@@ -288,11 +288,11 @@
// Decrypt in-place.
size_t len;
- if (!EVP_AEAD_CTX_open(ctx_.get(), in, &len, in_len, nonce, nonce_len, in,
- in_len, ad, ad_len)) {
+ if (!EVP_AEAD_CTX_open(ctx_.get(), in.data(), &len, in.size(), nonce,
+ nonce_len, in.data(), in.size(), ad, ad_len)) {
return false;
}
- CBS_init(out, in, len);
+ *out = in.subspan(0, len);
return true;
}
diff --git a/ssl/ssl_buffer.cc b/ssl/ssl_buffer.cc
index b424138..79f0cae 100644
--- a/ssl/ssl_buffer.cc
+++ b/ssl/ssl_buffer.cc
@@ -89,12 +89,9 @@
OPENSSL_memset(buf, 0, sizeof(SSL3_BUFFER));
}
-uint8_t *ssl_read_buffer(SSL *ssl) {
- return ssl->s3->read_buffer.buf + ssl->s3->read_buffer.offset;
-}
-
-size_t ssl_read_buffer_len(const SSL *ssl) {
- return ssl->s3->read_buffer.len;
+Span<uint8_t> ssl_read_buffer(SSL *ssl) {
+ return MakeSpan(ssl->s3->read_buffer.buf + ssl->s3->read_buffer.offset,
+ ssl->s3->read_buffer.len);
}
static int dtls_read_buffer_next_packet(SSL *ssl) {
diff --git a/ssl/ssl_cert.cc b/ssl/ssl_cert.cc
index 094d85a..de761d6 100644
--- a/ssl/ssl_cert.cc
+++ b/ssl/ssl_cert.cc
@@ -599,7 +599,8 @@
!CBS_get_optional_asn1(
&tbs_cert, &outer_extensions, &has_extensions,
CBS_ASN1_CONSTRUCTED | CBS_ASN1_CONTEXT_SPECIFIC | 3)) {
- goto parse_err;
+ OPENSSL_PUT_ERROR(SSL, SSL_R_CANNOT_PARSE_LEAF_CERT);
+ return 0;
}
if (!has_extensions) {
@@ -608,7 +609,8 @@
CBS extensions;
if (!CBS_get_asn1(&outer_extensions, &extensions, CBS_ASN1_SEQUENCE)) {
- goto parse_err;
+ OPENSSL_PUT_ERROR(SSL, SSL_R_CANNOT_PARSE_LEAF_CERT);
+ return 0;
}
while (CBS_len(&extensions) > 0) {
@@ -619,7 +621,8 @@
!CBS_get_asn1(&extension, NULL, CBS_ASN1_BOOLEAN)) ||
!CBS_get_asn1(&extension, &contents, CBS_ASN1_OCTETSTRING) ||
CBS_len(&extension) != 0) {
- goto parse_err;
+ OPENSSL_PUT_ERROR(SSL, SSL_R_CANNOT_PARSE_LEAF_CERT);
+ return 0;
}
static const uint8_t kKeyUsageOID[3] = {0x55, 0x1d, 0x0f};
@@ -632,13 +635,15 @@
CBS bit_string;
if (!CBS_get_asn1(&contents, &bit_string, CBS_ASN1_BITSTRING) ||
CBS_len(&contents) != 0) {
- goto parse_err;
+ OPENSSL_PUT_ERROR(SSL, SSL_R_CANNOT_PARSE_LEAF_CERT);
+ return 0;
}
// This is the KeyUsage extension. See
// https://tools.ietf.org/html/rfc5280#section-4.2.1.3
if (!CBS_is_valid_asn1_bitstring(&bit_string)) {
- goto parse_err;
+ OPENSSL_PUT_ERROR(SSL, SSL_R_CANNOT_PARSE_LEAF_CERT);
+ return 0;
}
if (!CBS_asn1_bitstring_has_bit(&bit_string, 0)) {
@@ -651,10 +656,6 @@
// No KeyUsage extension found.
return 1;
-
-parse_err:
- OPENSSL_PUT_ERROR(SSL, SSL_R_CANNOT_PARSE_LEAF_CERT);
- return 0;
}
UniquePtr<STACK_OF(CRYPTO_BUFFER)> ssl_parse_client_CA_list(SSL *ssl,
diff --git a/ssl/ssl_lib.cc b/ssl/ssl_lib.cc
index f62d155..89eb6fe 100644
--- a/ssl/ssl_lib.cc
+++ b/ssl/ssl_lib.cc
@@ -344,7 +344,7 @@
}
void ssl_do_msg_callback(SSL *ssl, int is_write, int content_type,
- const void *buf, size_t len) {
+ Span<const uint8_t> in) {
if (ssl->msg_callback == NULL) {
return;
}
@@ -364,7 +364,7 @@
version = SSL_version(ssl);
}
- ssl->msg_callback(is_write, version, content_type, buf, len, ssl,
+ ssl->msg_callback(is_write, version, content_type, in.data(), in.size(), ssl,
ssl->msg_callback_arg);
}
diff --git a/ssl/tls_record.cc b/ssl/tls_record.cc
index f9033e6..b70e4f5 100644
--- a/ssl/tls_record.cc
+++ b/ssl/tls_record.cc
@@ -187,13 +187,12 @@
return ret;
}
-enum ssl_open_record_t tls_open_record(SSL *ssl, uint8_t *out_type, CBS *out,
- size_t *out_consumed, uint8_t *out_alert,
- uint8_t *in, size_t in_len) {
+enum ssl_open_record_t tls_open_record(SSL *ssl, uint8_t *out_type,
+ Span<uint8_t> *out, size_t *out_consumed,
+ uint8_t *out_alert, Span<uint8_t> in) {
*out_consumed = 0;
- CBS cbs;
- CBS_init(&cbs, in, in_len);
+ CBS cbs = CBS(in);
// Decode the record header.
uint8_t type;
@@ -234,10 +233,10 @@
return ssl_open_record_partial;
}
- ssl_do_msg_callback(ssl, 0 /* read */, SSL3_RT_HEADER, in,
- SSL3_RT_HEADER_LENGTH);
+ ssl_do_msg_callback(ssl, 0 /* read */, SSL3_RT_HEADER,
+ in.subspan(0, SSL3_RT_HEADER_LENGTH));
- *out_consumed = in_len - CBS_len(&cbs);
+ *out_consumed = in.size() - CBS_len(&cbs);
// Skip early data received when expecting a second ClientHello if we rejected
// 0RTT.
@@ -248,9 +247,9 @@
}
// Decrypt the body in-place.
- if (!ssl->s3->aead_read_ctx->Open(out, type, version, ssl->s3->read_sequence,
- (uint8_t *)CBS_data(&body),
- CBS_len(&body))) {
+ if (!ssl->s3->aead_read_ctx->Open(
+ out, type, version, ssl->s3->read_sequence,
+ MakeSpan(const_cast<uint8_t *>(CBS_data(&body)), CBS_len(&body)))) {
if (ssl->s3->skip_early_data && !ssl->s3->aead_read_ctx->is_null_cipher()) {
ERR_clear_error();
goto skipped_data;
@@ -279,23 +278,25 @@
}
do {
- if (!CBS_get_last_u8(out, &type)) {
+ if (out->empty()) {
OPENSSL_PUT_ERROR(SSL, SSL_R_DECRYPTION_FAILED_OR_BAD_RECORD_MAC);
*out_alert = SSL_AD_DECRYPT_ERROR;
return ssl_open_record_error;
}
+ type = out->back();
+ *out = out->subspan(0, out->size() - 1);
} while (type == 0);
}
// Check the plaintext length.
- if (CBS_len(out) > SSL3_RT_MAX_PLAIN_LENGTH) {
+ if (out->size() > SSL3_RT_MAX_PLAIN_LENGTH) {
OPENSSL_PUT_ERROR(SSL, SSL_R_DATA_LENGTH_TOO_LONG);
*out_alert = SSL_AD_RECORD_OVERFLOW;
return ssl_open_record_error;
}
// Limit the number of consecutive empty records.
- if (CBS_len(out) == 0) {
+ if (out->empty()) {
ssl->s3->empty_record_count++;
if (ssl->s3->empty_record_count > kMaxEmptyRecords) {
OPENSSL_PUT_ERROR(SSL, SSL_R_TOO_MANY_EMPTY_FRAGMENTS);
@@ -310,14 +311,14 @@
if (type == SSL3_RT_ALERT) {
// Return end_of_early_data alerts as-is for the caller to process.
- if (CBS_len(out) == 2 &&
- CBS_data(out)[0] == SSL3_AL_WARNING &&
- CBS_data(out)[1] == TLS1_AD_END_OF_EARLY_DATA) {
+ if (out->size() == 2 &&
+ (*out)[0] == SSL3_AL_WARNING &&
+ (*out)[1] == TLS1_AD_END_OF_EARLY_DATA) {
*out_type = type;
return ssl_open_record_success;
}
- return ssl_process_alert(ssl, out_alert, CBS_data(out), CBS_len(out));
+ return ssl_process_alert(ssl, out_alert, *out);
}
ssl->s3->warning_alert_count = 0;
@@ -390,8 +391,8 @@
return 0;
}
- ssl_do_msg_callback(ssl, 1 /* write */, SSL3_RT_HEADER, out_prefix,
- SSL3_RT_HEADER_LENGTH);
+ ssl_do_msg_callback(ssl, 1 /* write */, SSL3_RT_HEADER,
+ MakeSpan(out_prefix, SSL3_RT_HEADER_LENGTH));
return 1;
}
@@ -516,15 +517,15 @@
}
enum ssl_open_record_t ssl_process_alert(SSL *ssl, uint8_t *out_alert,
- const uint8_t *in, size_t in_len) {
+ Span<const uint8_t> in) {
// Alerts records may not contain fragmented or multiple alerts.
- if (in_len != 2) {
+ if (in.size() != 2) {
*out_alert = SSL_AD_DECODE_ERROR;
OPENSSL_PUT_ERROR(SSL, SSL_R_BAD_ALERT);
return ssl_open_record_error;
}
- ssl_do_msg_callback(ssl, 0 /* read */, SSL3_RT_ALERT, in, in_len);
+ ssl_do_msg_callback(ssl, 0 /* read */, SSL3_RT_ALERT, in);
const uint8_t alert_level = in[0];
const uint8_t alert_descr = in[1];
@@ -584,10 +585,10 @@
return OpenRecordResult::kError;
}
- CBS plaintext;
+ Span<uint8_t> plaintext;
uint8_t type;
const ssl_open_record_t result = tls_open_record(
- ssl, &type, &plaintext, out_record_len, out_alert, in.data(), in.size());
+ ssl, &type, &plaintext, out_record_len, out_alert, in);
switch (result) {
case ssl_open_record_success:
@@ -595,8 +596,7 @@
*out_alert = SSL_AD_UNEXPECTED_MESSAGE;
return OpenRecordResult::kError;
}
- *out = MakeSpan(
- const_cast<uint8_t*>(CBS_data(&plaintext)), CBS_len(&plaintext));
+ *out = plaintext;
return OpenRecordResult::kOK;
case ssl_open_record_discard:
return OpenRecordResult::kDiscard;