blob: f3390f0b9a72c14b9a0aef148135ef448bfe32b6 [file] [log] [blame]
QUICHE teama6ef0a62019-03-07 20:34:33 -05001// Copyright (c) 2012 The Chromium Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5#include "net/third_party/quiche/src/quic/core/quic_packet_creator.h"
6
7#include <algorithm>
8#include <cstdint>
vasilvv872e7a32019-03-12 16:42:44 -07009#include <string>
QUICHE teama6ef0a62019-03-07 20:34:33 -050010
QUICHE teama6ef0a62019-03-07 20:34:33 -050011#include "net/third_party/quiche/src/quic/core/crypto/crypto_protocol.h"
12#include "net/third_party/quiche/src/quic/core/quic_connection_id.h"
ianswettb239f862019-04-05 09:15:06 -070013#include "net/third_party/quiche/src/quic/core/quic_constants.h"
QUICHE teama6ef0a62019-03-07 20:34:33 -050014#include "net/third_party/quiche/src/quic/core/quic_data_writer.h"
15#include "net/third_party/quiche/src/quic/core/quic_types.h"
16#include "net/third_party/quiche/src/quic/core/quic_utils.h"
ianswettb239f862019-04-05 09:15:06 -070017#include "net/third_party/quiche/src/quic/core/quic_versions.h"
QUICHE teama6ef0a62019-03-07 20:34:33 -050018#include "net/third_party/quiche/src/quic/platform/api/quic_aligned.h"
19#include "net/third_party/quiche/src/quic/platform/api/quic_arraysize.h"
20#include "net/third_party/quiche/src/quic/platform/api/quic_bug_tracker.h"
21#include "net/third_party/quiche/src/quic/platform/api/quic_flag_utils.h"
22#include "net/third_party/quiche/src/quic/platform/api/quic_flags.h"
23#include "net/third_party/quiche/src/quic/platform/api/quic_logging.h"
24#include "net/third_party/quiche/src/quic/platform/api/quic_ptr_util.h"
bnc2c2444e2019-05-03 08:18:23 -070025#include "net/third_party/quiche/src/quic/platform/api/quic_str_cat.h"
QUICHE teama6ef0a62019-03-07 20:34:33 -050026#include "net/third_party/quiche/src/quic/platform/api/quic_string_piece.h"
27#include "net/third_party/quiche/src/quic/platform/api/quic_text_utils.h"
28
29namespace quic {
30namespace {
31
32QuicLongHeaderType EncryptionlevelToLongHeaderType(EncryptionLevel level) {
33 switch (level) {
QUICHE team6987b4a2019-03-15 16:23:04 -070034 case ENCRYPTION_INITIAL:
QUICHE teama6ef0a62019-03-07 20:34:33 -050035 return INITIAL;
QUICHE team88ea0082019-03-15 10:05:26 -070036 case ENCRYPTION_HANDSHAKE:
37 return HANDSHAKE;
QUICHE teama6ef0a62019-03-07 20:34:33 -050038 case ENCRYPTION_ZERO_RTT:
39 return ZERO_RTT_PROTECTED;
40 case ENCRYPTION_FORWARD_SECURE:
41 QUIC_BUG
42 << "Try to derive long header type for packet with encryption level: "
43 << QuicUtils::EncryptionLevelToString(level);
44 return INVALID_PACKET_TYPE;
45 default:
46 QUIC_BUG << QuicUtils::EncryptionLevelToString(level);
47 return INVALID_PACKET_TYPE;
48 }
49}
50
51} // namespace
52
53#define ENDPOINT \
54 (framer_->perspective() == Perspective::IS_SERVER ? "Server: " : "Client: ")
55
56QuicPacketCreator::QuicPacketCreator(QuicConnectionId connection_id,
57 QuicFramer* framer,
58 DelegateInterface* delegate)
59 : QuicPacketCreator(connection_id,
60 framer,
61 QuicRandom::GetInstance(),
62 delegate) {}
63
64QuicPacketCreator::QuicPacketCreator(QuicConnectionId connection_id,
65 QuicFramer* framer,
66 QuicRandom* random,
67 DelegateInterface* delegate)
68 : delegate_(delegate),
69 debug_delegate_(nullptr),
70 framer_(framer),
71 random_(random),
72 send_version_in_packet_(framer->perspective() == Perspective::IS_CLIENT),
73 have_diversification_nonce_(false),
74 max_packet_length_(0),
75 connection_id_included_(CONNECTION_ID_PRESENT),
76 packet_size_(0),
77 connection_id_(connection_id),
78 packet_(QuicPacketNumber(),
79 PACKET_1BYTE_PACKET_NUMBER,
80 nullptr,
81 0,
82 false,
83 false),
84 pending_padding_bytes_(0),
85 needs_full_padding_(false),
wub98669f52019-04-18 10:49:18 -070086 can_set_transmission_type_(false) {
QUICHE teama6ef0a62019-03-07 20:34:33 -050087 SetMaxPacketLength(kDefaultMaxPacketSize);
88}
89
90QuicPacketCreator::~QuicPacketCreator() {
91 DeleteFrames(&packet_.retransmittable_frames);
92}
93
94void QuicPacketCreator::SetEncrypter(EncryptionLevel level,
95 std::unique_ptr<QuicEncrypter> encrypter) {
96 framer_->SetEncrypter(level, std::move(encrypter));
97 max_plaintext_size_ = framer_->GetMaxPlaintextSize(max_packet_length_);
98}
99
100bool QuicPacketCreator::CanSetMaxPacketLength() const {
101 // |max_packet_length_| should not be changed mid-packet.
102 return queued_frames_.empty();
103}
104
105void QuicPacketCreator::SetMaxPacketLength(QuicByteCount length) {
106 DCHECK(CanSetMaxPacketLength());
107
108 // Avoid recomputing |max_plaintext_size_| if the length does not actually
109 // change.
110 if (length == max_packet_length_) {
111 return;
112 }
113
114 max_packet_length_ = length;
115 max_plaintext_size_ = framer_->GetMaxPlaintextSize(max_packet_length_);
116}
117
118// Stops serializing version of the protocol in packets sent after this call.
119// A packet that is already open might send kQuicVersionSize bytes less than the
120// maximum packet size if we stop sending version before it is serialized.
121void QuicPacketCreator::StopSendingVersion() {
122 DCHECK(send_version_in_packet_);
123 DCHECK_LE(framer_->transport_version(), QUIC_VERSION_43);
124 send_version_in_packet_ = false;
125 if (packet_size_ > 0) {
126 DCHECK_LT(kQuicVersionSize, packet_size_);
127 packet_size_ -= kQuicVersionSize;
128 }
129}
130
131void QuicPacketCreator::SetDiversificationNonce(
132 const DiversificationNonce& nonce) {
133 DCHECK(!have_diversification_nonce_);
134 have_diversification_nonce_ = true;
135 diversification_nonce_ = nonce;
136}
137
138void QuicPacketCreator::UpdatePacketNumberLength(
139 QuicPacketNumber least_packet_awaited_by_peer,
140 QuicPacketCount max_packets_in_flight) {
141 if (!queued_frames_.empty()) {
142 // Don't change creator state if there are frames queued.
143 QUIC_BUG << "Called UpdatePacketNumberLength with " << queued_frames_.size()
144 << " queued_frames. First frame type:"
145 << queued_frames_.front().type
146 << " last frame type:" << queued_frames_.back().type;
147 return;
148 }
149
150 DCHECK_LE(least_packet_awaited_by_peer, packet_.packet_number + 1);
151 const uint64_t current_delta =
152 packet_.packet_number + 1 - least_packet_awaited_by_peer;
153 const uint64_t delta = std::max(current_delta, max_packets_in_flight);
154 packet_.packet_number_length = QuicFramer::GetMinPacketNumberLength(
155 framer_->transport_version(), QuicPacketNumber(delta * 4));
156}
157
158bool QuicPacketCreator::ConsumeCryptoData(EncryptionLevel level,
159 size_t write_length,
160 QuicStreamOffset offset,
161 TransmissionType transmission_type,
162 QuicFrame* frame) {
163 if (!CreateCryptoFrame(level, write_length, offset, frame)) {
164 return false;
165 }
166 // When crypto data was sent in stream frames, ConsumeData is called with
167 // |needs_full_padding = true|. Keep the same behavior here when sending
168 // crypto frames.
169 //
170 // TODO(nharper): Check what the IETF drafts say about padding out initial
171 // messages and change this as appropriate.
172 needs_full_padding_ = true;
173 return AddFrame(*frame, /*save_retransmittable_frames*/ true,
174 transmission_type);
175}
176
177bool QuicPacketCreator::ConsumeData(QuicStreamId id,
ianswette28f0222019-04-04 13:31:22 -0700178 size_t data_size,
QUICHE teama6ef0a62019-03-07 20:34:33 -0500179 QuicStreamOffset offset,
180 bool fin,
181 bool needs_full_padding,
182 TransmissionType transmission_type,
183 QuicFrame* frame) {
QUICHE teamf08778a2019-03-14 08:10:26 -0700184 if (!HasRoomForStreamFrame(id, offset, data_size)) {
QUICHE teama6ef0a62019-03-07 20:34:33 -0500185 return false;
186 }
QUICHE teamf08778a2019-03-14 08:10:26 -0700187 CreateStreamFrame(id, data_size, offset, fin, frame);
QUICHE teama6ef0a62019-03-07 20:34:33 -0500188 // Explicitly disallow multi-packet CHLOs.
189 if (FLAGS_quic_enforce_single_packet_chlo &&
ianswette28f0222019-04-04 13:31:22 -0700190 StreamFrameIsClientHello(frame->stream_frame) &&
191 frame->stream_frame.data_length < data_size) {
vasilvvc48c8712019-03-11 13:38:16 -0700192 const std::string error_details =
QUICHE teama6ef0a62019-03-07 20:34:33 -0500193 "Client hello won't fit in a single packet.";
194 QUIC_BUG << error_details << " Constructed stream frame length: "
195 << frame->stream_frame.data_length
ianswette28f0222019-04-04 13:31:22 -0700196 << " CHLO length: " << data_size;
QUICHE teama6ef0a62019-03-07 20:34:33 -0500197 delegate_->OnUnrecoverableError(QUIC_CRYPTO_CHLO_TOO_LARGE, error_details,
198 ConnectionCloseSource::FROM_SELF);
199 return false;
200 }
201 if (!AddFrame(*frame, /*save_retransmittable_frames=*/true,
202 transmission_type)) {
203 // Fails if we try to write unencrypted stream data.
204 return false;
205 }
206 if (needs_full_padding) {
207 needs_full_padding_ = true;
208 }
209
210 return true;
211}
212
213bool QuicPacketCreator::HasRoomForStreamFrame(QuicStreamId id,
214 QuicStreamOffset offset,
215 size_t data_size) {
216 return BytesFree() >
217 QuicFramer::GetMinStreamFrameSize(framer_->transport_version(), id,
218 offset, true, data_size);
219}
220
221bool QuicPacketCreator::HasRoomForMessageFrame(QuicByteCount length) {
222 return BytesFree() >= QuicFramer::GetMessageFrameSize(
223 framer_->transport_version(), true, length);
224}
225
226// TODO(fkastenholz): this method should not use constant values for
227// the last-frame-in-packet and data-length parameters to
228// GetMinStreamFrameSize. Proper values should be plumbed in from
229// higher up. This was left this way for now for a few reasons. First,
230// higher up calls to StreamFramePacketOverhead() do not always know
231// this information, leading to a cascade of changes and B) the
232// higher-up software does not always loop, calling
233// StreamFramePacketOverhead() once for every packet -- eg there is
234// a test in quic_connection_test that calls it once and assumes that
235// the value is the same for all packets.
236
237// static
238size_t QuicPacketCreator::StreamFramePacketOverhead(
239 QuicTransportVersion version,
240 QuicConnectionIdLength destination_connection_id_length,
241 QuicConnectionIdLength source_connection_id_length,
242 bool include_version,
243 bool include_diversification_nonce,
244 QuicPacketNumberLength packet_number_length,
245 QuicVariableLengthIntegerLength retry_token_length_length,
246 QuicVariableLengthIntegerLength length_length,
247 QuicStreamOffset offset) {
248 return GetPacketHeaderSize(version, destination_connection_id_length,
249 source_connection_id_length, include_version,
250 include_diversification_nonce,
251 packet_number_length, retry_token_length_length, 0,
252 length_length) +
253
254 // Assumes this is a packet with a single stream frame in it. Since
255 // last_frame_in_packet is set true, the size of the length field is
256 // not included in the calculation. This is OK because in other places
257 // in the code, the logic adds back 2 (the size of the Google QUIC
258 // length) when a frame is not the last frame of the packet. This is
259 // also acceptable for IETF Quic; even though the length field could be
260 // 8 bytes long, in practice it will not be longer than 2 bytes (enough
261 // to encode 16K). A length that would be encoded in 2 bytes (0xfff)
262 // is passed just for cleanliness.
263 //
264 // TODO(fkastenholz): This is very hacky and feels brittle. Ideally we
265 // would calculate the correct lengths at the correct time, based on
266 // the state at that time/place.
267 QuicFramer::GetMinStreamFrameSize(version, 1u, offset, true,
dschinazi66dea072019-04-09 11:41:06 -0700268 kMaxOutgoingPacketSize);
QUICHE teama6ef0a62019-03-07 20:34:33 -0500269}
270
271void QuicPacketCreator::CreateStreamFrame(QuicStreamId id,
QUICHE teamf08778a2019-03-14 08:10:26 -0700272 size_t data_size,
QUICHE teama6ef0a62019-03-07 20:34:33 -0500273 QuicStreamOffset offset,
274 bool fin,
275 QuicFrame* frame) {
QUICHE teama6ef0a62019-03-07 20:34:33 -0500276 DCHECK_GT(
277 max_packet_length_,
278 StreamFramePacketOverhead(
279 framer_->transport_version(), GetDestinationConnectionIdLength(),
280 GetSourceConnectionIdLength(), kIncludeVersion,
281 IncludeNonceInPublicHeader(), PACKET_6BYTE_PACKET_NUMBER,
282 GetRetryTokenLengthLength(), GetLengthLength(), offset));
283
284 QUIC_BUG_IF(!HasRoomForStreamFrame(id, offset, data_size))
285 << "No room for Stream frame, BytesFree: " << BytesFree()
286 << " MinStreamFrameSize: "
287 << QuicFramer::GetMinStreamFrameSize(framer_->transport_version(), id,
288 offset, true, data_size);
289
QUICHE teamf08778a2019-03-14 08:10:26 -0700290 QUIC_BUG_IF(data_size == 0 && !fin)
291 << "Creating a stream frame for stream ID:" << id
292 << " with no data or fin.";
QUICHE teama6ef0a62019-03-07 20:34:33 -0500293 size_t min_frame_size = QuicFramer::GetMinStreamFrameSize(
294 framer_->transport_version(), id, offset,
295 /* last_frame_in_packet= */ true, data_size);
296 size_t bytes_consumed =
297 std::min<size_t>(BytesFree() - min_frame_size, data_size);
298
299 bool set_fin = fin && bytes_consumed == data_size; // Last frame.
300 *frame = QuicFrame(QuicStreamFrame(id, set_fin, offset, bytes_consumed));
301}
302
303bool QuicPacketCreator::CreateCryptoFrame(EncryptionLevel level,
304 size_t write_length,
305 QuicStreamOffset offset,
306 QuicFrame* frame) {
307 size_t min_frame_size =
308 QuicFramer::GetMinCryptoFrameSize(write_length, offset);
309 if (BytesFree() <= min_frame_size) {
310 return false;
311 }
312 size_t max_write_length = BytesFree() - min_frame_size;
313 size_t bytes_consumed = std::min<size_t>(max_write_length, write_length);
314 *frame = QuicFrame(new QuicCryptoFrame(level, offset, bytes_consumed));
315 return true;
316}
317
318void QuicPacketCreator::ReserializeAllFrames(
319 const QuicPendingRetransmission& retransmission,
320 char* buffer,
321 size_t buffer_len) {
322 DCHECK(queued_frames_.empty());
323 DCHECK_EQ(0, packet_.num_padding_bytes);
324 QUIC_BUG_IF(retransmission.retransmittable_frames.empty())
325 << "Attempt to serialize empty packet";
326 const EncryptionLevel default_encryption_level = packet_.encryption_level;
327
328 // Temporarily set the packet number length and change the encryption level.
329 packet_.packet_number_length = retransmission.packet_number_length;
330 if (retransmission.num_padding_bytes == -1) {
331 // Only retransmit padding when original packet needs full padding. Padding
332 // from pending_padding_bytes_ are not retransmitted.
333 needs_full_padding_ = true;
334 }
335 // Only preserve the original encryption level if it's a handshake packet or
336 // if we haven't gone forward secure.
337 if (retransmission.has_crypto_handshake ||
338 packet_.encryption_level != ENCRYPTION_FORWARD_SECURE) {
339 packet_.encryption_level = retransmission.encryption_level;
340 }
341
342 // Serialize the packet and restore packet number length state.
343 for (const QuicFrame& frame : retransmission.retransmittable_frames) {
344 bool success = AddFrame(frame, false, retransmission.transmission_type);
345 QUIC_BUG_IF(!success) << " Failed to add frame of type:" << frame.type
346 << " num_frames:"
347 << retransmission.retransmittable_frames.size()
348 << " retransmission.packet_number_length:"
349 << retransmission.packet_number_length
350 << " packet_.packet_number_length:"
351 << packet_.packet_number_length;
352 }
353 packet_.transmission_type = retransmission.transmission_type;
354 SerializePacket(buffer, buffer_len);
355 packet_.original_packet_number = retransmission.packet_number;
356 OnSerializedPacket();
357 // Restore old values.
358 packet_.encryption_level = default_encryption_level;
359}
360
361void QuicPacketCreator::Flush() {
362 if (!HasPendingFrames() && pending_padding_bytes_ == 0) {
363 return;
364 }
365
dschinazi66dea072019-04-09 11:41:06 -0700366 QUIC_CACHELINE_ALIGNED char stack_buffer[kMaxOutgoingPacketSize];
QUICHE teama6ef0a62019-03-07 20:34:33 -0500367 char* serialized_packet_buffer = delegate_->GetPacketBuffer();
368 if (serialized_packet_buffer == nullptr) {
369 serialized_packet_buffer = stack_buffer;
370 }
371
dschinazi66dea072019-04-09 11:41:06 -0700372 SerializePacket(serialized_packet_buffer, kMaxOutgoingPacketSize);
QUICHE teama6ef0a62019-03-07 20:34:33 -0500373 OnSerializedPacket();
374}
375
376void QuicPacketCreator::OnSerializedPacket() {
377 if (packet_.encrypted_buffer == nullptr) {
vasilvvc48c8712019-03-11 13:38:16 -0700378 const std::string error_details = "Failed to SerializePacket.";
QUICHE teama6ef0a62019-03-07 20:34:33 -0500379 QUIC_BUG << error_details;
380 delegate_->OnUnrecoverableError(QUIC_FAILED_TO_SERIALIZE_PACKET,
381 error_details,
382 ConnectionCloseSource::FROM_SELF);
383 return;
384 }
385
386 SerializedPacket packet(std::move(packet_));
387 ClearPacket();
388 delegate_->OnSerializedPacket(&packet);
389}
390
391void QuicPacketCreator::ClearPacket() {
392 packet_.has_ack = false;
393 packet_.has_stop_waiting = false;
394 packet_.has_crypto_handshake = NOT_HANDSHAKE;
395 packet_.num_padding_bytes = 0;
396 packet_.original_packet_number.Clear();
wub98669f52019-04-18 10:49:18 -0700397 packet_.transmission_type = NOT_RETRANSMISSION;
QUICHE teama6ef0a62019-03-07 20:34:33 -0500398 packet_.encrypted_buffer = nullptr;
399 packet_.encrypted_length = 0;
400 DCHECK(packet_.retransmittable_frames.empty());
401 packet_.largest_acked.Clear();
402 needs_full_padding_ = false;
403}
404
405void QuicPacketCreator::CreateAndSerializeStreamFrame(
406 QuicStreamId id,
407 size_t write_length,
408 QuicStreamOffset iov_offset,
409 QuicStreamOffset stream_offset,
410 bool fin,
411 TransmissionType transmission_type,
412 size_t* num_bytes_consumed) {
413 DCHECK(queued_frames_.empty());
414 // Write out the packet header
415 QuicPacketHeader header;
416 FillPacketHeader(&header);
417
dschinazi66dea072019-04-09 11:41:06 -0700418 QUIC_CACHELINE_ALIGNED char stack_buffer[kMaxOutgoingPacketSize];
QUICHE teama6ef0a62019-03-07 20:34:33 -0500419 char* encrypted_buffer = delegate_->GetPacketBuffer();
420 if (encrypted_buffer == nullptr) {
421 encrypted_buffer = stack_buffer;
422 }
423
dschinazi66dea072019-04-09 11:41:06 -0700424 QuicDataWriter writer(kMaxOutgoingPacketSize, encrypted_buffer);
QUICHE teama6ef0a62019-03-07 20:34:33 -0500425 size_t length_field_offset = 0;
426 if (!framer_->AppendPacketHeader(header, &writer, &length_field_offset)) {
427 QUIC_BUG << "AppendPacketHeader failed";
428 return;
429 }
430
431 // Create a Stream frame with the remaining space.
432 QUIC_BUG_IF(iov_offset == write_length && !fin)
433 << "Creating a stream frame with no data or fin.";
434 const size_t remaining_data_size = write_length - iov_offset;
435 const size_t min_frame_size = QuicFramer::GetMinStreamFrameSize(
436 framer_->transport_version(), id, stream_offset,
437 /* last_frame_in_packet= */ true, remaining_data_size);
438 const size_t available_size =
439 max_plaintext_size_ - writer.length() - min_frame_size;
440 const size_t bytes_consumed =
441 std::min<size_t>(available_size, remaining_data_size);
442
443 const bool set_fin = fin && (bytes_consumed == remaining_data_size);
444 QuicStreamFrame frame(id, set_fin, stream_offset, bytes_consumed);
rchc76cd742019-03-26 16:00:03 -0700445 if (debug_delegate_ != nullptr) {
446 debug_delegate_->OnFrameAddedToPacket(QuicFrame(frame));
447 }
QUICHE teama6ef0a62019-03-07 20:34:33 -0500448 QUIC_DVLOG(1) << ENDPOINT << "Adding frame: " << frame;
449
450 // TODO(ianswett): AppendTypeByte and AppendStreamFrame could be optimized
451 // into one method that takes a QuicStreamFrame, if warranted.
452 if (!framer_->AppendTypeByte(QuicFrame(frame),
453 /* no stream frame length */ true, &writer)) {
454 QUIC_BUG << "AppendTypeByte failed";
455 return;
456 }
457 if (!framer_->AppendStreamFrame(frame, /* no stream frame length */ true,
458 &writer)) {
459 QUIC_BUG << "AppendStreamFrame failed";
460 return;
461 }
462
463 if (!framer_->WriteIetfLongHeaderLength(header, &writer, length_field_offset,
464 packet_.encryption_level)) {
465 return;
466 }
467
wub98669f52019-04-18 10:49:18 -0700468 if (can_set_transmission_type()) {
QUICHE teama6ef0a62019-03-07 20:34:33 -0500469 packet_.transmission_type = transmission_type;
470 }
471
472 size_t encrypted_length = framer_->EncryptInPlace(
473 packet_.encryption_level, packet_.packet_number,
474 GetStartOfEncryptedData(framer_->transport_version(), header),
dschinazi66dea072019-04-09 11:41:06 -0700475 writer.length(), kMaxOutgoingPacketSize, encrypted_buffer);
QUICHE teama6ef0a62019-03-07 20:34:33 -0500476 if (encrypted_length == 0) {
477 QUIC_BUG << "Failed to encrypt packet number " << header.packet_number;
478 return;
479 }
480 // TODO(ianswett): Optimize the storage so RetransmitableFrames can be
481 // unioned with a QuicStreamFrame and a UniqueStreamBuffer.
482 *num_bytes_consumed = bytes_consumed;
483 packet_size_ = 0;
484 packet_.encrypted_buffer = encrypted_buffer;
485 packet_.encrypted_length = encrypted_length;
486 packet_.retransmittable_frames.push_back(QuicFrame(frame));
487 OnSerializedPacket();
488}
489
490bool QuicPacketCreator::HasPendingFrames() const {
491 return !queued_frames_.empty();
492}
493
494bool QuicPacketCreator::HasPendingRetransmittableFrames() const {
495 return !packet_.retransmittable_frames.empty();
496}
497
498bool QuicPacketCreator::HasPendingStreamFramesOfStream(QuicStreamId id) const {
499 for (const auto& frame : packet_.retransmittable_frames) {
500 if (frame.type == STREAM_FRAME && frame.stream_frame.stream_id == id) {
501 return true;
502 }
503 }
504 return false;
505}
506
507size_t QuicPacketCreator::ExpansionOnNewFrame() const {
508 // If the last frame in the packet is a message frame, then it will expand to
509 // include the varint message length when a new frame is added.
510 const bool has_trailing_message_frame =
511 !queued_frames_.empty() && queued_frames_.back().type == MESSAGE_FRAME;
512 if (has_trailing_message_frame) {
513 return QuicDataWriter::GetVarInt62Len(
514 queued_frames_.back().message_frame->message_length);
515 }
516 // If the last frame in the packet is a stream frame, then it will expand to
517 // include the stream_length field when a new frame is added.
518 const bool has_trailing_stream_frame =
519 !queued_frames_.empty() && queued_frames_.back().type == STREAM_FRAME;
520 if (!has_trailing_stream_frame) {
521 return 0;
522 }
523 if (framer_->transport_version() == QUIC_VERSION_99) {
524 return QuicDataWriter::GetVarInt62Len(
525 queued_frames_.back().stream_frame.data_length);
526 }
527 return kQuicStreamPayloadLengthSize;
528}
529
530size_t QuicPacketCreator::BytesFree() {
531 DCHECK_GE(max_plaintext_size_, PacketSize());
532 return max_plaintext_size_ -
533 std::min(max_plaintext_size_, PacketSize() + ExpansionOnNewFrame());
534}
535
536size_t QuicPacketCreator::PacketSize() {
537 if (!queued_frames_.empty()) {
538 return packet_size_;
539 }
540 packet_size_ = GetPacketHeaderSize(
541 framer_->transport_version(), GetDestinationConnectionIdLength(),
542 GetSourceConnectionIdLength(), IncludeVersionInHeader(),
543 IncludeNonceInPublicHeader(), GetPacketNumberLength(),
544 GetRetryTokenLengthLength(), GetRetryToken().length(), GetLengthLength());
545 return packet_size_;
546}
547
548bool QuicPacketCreator::AddSavedFrame(const QuicFrame& frame,
549 TransmissionType transmission_type) {
550 return AddFrame(frame, /*save_retransmittable_frames=*/true,
551 transmission_type);
552}
553
554bool QuicPacketCreator::AddPaddedSavedFrame(
555 const QuicFrame& frame,
556 TransmissionType transmission_type) {
557 if (AddFrame(frame, /*save_retransmittable_frames=*/true,
558 transmission_type)) {
559 needs_full_padding_ = true;
560 return true;
561 }
562 return false;
563}
564
565void QuicPacketCreator::SerializePacket(char* encrypted_buffer,
566 size_t encrypted_buffer_len) {
567 DCHECK_LT(0u, encrypted_buffer_len);
568 QUIC_BUG_IF(queued_frames_.empty() && pending_padding_bytes_ == 0)
569 << "Attempt to serialize empty packet";
570 QuicPacketHeader header;
571 // FillPacketHeader increments packet_number_.
572 FillPacketHeader(&header);
573
574 MaybeAddPadding();
575
576 DCHECK_GE(max_plaintext_size_, packet_size_);
577 // Use the packet_size_ instead of the buffer size to ensure smaller
578 // packet sizes are properly used.
579 size_t length =
580 framer_->BuildDataPacket(header, queued_frames_, encrypted_buffer,
581 packet_size_, packet_.encryption_level);
582 if (length == 0) {
583 QUIC_BUG << "Failed to serialize " << queued_frames_.size() << " frames.";
584 return;
585 }
586
587 // ACK Frames will be truncated due to length only if they're the only frame
588 // in the packet, and if packet_size_ was set to max_plaintext_size_. If
589 // truncation due to length occurred, then GetSerializedFrameLength will have
590 // returned all bytes free.
591 bool possibly_truncated_by_length = packet_size_ == max_plaintext_size_ &&
592 queued_frames_.size() == 1 &&
593 queued_frames_.back().type == ACK_FRAME;
594 // Because of possible truncation, we can't be confident that our
595 // packet size calculation worked correctly.
596 if (!possibly_truncated_by_length) {
597 DCHECK_EQ(packet_size_, length);
598 }
599 const size_t encrypted_length = framer_->EncryptInPlace(
600 packet_.encryption_level, packet_.packet_number,
601 GetStartOfEncryptedData(framer_->transport_version(), header), length,
602 encrypted_buffer_len, encrypted_buffer);
603 if (encrypted_length == 0) {
604 QUIC_BUG << "Failed to encrypt packet number " << packet_.packet_number;
605 return;
606 }
607
608 packet_size_ = 0;
609 queued_frames_.clear();
610 packet_.encrypted_buffer = encrypted_buffer;
611 packet_.encrypted_length = encrypted_length;
612}
613
614std::unique_ptr<QuicEncryptedPacket>
615QuicPacketCreator::SerializeVersionNegotiationPacket(
616 bool ietf_quic,
617 const ParsedQuicVersionVector& supported_versions) {
618 DCHECK_EQ(Perspective::IS_SERVER, framer_->perspective());
619 std::unique_ptr<QuicEncryptedPacket> encrypted =
620 QuicFramer::BuildVersionNegotiationPacket(connection_id_, ietf_quic,
621 supported_versions);
622 DCHECK(encrypted);
623 DCHECK_GE(max_packet_length_, encrypted->length());
624 return encrypted;
625}
626
627OwningSerializedPacketPointer
628QuicPacketCreator::SerializeConnectivityProbingPacket() {
629 QUIC_BUG_IF(framer_->transport_version() == QUIC_VERSION_99)
630 << "Must not be version 99 to serialize padded ping connectivity probe";
631 QuicPacketHeader header;
632 // FillPacketHeader increments packet_number_.
633 FillPacketHeader(&header);
634
dschinazi66dea072019-04-09 11:41:06 -0700635 std::unique_ptr<char[]> buffer(new char[kMaxOutgoingPacketSize]);
QUICHE teama6ef0a62019-03-07 20:34:33 -0500636 size_t length = framer_->BuildConnectivityProbingPacket(
637 header, buffer.get(), max_plaintext_size_, packet_.encryption_level);
638 DCHECK(length);
639
640 const size_t encrypted_length = framer_->EncryptInPlace(
641 packet_.encryption_level, packet_.packet_number,
642 GetStartOfEncryptedData(framer_->transport_version(), header), length,
dschinazi66dea072019-04-09 11:41:06 -0700643 kMaxOutgoingPacketSize, buffer.get());
QUICHE teama6ef0a62019-03-07 20:34:33 -0500644 DCHECK(encrypted_length);
645
646 OwningSerializedPacketPointer serialize_packet(new SerializedPacket(
647 header.packet_number, header.packet_number_length, buffer.release(),
648 encrypted_length, /*has_ack=*/false, /*has_stop_waiting=*/false));
649
650 serialize_packet->encryption_level = packet_.encryption_level;
651 serialize_packet->transmission_type = NOT_RETRANSMISSION;
652
653 return serialize_packet;
654}
655
656OwningSerializedPacketPointer
657QuicPacketCreator::SerializePathChallengeConnectivityProbingPacket(
658 QuicPathFrameBuffer* payload) {
659 QUIC_BUG_IF(framer_->transport_version() != QUIC_VERSION_99)
660 << "Must be version 99 to serialize path challenge connectivity probe, "
661 "is version "
662 << framer_->transport_version();
663 QuicPacketHeader header;
664 // FillPacketHeader increments packet_number_.
665 FillPacketHeader(&header);
666
dschinazi66dea072019-04-09 11:41:06 -0700667 std::unique_ptr<char[]> buffer(new char[kMaxOutgoingPacketSize]);
QUICHE teama6ef0a62019-03-07 20:34:33 -0500668 size_t length = framer_->BuildPaddedPathChallengePacket(
669 header, buffer.get(), max_plaintext_size_, payload, random_,
670 packet_.encryption_level);
671 DCHECK(length);
672
673 const size_t encrypted_length = framer_->EncryptInPlace(
674 packet_.encryption_level, packet_.packet_number,
675 GetStartOfEncryptedData(framer_->transport_version(), header), length,
dschinazi66dea072019-04-09 11:41:06 -0700676 kMaxOutgoingPacketSize, buffer.get());
QUICHE teama6ef0a62019-03-07 20:34:33 -0500677 DCHECK(encrypted_length);
678
679 OwningSerializedPacketPointer serialize_packet(new SerializedPacket(
680 header.packet_number, header.packet_number_length, buffer.release(),
681 encrypted_length, /*has_ack=*/false, /*has_stop_waiting=*/false));
682
683 serialize_packet->encryption_level = packet_.encryption_level;
684 serialize_packet->transmission_type = NOT_RETRANSMISSION;
685
686 return serialize_packet;
687}
688
689OwningSerializedPacketPointer
690QuicPacketCreator::SerializePathResponseConnectivityProbingPacket(
691 const QuicDeque<QuicPathFrameBuffer>& payloads,
692 const bool is_padded) {
693 QUIC_BUG_IF(framer_->transport_version() != QUIC_VERSION_99)
694 << "Must be version 99 to serialize path response connectivity probe, is "
695 "version "
696 << framer_->transport_version();
697 QuicPacketHeader header;
698 // FillPacketHeader increments packet_number_.
699 FillPacketHeader(&header);
700
dschinazi66dea072019-04-09 11:41:06 -0700701 std::unique_ptr<char[]> buffer(new char[kMaxOutgoingPacketSize]);
QUICHE teama6ef0a62019-03-07 20:34:33 -0500702 size_t length = framer_->BuildPathResponsePacket(
703 header, buffer.get(), max_plaintext_size_, payloads, is_padded,
704 packet_.encryption_level);
705 DCHECK(length);
706
707 const size_t encrypted_length = framer_->EncryptInPlace(
708 packet_.encryption_level, packet_.packet_number,
709 GetStartOfEncryptedData(framer_->transport_version(), header), length,
dschinazi66dea072019-04-09 11:41:06 -0700710 kMaxOutgoingPacketSize, buffer.get());
QUICHE teama6ef0a62019-03-07 20:34:33 -0500711 DCHECK(encrypted_length);
712
713 OwningSerializedPacketPointer serialize_packet(new SerializedPacket(
714 header.packet_number, header.packet_number_length, buffer.release(),
715 encrypted_length, /*has_ack=*/false, /*has_stop_waiting=*/false));
716
717 serialize_packet->encryption_level = packet_.encryption_level;
718 serialize_packet->transmission_type = NOT_RETRANSMISSION;
719
720 return serialize_packet;
721}
722
723// TODO(b/74062209): Make this a public method of framer?
724SerializedPacket QuicPacketCreator::NoPacket() {
725 return SerializedPacket(QuicPacketNumber(), PACKET_1BYTE_PACKET_NUMBER,
726 nullptr, 0, false, false);
727}
728
729QuicConnectionIdIncluded QuicPacketCreator::GetDestinationConnectionIdIncluded()
730 const {
731 if (framer_->transport_version() > QUIC_VERSION_43) {
732 // Packets sent by client always include destination connection ID, and
733 // those sent by the server do not include destination connection ID.
734 return framer_->perspective() == Perspective::IS_CLIENT
735 ? CONNECTION_ID_PRESENT
736 : CONNECTION_ID_ABSENT;
737 }
738 return connection_id_included_;
739}
740
741QuicConnectionIdIncluded QuicPacketCreator::GetSourceConnectionIdIncluded()
742 const {
743 // Long header packets sent by server include source connection ID.
744 if (HasIetfLongHeader() && framer_->perspective() == Perspective::IS_SERVER) {
745 return CONNECTION_ID_PRESENT;
746 }
747 return CONNECTION_ID_ABSENT;
748}
749
750QuicConnectionIdLength QuicPacketCreator::GetDestinationConnectionIdLength()
751 const {
752 DCHECK(QuicUtils::IsConnectionIdValidForVersion(connection_id_,
753 transport_version()));
754 return GetDestinationConnectionIdIncluded() == CONNECTION_ID_PRESENT
755 ? static_cast<QuicConnectionIdLength>(connection_id_.length())
756 : PACKET_0BYTE_CONNECTION_ID;
757}
758
759QuicConnectionIdLength QuicPacketCreator::GetSourceConnectionIdLength() const {
760 DCHECK(QuicUtils::IsConnectionIdValidForVersion(connection_id_,
761 transport_version()));
762 return GetSourceConnectionIdIncluded() == CONNECTION_ID_PRESENT
763 ? static_cast<QuicConnectionIdLength>(connection_id_.length())
764 : PACKET_0BYTE_CONNECTION_ID;
765}
766
767QuicPacketNumberLength QuicPacketCreator::GetPacketNumberLength() const {
768 if (HasIetfLongHeader() && framer_->transport_version() != QUIC_VERSION_99) {
769 return PACKET_4BYTE_PACKET_NUMBER;
770 }
771 return packet_.packet_number_length;
772}
773
774QuicVariableLengthIntegerLength QuicPacketCreator::GetRetryTokenLengthLength()
775 const {
776 if (QuicVersionHasLongHeaderLengths(framer_->transport_version()) &&
777 HasIetfLongHeader() &&
778 EncryptionlevelToLongHeaderType(packet_.encryption_level) == INITIAL) {
779 return QuicDataWriter::GetVarInt62Len(GetRetryToken().length());
780 }
781 return VARIABLE_LENGTH_INTEGER_LENGTH_0;
782}
783
784QuicStringPiece QuicPacketCreator::GetRetryToken() const {
785 return retry_token_;
786}
787
788void QuicPacketCreator::SetRetryToken(QuicStringPiece retry_token) {
vasilvvc48c8712019-03-11 13:38:16 -0700789 retry_token_ = std::string(retry_token);
QUICHE teama6ef0a62019-03-07 20:34:33 -0500790}
791
792QuicVariableLengthIntegerLength QuicPacketCreator::GetLengthLength() const {
793 if (QuicVersionHasLongHeaderLengths(framer_->transport_version()) &&
794 HasIetfLongHeader()) {
795 QuicLongHeaderType long_header_type =
796 EncryptionlevelToLongHeaderType(packet_.encryption_level);
797 if (long_header_type == INITIAL || long_header_type == ZERO_RTT_PROTECTED ||
798 long_header_type == HANDSHAKE) {
799 return VARIABLE_LENGTH_INTEGER_LENGTH_2;
800 }
801 }
802 return VARIABLE_LENGTH_INTEGER_LENGTH_0;
803}
804
805void QuicPacketCreator::FillPacketHeader(QuicPacketHeader* header) {
806 header->destination_connection_id = connection_id_;
807 header->destination_connection_id_included =
808 GetDestinationConnectionIdIncluded();
809 header->source_connection_id = connection_id_;
810 header->source_connection_id_included = GetSourceConnectionIdIncluded();
811 header->reset_flag = false;
812 header->version_flag = IncludeVersionInHeader();
813 if (IncludeNonceInPublicHeader()) {
814 DCHECK_EQ(Perspective::IS_SERVER, framer_->perspective());
815 header->nonce = &diversification_nonce_;
816 } else {
817 header->nonce = nullptr;
818 }
819 if (!packet_.packet_number.IsInitialized()) {
820 packet_.packet_number = framer_->first_sending_packet_number();
821 } else {
822 ++packet_.packet_number;
823 }
824 header->packet_number = packet_.packet_number;
825 header->packet_number_length = GetPacketNumberLength();
826 header->retry_token_length_length = GetRetryTokenLengthLength();
827 header->retry_token = GetRetryToken();
828 header->length_length = GetLengthLength();
829 header->remaining_packet_length = 0;
830 if (!HasIetfLongHeader()) {
831 return;
832 }
833 header->long_packet_type =
834 EncryptionlevelToLongHeaderType(packet_.encryption_level);
835}
836
837bool QuicPacketCreator::AddFrame(const QuicFrame& frame,
838 bool save_retransmittable_frames,
839 TransmissionType transmission_type) {
840 QUIC_DVLOG(1) << ENDPOINT << "Adding frame with transmission type "
841 << transmission_type << ": " << frame;
842 if (frame.type == STREAM_FRAME &&
843 frame.stream_frame.stream_id !=
844 QuicUtils::GetCryptoStreamId(framer_->transport_version()) &&
fayang49523232019-05-03 06:28:22 -0700845 (packet_.encryption_level == ENCRYPTION_INITIAL ||
846 packet_.encryption_level == ENCRYPTION_HANDSHAKE)) {
847 const std::string error_details = QuicStrCat(
848 "Cannot send stream data with level: ",
849 QuicUtils::EncryptionLevelToString(packet_.encryption_level));
QUICHE teama6ef0a62019-03-07 20:34:33 -0500850 QUIC_BUG << error_details;
851 delegate_->OnUnrecoverableError(
852 QUIC_ATTEMPT_TO_SEND_UNENCRYPTED_STREAM_DATA, error_details,
853 ConnectionCloseSource::FROM_SELF);
854 return false;
855 }
856 size_t frame_len = framer_->GetSerializedFrameLength(
857 frame, BytesFree(), queued_frames_.empty(),
858 /* last_frame_in_packet= */ true, GetPacketNumberLength());
859 if (frame_len == 0) {
860 // Current open packet is full.
861 Flush();
862 return false;
863 }
864 DCHECK_LT(0u, packet_size_);
865
866 packet_size_ += ExpansionOnNewFrame() + frame_len;
867
868 if (save_retransmittable_frames &&
869 QuicUtils::IsRetransmittableFrame(frame.type)) {
870 packet_.retransmittable_frames.push_back(frame);
871 queued_frames_.push_back(frame);
872 if (QuicUtils::IsHandshakeFrame(frame, framer_->transport_version())) {
873 packet_.has_crypto_handshake = IS_HANDSHAKE;
874 }
875 } else {
876 queued_frames_.push_back(frame);
877 }
878
879 if (frame.type == ACK_FRAME) {
880 packet_.has_ack = true;
881 packet_.largest_acked = LargestAcked(*frame.ack_frame);
882 }
883 if (frame.type == STOP_WAITING_FRAME) {
884 packet_.has_stop_waiting = true;
885 }
886 if (debug_delegate_ != nullptr) {
887 debug_delegate_->OnFrameAddedToPacket(frame);
888 }
889
890 // Packet transmission type is determined by the last added retransmittable
891 // frame.
wub98669f52019-04-18 10:49:18 -0700892 if (can_set_transmission_type() &&
QUICHE teama6ef0a62019-03-07 20:34:33 -0500893 QuicUtils::IsRetransmittableFrame(frame.type)) {
QUICHE teama6ef0a62019-03-07 20:34:33 -0500894 packet_.transmission_type = transmission_type;
895 }
896 return true;
897}
898
899void QuicPacketCreator::MaybeAddPadding() {
900 // The current packet should have no padding bytes because padding is only
901 // added when this method is called just before the packet is serialized.
902 DCHECK_EQ(0, packet_.num_padding_bytes);
903 if (BytesFree() == 0) {
904 // Don't pad full packets.
905 return;
906 }
907
908 if (packet_.transmission_type == PROBING_RETRANSMISSION) {
909 needs_full_padding_ = true;
910 }
911
912 if (!needs_full_padding_ && pending_padding_bytes_ == 0) {
913 // Do not need padding.
914 return;
915 }
916
917 if (needs_full_padding_) {
918 // Full padding does not consume pending padding bytes.
919 packet_.num_padding_bytes = -1;
920 } else {
921 packet_.num_padding_bytes =
922 std::min<int16_t>(pending_padding_bytes_, BytesFree());
923 pending_padding_bytes_ -= packet_.num_padding_bytes;
924 }
925
926 bool success =
927 AddFrame(QuicFrame(QuicPaddingFrame(packet_.num_padding_bytes)), false,
928 packet_.transmission_type);
929 DCHECK(success);
930}
931
932bool QuicPacketCreator::IncludeNonceInPublicHeader() const {
933 return have_diversification_nonce_ &&
934 packet_.encryption_level == ENCRYPTION_ZERO_RTT;
935}
936
937bool QuicPacketCreator::IncludeVersionInHeader() const {
938 if (framer_->transport_version() > QUIC_VERSION_43) {
939 return packet_.encryption_level < ENCRYPTION_FORWARD_SECURE;
940 }
941 return send_version_in_packet_;
942}
943
944void QuicPacketCreator::AddPendingPadding(QuicByteCount size) {
945 pending_padding_bytes_ += size;
946}
947
ianswette28f0222019-04-04 13:31:22 -0700948bool QuicPacketCreator::StreamFrameIsClientHello(
QUICHE teama6ef0a62019-03-07 20:34:33 -0500949 const QuicStreamFrame& frame) const {
950 if (framer_->perspective() == Perspective::IS_SERVER ||
951 frame.stream_id !=
ianswette28f0222019-04-04 13:31:22 -0700952 QuicUtils::GetCryptoStreamId(framer_->transport_version())) {
QUICHE teama6ef0a62019-03-07 20:34:33 -0500953 return false;
954 }
ianswette28f0222019-04-04 13:31:22 -0700955 // The ClientHello is always sent with INITIAL encryption.
956 return packet_.encryption_level == ENCRYPTION_INITIAL;
QUICHE teama6ef0a62019-03-07 20:34:33 -0500957}
958
959void QuicPacketCreator::SetConnectionIdIncluded(
960 QuicConnectionIdIncluded connection_id_included) {
961 DCHECK(connection_id_included == CONNECTION_ID_PRESENT ||
962 connection_id_included == CONNECTION_ID_ABSENT);
963 DCHECK(framer_->perspective() == Perspective::IS_SERVER ||
964 connection_id_included != CONNECTION_ID_ABSENT);
965 connection_id_included_ = connection_id_included;
966}
967
QUICHE teamc65d1d12019-03-19 20:58:04 -0700968void QuicPacketCreator::SetConnectionId(QuicConnectionId connection_id) {
969 connection_id_ = connection_id;
970}
971
QUICHE teama6ef0a62019-03-07 20:34:33 -0500972void QuicPacketCreator::SetTransmissionType(TransmissionType type) {
973 DCHECK(can_set_transmission_type_);
974
wub98669f52019-04-18 10:49:18 -0700975 if (!can_set_transmission_type()) {
QUICHE teama6ef0a62019-03-07 20:34:33 -0500976 QUIC_DVLOG_IF(1, type != packet_.transmission_type)
977 << ENDPOINT << "Setting Transmission type to "
978 << QuicUtils::TransmissionTypeToString(type);
979
980 packet_.transmission_type = type;
981 }
982}
983
ianswettb239f862019-04-05 09:15:06 -0700984QuicPacketLength QuicPacketCreator::GetCurrentLargestMessagePayload() const {
QUICHE teama6ef0a62019-03-07 20:34:33 -0500985 if (framer_->transport_version() <= QUIC_VERSION_44) {
986 return 0;
987 }
988 const size_t packet_header_size = GetPacketHeaderSize(
989 framer_->transport_version(), GetDestinationConnectionIdLength(),
990 GetSourceConnectionIdLength(), IncludeVersionInHeader(),
991 IncludeNonceInPublicHeader(), GetPacketNumberLength(),
ianswettb239f862019-04-05 09:15:06 -0700992 // No Retry token on packets containing application data.
993 VARIABLE_LENGTH_INTEGER_LENGTH_0, 0, GetLengthLength());
QUICHE teama6ef0a62019-03-07 20:34:33 -0500994 // This is the largest possible message payload when the length field is
995 // omitted.
996 return max_plaintext_size_ -
997 std::min(max_plaintext_size_, packet_header_size + kQuicFrameTypeSize);
998}
999
ianswettb239f862019-04-05 09:15:06 -07001000QuicPacketLength QuicPacketCreator::GetGuaranteedLargestMessagePayload() const {
1001 if (framer_->transport_version() <= QUIC_VERSION_44) {
1002 return 0;
1003 }
1004 // QUIC Crypto server packets may include a diversification nonce.
1005 const bool may_include_nonce =
1006 framer_->version().handshake_protocol == PROTOCOL_QUIC_CRYPTO &&
1007 framer_->perspective() == Perspective::IS_SERVER;
1008 // IETF QUIC long headers include a length on client 0RTT packets.
1009 QuicVariableLengthIntegerLength length_length =
1010 framer_->perspective() == Perspective::IS_CLIENT
1011 ? VARIABLE_LENGTH_INTEGER_LENGTH_2
1012 : VARIABLE_LENGTH_INTEGER_LENGTH_0;
1013 const size_t packet_header_size = GetPacketHeaderSize(
1014 framer_->transport_version(), GetDestinationConnectionIdLength(),
1015 // Assume CID lengths don't change, but version may be present.
1016 GetSourceConnectionIdLength(), kIncludeVersion, may_include_nonce,
1017 PACKET_4BYTE_PACKET_NUMBER,
1018 // No Retry token on packets containing application data.
1019 VARIABLE_LENGTH_INTEGER_LENGTH_0, 0, length_length);
1020 // This is the largest possible message payload when the length field is
1021 // omitted.
1022 const QuicPacketLength largest_payload =
1023 max_plaintext_size_ -
1024 std::min(max_plaintext_size_, packet_header_size + kQuicFrameTypeSize);
1025 // This must always be less than or equal to GetCurrentLargestMessagePayload.
1026 DCHECK_LE(largest_payload, GetCurrentLargestMessagePayload());
1027 return largest_payload;
1028}
1029
QUICHE teama6ef0a62019-03-07 20:34:33 -05001030bool QuicPacketCreator::HasIetfLongHeader() const {
1031 return framer_->transport_version() > QUIC_VERSION_43 &&
1032 packet_.encryption_level < ENCRYPTION_FORWARD_SECURE;
1033}
1034
1035#undef ENDPOINT // undef for jumbo builds
1036} // namespace quic