1 // 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_packets.h"
6
7 #include <utility>
8
9 #include "absl/strings/escaping.h"
10 #include "absl/strings/string_view.h"
11 #include "net/third_party/quiche/src/quic/core/quic_connection_id.h"
12 #include "net/third_party/quiche/src/quic/core/quic_types.h"
13 #include "net/third_party/quiche/src/quic/core/quic_utils.h"
14 #include "net/third_party/quiche/src/quic/core/quic_versions.h"
15 #include "net/third_party/quiche/src/quic/platform/api/quic_flag_utils.h"
16 #include "net/third_party/quiche/src/quic/platform/api/quic_flags.h"
17 #include "net/third_party/quiche/src/quic/platform/api/quic_string_utils.h"
18 #include "net/third_party/quiche/src/common/platform/api/quiche_str_cat.h"
19 #include "net/third_party/quiche/src/common/platform/api/quiche_text_utils.h"
20
21 namespace quic {
22
GetServerConnectionIdAsRecipient(const QuicPacketHeader & header,Perspective perspective)23 QuicConnectionId GetServerConnectionIdAsRecipient(
24 const QuicPacketHeader& header,
25 Perspective perspective) {
26 if (perspective == Perspective::IS_SERVER) {
27 return header.destination_connection_id;
28 }
29 return header.source_connection_id;
30 }
31
GetClientConnectionIdAsRecipient(const QuicPacketHeader & header,Perspective perspective)32 QuicConnectionId GetClientConnectionIdAsRecipient(
33 const QuicPacketHeader& header,
34 Perspective perspective) {
35 if (perspective == Perspective::IS_CLIENT) {
36 return header.destination_connection_id;
37 }
38 return header.source_connection_id;
39 }
40
GetServerConnectionIdAsSender(const QuicPacketHeader & header,Perspective perspective)41 QuicConnectionId GetServerConnectionIdAsSender(const QuicPacketHeader& header,
42 Perspective perspective) {
43 if (perspective == Perspective::IS_CLIENT) {
44 return header.destination_connection_id;
45 }
46 return header.source_connection_id;
47 }
48
GetServerConnectionIdIncludedAsSender(const QuicPacketHeader & header,Perspective perspective)49 QuicConnectionIdIncluded GetServerConnectionIdIncludedAsSender(
50 const QuicPacketHeader& header,
51 Perspective perspective) {
52 if (perspective == Perspective::IS_CLIENT) {
53 return header.destination_connection_id_included;
54 }
55 return header.source_connection_id_included;
56 }
57
GetClientConnectionIdAsSender(const QuicPacketHeader & header,Perspective perspective)58 QuicConnectionId GetClientConnectionIdAsSender(const QuicPacketHeader& header,
59 Perspective perspective) {
60 if (perspective == Perspective::IS_CLIENT) {
61 return header.source_connection_id;
62 }
63 return header.destination_connection_id;
64 }
65
GetClientConnectionIdIncludedAsSender(const QuicPacketHeader & header,Perspective perspective)66 QuicConnectionIdIncluded GetClientConnectionIdIncludedAsSender(
67 const QuicPacketHeader& header,
68 Perspective perspective) {
69 if (perspective == Perspective::IS_CLIENT) {
70 return header.source_connection_id_included;
71 }
72 return header.destination_connection_id_included;
73 }
74
GetIncludedConnectionIdLength(QuicConnectionId connection_id,QuicConnectionIdIncluded connection_id_included)75 QuicConnectionIdLength GetIncludedConnectionIdLength(
76 QuicConnectionId connection_id,
77 QuicConnectionIdIncluded connection_id_included) {
78 DCHECK(connection_id_included == CONNECTION_ID_PRESENT ||
79 connection_id_included == CONNECTION_ID_ABSENT);
80 return connection_id_included == CONNECTION_ID_PRESENT
81 ? static_cast<QuicConnectionIdLength>(connection_id.length())
82 : PACKET_0BYTE_CONNECTION_ID;
83 }
84
GetIncludedDestinationConnectionIdLength(const QuicPacketHeader & header)85 QuicConnectionIdLength GetIncludedDestinationConnectionIdLength(
86 const QuicPacketHeader& header) {
87 return GetIncludedConnectionIdLength(
88 header.destination_connection_id,
89 header.destination_connection_id_included);
90 }
91
GetIncludedSourceConnectionIdLength(const QuicPacketHeader & header)92 QuicConnectionIdLength GetIncludedSourceConnectionIdLength(
93 const QuicPacketHeader& header) {
94 return GetIncludedConnectionIdLength(header.source_connection_id,
95 header.source_connection_id_included);
96 }
97
GetPacketHeaderSize(QuicTransportVersion version,const QuicPacketHeader & header)98 size_t GetPacketHeaderSize(QuicTransportVersion version,
99 const QuicPacketHeader& header) {
100 return GetPacketHeaderSize(
101 version, GetIncludedDestinationConnectionIdLength(header),
102 GetIncludedSourceConnectionIdLength(header), header.version_flag,
103 header.nonce != nullptr, header.packet_number_length,
104 header.retry_token_length_length, header.retry_token.length(),
105 header.length_length);
106 }
107
GetPacketHeaderSize(QuicTransportVersion version,QuicConnectionIdLength destination_connection_id_length,QuicConnectionIdLength source_connection_id_length,bool include_version,bool include_diversification_nonce,QuicPacketNumberLength packet_number_length,QuicVariableLengthIntegerLength retry_token_length_length,QuicByteCount retry_token_length,QuicVariableLengthIntegerLength length_length)108 size_t GetPacketHeaderSize(
109 QuicTransportVersion version,
110 QuicConnectionIdLength destination_connection_id_length,
111 QuicConnectionIdLength source_connection_id_length,
112 bool include_version,
113 bool include_diversification_nonce,
114 QuicPacketNumberLength packet_number_length,
115 QuicVariableLengthIntegerLength retry_token_length_length,
116 QuicByteCount retry_token_length,
117 QuicVariableLengthIntegerLength length_length) {
118 if (VersionHasIetfInvariantHeader(version)) {
119 if (include_version) {
120 // Long header.
121 size_t size = kPacketHeaderTypeSize + kConnectionIdLengthSize +
122 destination_connection_id_length +
123 source_connection_id_length + packet_number_length +
124 kQuicVersionSize;
125 if (include_diversification_nonce) {
126 size += kDiversificationNonceSize;
127 }
128 if (VersionHasLengthPrefixedConnectionIds(version)) {
129 size += kConnectionIdLengthSize;
130 }
131 DCHECK(QuicVersionHasLongHeaderLengths(version) ||
132 retry_token_length_length + retry_token_length + length_length ==
133 0);
134 if (QuicVersionHasLongHeaderLengths(version)) {
135 size += retry_token_length_length + retry_token_length + length_length;
136 }
137 return size;
138 }
139 // Short header.
140 return kPacketHeaderTypeSize + destination_connection_id_length +
141 packet_number_length;
142 }
143 // Google QUIC versions <= 43 can only carry one connection ID.
144 DCHECK(destination_connection_id_length == 0 ||
145 source_connection_id_length == 0);
146 return kPublicFlagsSize + destination_connection_id_length +
147 source_connection_id_length +
148 (include_version ? kQuicVersionSize : 0) + packet_number_length +
149 (include_diversification_nonce ? kDiversificationNonceSize : 0);
150 }
151
GetStartOfEncryptedData(QuicTransportVersion version,const QuicPacketHeader & header)152 size_t GetStartOfEncryptedData(QuicTransportVersion version,
153 const QuicPacketHeader& header) {
154 return GetPacketHeaderSize(version, header);
155 }
156
GetStartOfEncryptedData(QuicTransportVersion version,QuicConnectionIdLength destination_connection_id_length,QuicConnectionIdLength source_connection_id_length,bool include_version,bool include_diversification_nonce,QuicPacketNumberLength packet_number_length,QuicVariableLengthIntegerLength retry_token_length_length,QuicByteCount retry_token_length,QuicVariableLengthIntegerLength length_length)157 size_t GetStartOfEncryptedData(
158 QuicTransportVersion version,
159 QuicConnectionIdLength destination_connection_id_length,
160 QuicConnectionIdLength source_connection_id_length,
161 bool include_version,
162 bool include_diversification_nonce,
163 QuicPacketNumberLength packet_number_length,
164 QuicVariableLengthIntegerLength retry_token_length_length,
165 QuicByteCount retry_token_length,
166 QuicVariableLengthIntegerLength length_length) {
167 // Encryption starts before private flags.
168 return GetPacketHeaderSize(
169 version, destination_connection_id_length, source_connection_id_length,
170 include_version, include_diversification_nonce, packet_number_length,
171 retry_token_length_length, retry_token_length, length_length);
172 }
173
QuicPacketHeader()174 QuicPacketHeader::QuicPacketHeader()
175 : destination_connection_id(EmptyQuicConnectionId()),
176 destination_connection_id_included(CONNECTION_ID_PRESENT),
177 source_connection_id(EmptyQuicConnectionId()),
178 source_connection_id_included(CONNECTION_ID_ABSENT),
179 reset_flag(false),
180 version_flag(false),
181 has_possible_stateless_reset_token(false),
182 packet_number_length(PACKET_4BYTE_PACKET_NUMBER),
183 version(UnsupportedQuicVersion()),
184 nonce(nullptr),
185 form(GOOGLE_QUIC_PACKET),
186 long_packet_type(INITIAL),
187 possible_stateless_reset_token(0),
188 retry_token_length_length(VARIABLE_LENGTH_INTEGER_LENGTH_0),
189 retry_token(absl::string_view()),
190 length_length(VARIABLE_LENGTH_INTEGER_LENGTH_0),
191 remaining_packet_length(0) {}
192
193 QuicPacketHeader::QuicPacketHeader(const QuicPacketHeader& other) = default;
194
~QuicPacketHeader()195 QuicPacketHeader::~QuicPacketHeader() {}
196
197 QuicPacketHeader& QuicPacketHeader::operator=(const QuicPacketHeader& other) =
198 default;
199
QuicPublicResetPacket()200 QuicPublicResetPacket::QuicPublicResetPacket()
201 : connection_id(EmptyQuicConnectionId()), nonce_proof(0) {}
202
QuicPublicResetPacket(QuicConnectionId connection_id)203 QuicPublicResetPacket::QuicPublicResetPacket(QuicConnectionId connection_id)
204 : connection_id(connection_id), nonce_proof(0) {}
205
QuicVersionNegotiationPacket()206 QuicVersionNegotiationPacket::QuicVersionNegotiationPacket()
207 : connection_id(EmptyQuicConnectionId()) {}
208
QuicVersionNegotiationPacket(QuicConnectionId connection_id)209 QuicVersionNegotiationPacket::QuicVersionNegotiationPacket(
210 QuicConnectionId connection_id)
211 : connection_id(connection_id) {}
212
213 QuicVersionNegotiationPacket::QuicVersionNegotiationPacket(
214 const QuicVersionNegotiationPacket& other) = default;
215
~QuicVersionNegotiationPacket()216 QuicVersionNegotiationPacket::~QuicVersionNegotiationPacket() {}
217
QuicIetfStatelessResetPacket()218 QuicIetfStatelessResetPacket::QuicIetfStatelessResetPacket()
219 : stateless_reset_token(0) {}
220
QuicIetfStatelessResetPacket(const QuicPacketHeader & header,QuicUint128 token)221 QuicIetfStatelessResetPacket::QuicIetfStatelessResetPacket(
222 const QuicPacketHeader& header,
223 QuicUint128 token)
224 : header(header), stateless_reset_token(token) {}
225
226 QuicIetfStatelessResetPacket::QuicIetfStatelessResetPacket(
227 const QuicIetfStatelessResetPacket& other) = default;
228
~QuicIetfStatelessResetPacket()229 QuicIetfStatelessResetPacket::~QuicIetfStatelessResetPacket() {}
230
operator <<(std::ostream & os,const QuicPacketHeader & header)231 std::ostream& operator<<(std::ostream& os, const QuicPacketHeader& header) {
232 os << "{ destination_connection_id: " << header.destination_connection_id
233 << " ("
234 << (header.destination_connection_id_included == CONNECTION_ID_PRESENT
235 ? "present"
236 : "absent")
237 << "), source_connection_id: " << header.source_connection_id << " ("
238 << (header.source_connection_id_included == CONNECTION_ID_PRESENT
239 ? "present"
240 : "absent")
241 << "), packet_number_length: "
242 << static_cast<int>(header.packet_number_length)
243 << ", reset_flag: " << header.reset_flag
244 << ", version_flag: " << header.version_flag;
245 if (header.version_flag) {
246 os << ", version: " << ParsedQuicVersionToString(header.version);
247 if (header.long_packet_type != INVALID_PACKET_TYPE) {
248 os << ", long_packet_type: "
249 << QuicUtils::QuicLongHeaderTypetoString(header.long_packet_type);
250 }
251 if (header.retry_token_length_length != VARIABLE_LENGTH_INTEGER_LENGTH_0) {
252 os << ", retry_token_length_length: "
253 << static_cast<int>(header.retry_token_length_length);
254 }
255 if (header.retry_token.length() != 0) {
256 os << ", retry_token_length: " << header.retry_token.length();
257 }
258 if (header.length_length != VARIABLE_LENGTH_INTEGER_LENGTH_0) {
259 os << ", length_length: " << static_cast<int>(header.length_length);
260 }
261 if (header.remaining_packet_length != 0) {
262 os << ", remaining_packet_length: " << header.remaining_packet_length;
263 }
264 }
265 if (header.nonce != nullptr) {
266 os << ", diversification_nonce: "
267 << absl::BytesToHexString(
268 absl::string_view(header.nonce->data(), header.nonce->size()));
269 }
270 os << ", packet_number: " << header.packet_number << " }\n";
271 return os;
272 }
273
QuicData(const char * buffer,size_t length)274 QuicData::QuicData(const char* buffer, size_t length)
275 : buffer_(buffer), length_(length), owns_buffer_(false) {}
276
QuicData(const char * buffer,size_t length,bool owns_buffer)277 QuicData::QuicData(const char* buffer, size_t length, bool owns_buffer)
278 : buffer_(buffer), length_(length), owns_buffer_(owns_buffer) {}
279
QuicData(absl::string_view packet_data)280 QuicData::QuicData(absl::string_view packet_data)
281 : buffer_(packet_data.data()),
282 length_(packet_data.length()),
283 owns_buffer_(false) {}
284
~QuicData()285 QuicData::~QuicData() {
286 if (owns_buffer_) {
287 delete[] const_cast<char*>(buffer_);
288 }
289 }
290
QuicPacket(char * buffer,size_t length,bool owns_buffer,QuicConnectionIdLength destination_connection_id_length,QuicConnectionIdLength source_connection_id_length,bool includes_version,bool includes_diversification_nonce,QuicPacketNumberLength packet_number_length,QuicVariableLengthIntegerLength retry_token_length_length,QuicByteCount retry_token_length,QuicVariableLengthIntegerLength length_length)291 QuicPacket::QuicPacket(
292 char* buffer,
293 size_t length,
294 bool owns_buffer,
295 QuicConnectionIdLength destination_connection_id_length,
296 QuicConnectionIdLength source_connection_id_length,
297 bool includes_version,
298 bool includes_diversification_nonce,
299 QuicPacketNumberLength packet_number_length,
300 QuicVariableLengthIntegerLength retry_token_length_length,
301 QuicByteCount retry_token_length,
302 QuicVariableLengthIntegerLength length_length)
303 : QuicData(buffer, length, owns_buffer),
304 buffer_(buffer),
305 destination_connection_id_length_(destination_connection_id_length),
306 source_connection_id_length_(source_connection_id_length),
307 includes_version_(includes_version),
308 includes_diversification_nonce_(includes_diversification_nonce),
309 packet_number_length_(packet_number_length),
310 retry_token_length_length_(retry_token_length_length),
311 retry_token_length_(retry_token_length),
312 length_length_(length_length) {}
313
QuicPacket(QuicTransportVersion,char * buffer,size_t length,bool owns_buffer,const QuicPacketHeader & header)314 QuicPacket::QuicPacket(QuicTransportVersion /*version*/,
315 char* buffer,
316 size_t length,
317 bool owns_buffer,
318 const QuicPacketHeader& header)
319 : QuicPacket(buffer,
320 length,
321 owns_buffer,
322 GetIncludedDestinationConnectionIdLength(header),
323 GetIncludedSourceConnectionIdLength(header),
324 header.version_flag,
325 header.nonce != nullptr,
326 header.packet_number_length,
327 header.retry_token_length_length,
328 header.retry_token.length(),
329 header.length_length) {}
330
QuicEncryptedPacket(const char * buffer,size_t length)331 QuicEncryptedPacket::QuicEncryptedPacket(const char* buffer, size_t length)
332 : QuicData(buffer, length) {}
333
QuicEncryptedPacket(const char * buffer,size_t length,bool owns_buffer)334 QuicEncryptedPacket::QuicEncryptedPacket(const char* buffer,
335 size_t length,
336 bool owns_buffer)
337 : QuicData(buffer, length, owns_buffer) {}
338
QuicEncryptedPacket(absl::string_view data)339 QuicEncryptedPacket::QuicEncryptedPacket(absl::string_view data)
340 : QuicData(data) {}
341
Clone() const342 std::unique_ptr<QuicEncryptedPacket> QuicEncryptedPacket::Clone() const {
343 char* buffer = new char[this->length()];
344 memcpy(buffer, this->data(), this->length());
345 return std::make_unique<QuicEncryptedPacket>(buffer, this->length(), true);
346 }
347
operator <<(std::ostream & os,const QuicEncryptedPacket & s)348 std::ostream& operator<<(std::ostream& os, const QuicEncryptedPacket& s) {
349 os << s.length() << "-byte data";
350 return os;
351 }
352
QuicReceivedPacket(const char * buffer,size_t length,QuicTime receipt_time)353 QuicReceivedPacket::QuicReceivedPacket(const char* buffer,
354 size_t length,
355 QuicTime receipt_time)
356 : QuicReceivedPacket(buffer,
357 length,
358 receipt_time,
359 false /* owns_buffer */) {}
360
QuicReceivedPacket(const char * buffer,size_t length,QuicTime receipt_time,bool owns_buffer)361 QuicReceivedPacket::QuicReceivedPacket(const char* buffer,
362 size_t length,
363 QuicTime receipt_time,
364 bool owns_buffer)
365 : QuicReceivedPacket(buffer,
366 length,
367 receipt_time,
368 owns_buffer,
369 0 /* ttl */,
370 true /* ttl_valid */) {}
371
QuicReceivedPacket(const char * buffer,size_t length,QuicTime receipt_time,bool owns_buffer,int ttl,bool ttl_valid)372 QuicReceivedPacket::QuicReceivedPacket(const char* buffer,
373 size_t length,
374 QuicTime receipt_time,
375 bool owns_buffer,
376 int ttl,
377 bool ttl_valid)
378 : quic::QuicReceivedPacket(buffer,
379 length,
380 receipt_time,
381 owns_buffer,
382 ttl,
383 ttl_valid,
384 nullptr /* packet_headers */,
385 0 /* headers_length */,
386 false /* owns_header_buffer */) {}
387
QuicReceivedPacket(const char * buffer,size_t length,QuicTime receipt_time,bool owns_buffer,int ttl,bool ttl_valid,char * packet_headers,size_t headers_length,bool owns_header_buffer)388 QuicReceivedPacket::QuicReceivedPacket(const char* buffer,
389 size_t length,
390 QuicTime receipt_time,
391 bool owns_buffer,
392 int ttl,
393 bool ttl_valid,
394 char* packet_headers,
395 size_t headers_length,
396 bool owns_header_buffer)
397 : QuicEncryptedPacket(buffer, length, owns_buffer),
398 receipt_time_(receipt_time),
399 ttl_(ttl_valid ? ttl : -1),
400 packet_headers_(packet_headers),
401 headers_length_(headers_length),
402 owns_header_buffer_(owns_header_buffer) {}
403
~QuicReceivedPacket()404 QuicReceivedPacket::~QuicReceivedPacket() {
405 if (owns_header_buffer_) {
406 delete[] static_cast<char*>(packet_headers_);
407 }
408 }
409
Clone() const410 std::unique_ptr<QuicReceivedPacket> QuicReceivedPacket::Clone() const {
411 char* buffer = new char[this->length()];
412 memcpy(buffer, this->data(), this->length());
413 if (this->packet_headers()) {
414 char* headers_buffer = new char[this->headers_length()];
415 memcpy(headers_buffer, this->packet_headers(), this->headers_length());
416 return std::make_unique<QuicReceivedPacket>(
417 buffer, this->length(), receipt_time(), true, ttl(), ttl() >= 0,
418 headers_buffer, this->headers_length(), true);
419 }
420
421 return std::make_unique<QuicReceivedPacket>(
422 buffer, this->length(), receipt_time(), true, ttl(), ttl() >= 0);
423 }
424
operator <<(std::ostream & os,const QuicReceivedPacket & s)425 std::ostream& operator<<(std::ostream& os, const QuicReceivedPacket& s) {
426 os << s.length() << "-byte data";
427 return os;
428 }
429
AssociatedData(QuicTransportVersion version) const430 absl::string_view QuicPacket::AssociatedData(
431 QuicTransportVersion version) const {
432 return absl::string_view(
433 data(),
434 GetStartOfEncryptedData(version, destination_connection_id_length_,
435 source_connection_id_length_, includes_version_,
436 includes_diversification_nonce_,
437 packet_number_length_, retry_token_length_length_,
438 retry_token_length_, length_length_));
439 }
440
Plaintext(QuicTransportVersion version) const441 absl::string_view QuicPacket::Plaintext(QuicTransportVersion version) const {
442 const size_t start_of_encrypted_data = GetStartOfEncryptedData(
443 version, destination_connection_id_length_, source_connection_id_length_,
444 includes_version_, includes_diversification_nonce_, packet_number_length_,
445 retry_token_length_length_, retry_token_length_, length_length_);
446 return absl::string_view(data() + start_of_encrypted_data,
447 length() - start_of_encrypted_data);
448 }
449
SerializedPacket(QuicPacketNumber packet_number,QuicPacketNumberLength packet_number_length,const char * encrypted_buffer,QuicPacketLength encrypted_length,bool has_ack,bool has_stop_waiting)450 SerializedPacket::SerializedPacket(QuicPacketNumber packet_number,
451 QuicPacketNumberLength packet_number_length,
452 const char* encrypted_buffer,
453 QuicPacketLength encrypted_length,
454 bool has_ack,
455 bool has_stop_waiting)
456 : encrypted_buffer(encrypted_buffer),
457 encrypted_length(encrypted_length),
458 has_crypto_handshake(NOT_HANDSHAKE),
459 packet_number(packet_number),
460 packet_number_length(packet_number_length),
461 encryption_level(ENCRYPTION_INITIAL),
462 has_ack(has_ack),
463 has_stop_waiting(has_stop_waiting),
464 transmission_type(NOT_RETRANSMISSION),
465 has_ack_frame_copy(false),
466 has_ack_frequency(false),
467 has_message(false),
468 fate(SEND_TO_WRITER) {}
469
SerializedPacket(SerializedPacket && other)470 SerializedPacket::SerializedPacket(SerializedPacket&& other)
471 : has_crypto_handshake(other.has_crypto_handshake),
472 packet_number(other.packet_number),
473 packet_number_length(other.packet_number_length),
474 encryption_level(other.encryption_level),
475 has_ack(other.has_ack),
476 has_stop_waiting(other.has_stop_waiting),
477 transmission_type(other.transmission_type),
478 largest_acked(other.largest_acked),
479 has_ack_frame_copy(other.has_ack_frame_copy),
480 has_ack_frequency(other.has_ack_frequency),
481 has_message(other.has_message),
482 fate(other.fate),
483 peer_address(other.peer_address) {
484 if (this != &other) {
485 if (release_encrypted_buffer && encrypted_buffer != nullptr) {
486 release_encrypted_buffer(encrypted_buffer);
487 }
488 encrypted_buffer = other.encrypted_buffer;
489 encrypted_length = other.encrypted_length;
490 release_encrypted_buffer = std::move(other.release_encrypted_buffer);
491 other.release_encrypted_buffer = nullptr;
492
493 retransmittable_frames.swap(other.retransmittable_frames);
494 nonretransmittable_frames.swap(other.nonretransmittable_frames);
495 }
496 }
497
~SerializedPacket()498 SerializedPacket::~SerializedPacket() {
499 if (release_encrypted_buffer && encrypted_buffer != nullptr) {
500 release_encrypted_buffer(encrypted_buffer);
501 }
502
503 if (!retransmittable_frames.empty()) {
504 DeleteFrames(&retransmittable_frames);
505 }
506 for (auto& frame : nonretransmittable_frames) {
507 if (!has_ack_frame_copy && frame.type == ACK_FRAME) {
508 // Do not delete ack frame if the packet does not own a copy of it.
509 continue;
510 }
511 DeleteFrame(&frame);
512 }
513 }
514
CopySerializedPacket(const SerializedPacket & serialized,QuicBufferAllocator * allocator,bool copy_buffer)515 SerializedPacket* CopySerializedPacket(const SerializedPacket& serialized,
516 QuicBufferAllocator* allocator,
517 bool copy_buffer) {
518 SerializedPacket* copy = new SerializedPacket(
519 serialized.packet_number, serialized.packet_number_length,
520 serialized.encrypted_buffer, serialized.encrypted_length,
521 serialized.has_ack, serialized.has_stop_waiting);
522 copy->has_crypto_handshake = serialized.has_crypto_handshake;
523 copy->encryption_level = serialized.encryption_level;
524 copy->transmission_type = serialized.transmission_type;
525 copy->largest_acked = serialized.largest_acked;
526 copy->has_ack_frequency = serialized.has_ack_frequency;
527 copy->has_message = serialized.has_message;
528 copy->fate = serialized.fate;
529 copy->peer_address = serialized.peer_address;
530
531 if (copy_buffer) {
532 copy->encrypted_buffer = CopyBuffer(serialized);
533 copy->release_encrypted_buffer = [](const char* p) { delete[] p; };
534 }
535 // Copy underlying frames.
536 copy->retransmittable_frames =
537 CopyQuicFrames(allocator, serialized.retransmittable_frames);
538 DCHECK(copy->nonretransmittable_frames.empty());
539 for (const auto& frame : serialized.nonretransmittable_frames) {
540 if (frame.type == ACK_FRAME) {
541 copy->has_ack_frame_copy = true;
542 }
543 copy->nonretransmittable_frames.push_back(CopyQuicFrame(allocator, frame));
544 }
545 return copy;
546 }
547
CopyBuffer(const SerializedPacket & packet)548 char* CopyBuffer(const SerializedPacket& packet) {
549 return CopyBuffer(packet.encrypted_buffer, packet.encrypted_length);
550 }
551
CopyBuffer(const char * encrypted_buffer,QuicPacketLength encrypted_length)552 char* CopyBuffer(const char* encrypted_buffer,
553 QuicPacketLength encrypted_length) {
554 char* dst_buffer = new char[encrypted_length];
555 memcpy(dst_buffer, encrypted_buffer, encrypted_length);
556 return dst_buffer;
557 }
558
ReceivedPacketInfo(const QuicSocketAddress & self_address,const QuicSocketAddress & peer_address,const QuicReceivedPacket & packet)559 ReceivedPacketInfo::ReceivedPacketInfo(const QuicSocketAddress& self_address,
560 const QuicSocketAddress& peer_address,
561 const QuicReceivedPacket& packet)
562 : self_address(self_address),
563 peer_address(peer_address),
564 packet(packet),
565 form(GOOGLE_QUIC_PACKET),
566 long_packet_type(INVALID_PACKET_TYPE),
567 version_flag(false),
568 use_length_prefix(false),
569 version_label(0),
570 version(ParsedQuicVersion::Unsupported()),
571 destination_connection_id(EmptyQuicConnectionId()),
572 source_connection_id(EmptyQuicConnectionId()) {}
573
~ReceivedPacketInfo()574 ReceivedPacketInfo::~ReceivedPacketInfo() {}
575
ToString() const576 std::string ReceivedPacketInfo::ToString() const {
577 std::string output = quiche::QuicheStrCat(
578 "{ self_address: ", self_address.ToString(),
579 ", peer_address: ", peer_address.ToString(),
580 ", packet_length: ", packet.length(), ", header_format: ", form,
581 ", version_flag: ", version_flag);
582 if (version_flag) {
583 QuicStrAppend(&output, ", version: ", ParsedQuicVersionToString(version));
584 }
585 QuicStrAppend(
586 &output,
587 ", destination_connection_id: ", destination_connection_id.ToString(),
588 ", source_connection_id: ", source_connection_id.ToString(), " }\n");
589 return output;
590 }
591
operator <<(std::ostream & os,const ReceivedPacketInfo & packet_info)592 std::ostream& operator<<(std::ostream& os,
593 const ReceivedPacketInfo& packet_info) {
594 os << packet_info.ToString();
595 return os;
596 }
597
598 } // namespace quic
599