Spanify the DTLS packet assembly logic a bit
The out/out_len/max_out trio can at least be out(span)/out_len pairs.
Still a ways to go, but this is a little tidier.
Bug: 374890768
Change-Id: I8816eb2aff9d35192af15992fc307f18c53ce8e4
Reviewed-on: https://boringssl-review.googlesource.com/c/boringssl/+/72307
Commit-Queue: David Benjamin <davidben@google.com>
Reviewed-by: Nick Harper <nharper@chromium.org>
diff --git a/ssl/d1_both.cc b/ssl/d1_both.cc
index f262094..7f077a3 100644
--- a/ssl/d1_both.cc
+++ b/ssl/d1_both.cc
@@ -702,8 +702,8 @@
// seal_next_message seals |msg|, which must be the next message, to |out|. If
// progress was made, it returns |seal_partial| or |seal_success| and sets
// |*out_len| to the number of bytes written.
-static enum seal_result_t seal_next_message(SSL *ssl, uint8_t *out,
- size_t *out_len, size_t max_out,
+static enum seal_result_t seal_next_message(SSL *ssl, Span<uint8_t> out,
+ size_t *out_len,
const DTLSOutgoingMessage *msg) {
assert(ssl->d1->outgoing_written < ssl->d1->outgoing_messages.size());
assert(msg == &ssl->d1->outgoing_messages[ssl->d1->outgoing_written]);
@@ -714,12 +714,12 @@
if (msg->is_ccs) {
// Check there is room for the ChangeCipherSpec.
static const uint8_t kChangeCipherSpec[1] = {SSL3_MT_CCS};
- if (max_out < sizeof(kChangeCipherSpec) + overhead) {
+ if (out.size() < sizeof(kChangeCipherSpec) + overhead) {
return seal_no_progress;
}
DTLSRecordNumber record_number;
- if (!dtls_seal_record(ssl, &record_number, out, out_len, max_out,
+ if (!dtls_seal_record(ssl, &record_number, out.data(), out_len, out.size(),
SSL3_RT_CHANGE_CIPHER_SPEC, kChangeCipherSpec,
sizeof(kChangeCipherSpec), msg->epoch)) {
return seal_error;
@@ -731,34 +731,34 @@
}
// DTLS messages are serialized as a single fragment in |msg|.
- CBS cbs, body;
+ CBS cbs(msg->data), body;
struct hm_header_st hdr;
- CBS_init(&cbs, msg->data.data(), msg->data.size());
- if (!dtls1_parse_fragment(&cbs, &hdr, &body) ||
- hdr.frag_off != 0 ||
- hdr.frag_len != CBS_len(&body) ||
+ if (!dtls1_parse_fragment(&cbs, &hdr, &body) || //
+ hdr.frag_off != 0 || //
+ hdr.frag_len != CBS_len(&body) || //
hdr.msg_len != CBS_len(&body) ||
- !CBS_skip(&body, ssl->d1->outgoing_offset) ||
+ !CBS_skip(&body, ssl->d1->outgoing_offset) || //
CBS_len(&cbs) != 0) {
OPENSSL_PUT_ERROR(SSL, ERR_R_INTERNAL_ERROR);
return seal_error;
}
// Determine how much progress can be made.
- if (max_out < DTLS1_HM_HEADER_LENGTH + 1 + overhead || max_out < prefix) {
+ if (out.size() < DTLS1_HM_HEADER_LENGTH + 1 + overhead ||
+ out.size() < prefix) {
return seal_no_progress;
}
size_t todo = CBS_len(&body);
- if (todo > max_out - DTLS1_HM_HEADER_LENGTH - overhead) {
- todo = max_out - DTLS1_HM_HEADER_LENGTH - overhead;
+ if (todo > out.size() - DTLS1_HM_HEADER_LENGTH - overhead) {
+ todo = out.size() - DTLS1_HM_HEADER_LENGTH - overhead;
}
// Assemble a fragment, to be sealed in-place.
ScopedCBB cbb;
CBB child;
- uint8_t *frag = out + prefix;
- size_t max_frag = max_out - prefix, frag_len;
- if (!CBB_init_fixed(cbb.get(), frag, max_frag) ||
+ Span<uint8_t> frag = out.subspan(prefix);
+ size_t frag_len;
+ if (!CBB_init_fixed(cbb.get(), frag.data(), frag.size()) ||
!CBB_add_u8(cbb.get(), hdr.type) ||
!CBB_add_u24(cbb.get(), hdr.msg_len) ||
!CBB_add_u16(cbb.get(), hdr.seq) ||
@@ -770,12 +770,12 @@
return seal_error;
}
- ssl_do_msg_callback(ssl, 1 /* write */, SSL3_RT_HANDSHAKE,
- MakeSpan(frag, frag_len));
+ frag = frag.first(frag_len);
+ ssl_do_msg_callback(ssl, 1 /* write */, SSL3_RT_HANDSHAKE, frag);
DTLSRecordNumber record_number;
- if (!dtls_seal_record(ssl, &record_number, out, out_len, max_out,
- SSL3_RT_HANDSHAKE, out + prefix, frag_len,
+ if (!dtls_seal_record(ssl, &record_number, out.data(), out_len, out.size(),
+ SSL3_RT_HANDSHAKE, frag.data(), frag.size(),
msg->epoch)) {
return seal_error;
}
@@ -793,8 +793,7 @@
// seal_next_packet writes as much of the next flight as possible to |out| and
// advances |ssl->d1->outgoing_written| and |ssl->d1->outgoing_offset| as
// appropriate.
-static bool seal_next_packet(SSL *ssl, uint8_t *out, size_t *out_len,
- size_t max_out) {
+static bool seal_next_packet(SSL *ssl, Span<uint8_t> out, size_t *out_len) {
bool made_progress = false;
size_t total = 0;
assert(ssl->d1->outgoing_written < ssl->d1->outgoing_messages.size());
@@ -803,7 +802,7 @@
const DTLSOutgoingMessage *msg =
&ssl->d1->outgoing_messages[ssl->d1->outgoing_written];
size_t len;
- enum seal_result_t ret = seal_next_message(ssl, out, &len, max_out, msg);
+ enum seal_result_t ret = seal_next_message(ssl, out, &len, msg);
switch (ret) {
case seal_error:
return false;
@@ -813,8 +812,7 @@
case seal_partial:
case seal_success:
- out += len;
- max_out -= len;
+ out = out.subspan(len);
total += len;
made_progress = true;
@@ -859,7 +857,7 @@
uint32_t old_offset = ssl->d1->outgoing_offset;
size_t packet_len;
- if (!seal_next_packet(ssl, packet.data(), &packet_len, packet.size())) {
+ if (!seal_next_packet(ssl, MakeSpan(packet), &packet_len)) {
return -1;
}