• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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 "quiche/quic/core/quic_crypto_stream.h"
6 
7 #include <string>
8 
9 #include "absl/strings/str_cat.h"
10 #include "absl/strings/string_view.h"
11 #include "absl/types/optional.h"
12 #include "quiche/quic/core/crypto/crypto_handshake.h"
13 #include "quiche/quic/core/frames/quic_crypto_frame.h"
14 #include "quiche/quic/core/quic_connection.h"
15 #include "quiche/quic/core/quic_error_codes.h"
16 #include "quiche/quic/core/quic_session.h"
17 #include "quiche/quic/core/quic_types.h"
18 #include "quiche/quic/core/quic_utils.h"
19 #include "quiche/quic/platform/api/quic_flag_utils.h"
20 #include "quiche/quic/platform/api/quic_flags.h"
21 #include "quiche/quic/platform/api/quic_logging.h"
22 
23 namespace quic {
24 
25 #define ENDPOINT                                                   \
26   (session()->perspective() == Perspective::IS_SERVER ? "Server: " \
27                                                       : "Client:"  \
28                                                         " ")
29 
QuicCryptoStream(QuicSession * session)30 QuicCryptoStream::QuicCryptoStream(QuicSession* session)
31     : QuicStream(
32           QuicVersionUsesCryptoFrames(session->transport_version())
33               ? QuicUtils::GetInvalidStreamId(session->transport_version())
34               : QuicUtils::GetCryptoStreamId(session->transport_version()),
35           session,
36           /*is_static=*/true,
37           QuicVersionUsesCryptoFrames(session->transport_version())
38               ? CRYPTO
39               : BIDIRECTIONAL),
40       substreams_{{{this}, {this}, {this}}} {
41   // The crypto stream is exempt from connection level flow control.
42   DisableConnectionFlowControlForThisStream();
43 }
44 
~QuicCryptoStream()45 QuicCryptoStream::~QuicCryptoStream() {}
46 
47 // static
CryptoMessageFramingOverhead(QuicTransportVersion version,QuicConnectionId connection_id)48 QuicByteCount QuicCryptoStream::CryptoMessageFramingOverhead(
49     QuicTransportVersion version, QuicConnectionId connection_id) {
50   QUICHE_DCHECK(
51       QuicUtils::IsConnectionIdValidForVersion(connection_id, version));
52   quiche::QuicheVariableLengthIntegerLength retry_token_length_length =
53       quiche::VARIABLE_LENGTH_INTEGER_LENGTH_1;
54   quiche::QuicheVariableLengthIntegerLength length_length =
55       quiche::VARIABLE_LENGTH_INTEGER_LENGTH_2;
56   if (!QuicVersionHasLongHeaderLengths(version)) {
57     retry_token_length_length = quiche::VARIABLE_LENGTH_INTEGER_LENGTH_0;
58     length_length = quiche::VARIABLE_LENGTH_INTEGER_LENGTH_0;
59   }
60   return QuicPacketCreator::StreamFramePacketOverhead(
61       version, connection_id.length(), 0, /*include_version=*/true,
62       /*include_diversification_nonce=*/true,
63       VersionHasIetfInvariantHeader(version) ? PACKET_4BYTE_PACKET_NUMBER
64                                              : PACKET_1BYTE_PACKET_NUMBER,
65       retry_token_length_length, length_length,
66       /*offset=*/0);
67 }
68 
OnCryptoFrame(const QuicCryptoFrame & frame)69 void QuicCryptoStream::OnCryptoFrame(const QuicCryptoFrame& frame) {
70   QUIC_BUG_IF(quic_bug_12573_1,
71               !QuicVersionUsesCryptoFrames(session()->transport_version()))
72       << "Versions less than 47 shouldn't receive CRYPTO frames";
73   EncryptionLevel level = session()->connection()->last_decrypted_level();
74   if (!IsCryptoFrameExpectedForEncryptionLevel(level)) {
75     OnUnrecoverableError(
76         IETF_QUIC_PROTOCOL_VIOLATION,
77         absl::StrCat("CRYPTO_FRAME is unexpectedly received at level ", level));
78     return;
79   }
80   CryptoSubstream& substream =
81       substreams_[QuicUtils::GetPacketNumberSpace(level)];
82   substream.sequencer.OnCryptoFrame(frame);
83   EncryptionLevel frame_level = level;
84   if (substream.sequencer.NumBytesBuffered() >
85       BufferSizeLimitForLevel(frame_level)) {
86     OnUnrecoverableError(QUIC_FLOW_CONTROL_RECEIVED_TOO_MUCH_DATA,
87                          "Too much crypto data received");
88   }
89 }
90 
OnStreamFrame(const QuicStreamFrame & frame)91 void QuicCryptoStream::OnStreamFrame(const QuicStreamFrame& frame) {
92   if (QuicVersionUsesCryptoFrames(session()->transport_version())) {
93     QUIC_PEER_BUG(quic_peer_bug_12573_2)
94         << "Crypto data received in stream frame instead of crypto frame";
95     OnUnrecoverableError(QUIC_INVALID_STREAM_DATA, "Unexpected stream frame");
96   }
97   QuicStream::OnStreamFrame(frame);
98 }
99 
OnDataAvailable()100 void QuicCryptoStream::OnDataAvailable() {
101   EncryptionLevel level = session()->connection()->last_decrypted_level();
102   if (!QuicVersionUsesCryptoFrames(session()->transport_version())) {
103     // Versions less than 47 only support QUIC crypto, which ignores the
104     // EncryptionLevel passed into CryptoMessageParser::ProcessInput (and
105     // OnDataAvailableInSequencer).
106     OnDataAvailableInSequencer(sequencer(), level);
107     return;
108   }
109   OnDataAvailableInSequencer(
110       &substreams_[QuicUtils::GetPacketNumberSpace(level)].sequencer, level);
111 }
112 
OnDataAvailableInSequencer(QuicStreamSequencer * sequencer,EncryptionLevel level)113 void QuicCryptoStream::OnDataAvailableInSequencer(
114     QuicStreamSequencer* sequencer, EncryptionLevel level) {
115   struct iovec iov;
116   while (sequencer->GetReadableRegion(&iov)) {
117     absl::string_view data(static_cast<char*>(iov.iov_base), iov.iov_len);
118     if (!crypto_message_parser()->ProcessInput(data, level)) {
119       OnUnrecoverableError(crypto_message_parser()->error(),
120                            crypto_message_parser()->error_detail());
121       return;
122     }
123     sequencer->MarkConsumed(iov.iov_len);
124     if (one_rtt_keys_available() &&
125         crypto_message_parser()->InputBytesRemaining() == 0) {
126       // If the handshake is complete and the current message has been fully
127       // processed then no more handshake messages are likely to arrive soon
128       // so release the memory in the stream sequencer.
129       sequencer->ReleaseBufferIfEmpty();
130     }
131   }
132 }
133 
WriteCryptoData(EncryptionLevel level,absl::string_view data)134 void QuicCryptoStream::WriteCryptoData(EncryptionLevel level,
135                                        absl::string_view data) {
136   if (!QuicVersionUsesCryptoFrames(session()->transport_version())) {
137     WriteOrBufferDataAtLevel(data, /*fin=*/false, level,
138                              /*ack_listener=*/nullptr);
139     return;
140   }
141   if (data.empty()) {
142     QUIC_BUG(quic_bug_10322_1) << "Empty crypto data being written";
143     return;
144   }
145   const bool had_buffered_data = HasBufferedCryptoFrames();
146   QuicStreamSendBuffer* send_buffer =
147       &substreams_[QuicUtils::GetPacketNumberSpace(level)].send_buffer;
148   QuicStreamOffset offset = send_buffer->stream_offset();
149 
150   // Ensure this data does not cause the send buffer for this encryption level
151   // to exceed its size limit.
152   if (GetQuicFlag(quic_bounded_crypto_send_buffer)) {
153     QUIC_BUG_IF(quic_crypto_stream_offset_lt_bytes_written,
154                 offset < send_buffer->stream_bytes_written());
155     uint64_t current_buffer_size =
156         offset - std::min(offset, send_buffer->stream_bytes_written());
157     if (current_buffer_size > 0) {
158       QUIC_CODE_COUNT(quic_received_crypto_data_with_non_empty_send_buffer);
159       if (BufferSizeLimitForLevel(level) <
160           (current_buffer_size + data.length())) {
161         QUIC_BUG(quic_crypto_send_buffer_overflow)
162             << absl::StrCat("Too much data for crypto send buffer with level: ",
163                             EncryptionLevelToString(level),
164                             ", current_buffer_size: ", current_buffer_size,
165                             ", data length: ", data.length(),
166                             ", SNI: ", crypto_negotiated_params().sni);
167         OnUnrecoverableError(QUIC_INTERNAL_ERROR,
168                              "Too much data for crypto send buffer");
169         return;
170       }
171     }
172   }
173 
174   // Append |data| to the send buffer for this encryption level.
175   send_buffer->SaveStreamData(data);
176   if (kMaxStreamLength - offset < data.length()) {
177     QUIC_BUG(quic_bug_10322_2) << "Writing too much crypto handshake data";
178     OnUnrecoverableError(QUIC_INTERNAL_ERROR,
179                          "Writing too much crypto handshake data");
180     return;
181   }
182   if (had_buffered_data) {
183     // Do not try to write if there is buffered data.
184     return;
185   }
186 
187   size_t bytes_consumed = stream_delegate()->SendCryptoData(
188       level, data.length(), offset, NOT_RETRANSMISSION);
189   send_buffer->OnStreamDataConsumed(bytes_consumed);
190 }
191 
BufferSizeLimitForLevel(EncryptionLevel) const192 size_t QuicCryptoStream::BufferSizeLimitForLevel(EncryptionLevel) const {
193   return GetQuicFlag(quic_max_buffered_crypto_bytes);
194 }
195 
OnCryptoFrameAcked(const QuicCryptoFrame & frame,QuicTime::Delta)196 bool QuicCryptoStream::OnCryptoFrameAcked(const QuicCryptoFrame& frame,
197                                           QuicTime::Delta /*ack_delay_time*/) {
198   QuicByteCount newly_acked_length = 0;
199   if (!substreams_[QuicUtils::GetPacketNumberSpace(frame.level)]
200            .send_buffer.OnStreamDataAcked(frame.offset, frame.data_length,
201                                           &newly_acked_length)) {
202     OnUnrecoverableError(QUIC_INTERNAL_ERROR,
203                          "Trying to ack unsent crypto data.");
204     return false;
205   }
206   return newly_acked_length > 0;
207 }
208 
OnStreamReset(const QuicRstStreamFrame &)209 void QuicCryptoStream::OnStreamReset(const QuicRstStreamFrame& /*frame*/) {
210   stream_delegate()->OnStreamError(QUIC_INVALID_STREAM_ID,
211                                    "Attempt to reset crypto stream");
212 }
213 
NeuterUnencryptedStreamData()214 void QuicCryptoStream::NeuterUnencryptedStreamData() {
215   NeuterStreamDataOfEncryptionLevel(ENCRYPTION_INITIAL);
216 }
217 
NeuterStreamDataOfEncryptionLevel(EncryptionLevel level)218 void QuicCryptoStream::NeuterStreamDataOfEncryptionLevel(
219     EncryptionLevel level) {
220   if (!QuicVersionUsesCryptoFrames(session()->transport_version())) {
221     for (const auto& interval : bytes_consumed_[level]) {
222       QuicByteCount newly_acked_length = 0;
223       send_buffer().OnStreamDataAcked(
224           interval.min(), interval.max() - interval.min(), &newly_acked_length);
225     }
226     return;
227   }
228   QuicStreamSendBuffer* send_buffer =
229       &substreams_[QuicUtils::GetPacketNumberSpace(level)].send_buffer;
230   // TODO(nharper): Consider adding a Clear() method to QuicStreamSendBuffer
231   // to replace the following code.
232   QuicIntervalSet<QuicStreamOffset> to_ack = send_buffer->bytes_acked();
233   to_ack.Complement(0, send_buffer->stream_offset());
234   for (const auto& interval : to_ack) {
235     QuicByteCount newly_acked_length = 0;
236     send_buffer->OnStreamDataAcked(
237         interval.min(), interval.max() - interval.min(), &newly_acked_length);
238   }
239 }
240 
OnStreamDataConsumed(QuicByteCount bytes_consumed)241 void QuicCryptoStream::OnStreamDataConsumed(QuicByteCount bytes_consumed) {
242   if (QuicVersionUsesCryptoFrames(session()->transport_version())) {
243     QUIC_BUG(quic_bug_10322_3)
244         << "Stream data consumed when CRYPTO frames should be in use";
245   }
246   if (bytes_consumed > 0) {
247     bytes_consumed_[session()->connection()->encryption_level()].Add(
248         stream_bytes_written(), stream_bytes_written() + bytes_consumed);
249   }
250   QuicStream::OnStreamDataConsumed(bytes_consumed);
251 }
252 
HasPendingCryptoRetransmission() const253 bool QuicCryptoStream::HasPendingCryptoRetransmission() const {
254   if (!QuicVersionUsesCryptoFrames(session()->transport_version())) {
255     return false;
256   }
257   for (const auto& substream : substreams_) {
258     if (substream.send_buffer.HasPendingRetransmission()) {
259       return true;
260     }
261   }
262   return false;
263 }
264 
WritePendingCryptoRetransmission()265 void QuicCryptoStream::WritePendingCryptoRetransmission() {
266   QUIC_BUG_IF(quic_bug_12573_3,
267               !QuicVersionUsesCryptoFrames(session()->transport_version()))
268       << "Versions less than 47 don't write CRYPTO frames";
269   for (uint8_t i = INITIAL_DATA; i <= APPLICATION_DATA; ++i) {
270     auto packet_number_space = static_cast<PacketNumberSpace>(i);
271     QuicStreamSendBuffer* send_buffer =
272         &substreams_[packet_number_space].send_buffer;
273     while (send_buffer->HasPendingRetransmission()) {
274       auto pending = send_buffer->NextPendingRetransmission();
275       size_t bytes_consumed = stream_delegate()->SendCryptoData(
276           GetEncryptionLevelToSendCryptoDataOfSpace(packet_number_space),
277           pending.length, pending.offset, HANDSHAKE_RETRANSMISSION);
278       send_buffer->OnStreamDataRetransmitted(pending.offset, bytes_consumed);
279       if (bytes_consumed < pending.length) {
280         return;
281       }
282     }
283   }
284 }
285 
WritePendingRetransmission()286 void QuicCryptoStream::WritePendingRetransmission() {
287   while (HasPendingRetransmission()) {
288     StreamPendingRetransmission pending =
289         send_buffer().NextPendingRetransmission();
290     QuicIntervalSet<QuicStreamOffset> retransmission(
291         pending.offset, pending.offset + pending.length);
292     EncryptionLevel retransmission_encryption_level = ENCRYPTION_INITIAL;
293     // Determine the encryption level to write the retransmission
294     // at. The retransmission should be written at the same encryption level
295     // as the original transmission.
296     for (size_t i = 0; i < NUM_ENCRYPTION_LEVELS; ++i) {
297       if (retransmission.Intersects(bytes_consumed_[i])) {
298         retransmission_encryption_level = static_cast<EncryptionLevel>(i);
299         retransmission.Intersection(bytes_consumed_[i]);
300         break;
301       }
302     }
303     pending.offset = retransmission.begin()->min();
304     pending.length =
305         retransmission.begin()->max() - retransmission.begin()->min();
306     QuicConsumedData consumed = RetransmitStreamDataAtLevel(
307         pending.offset, pending.length, retransmission_encryption_level,
308         HANDSHAKE_RETRANSMISSION);
309     if (consumed.bytes_consumed < pending.length) {
310       // The connection is write blocked.
311       break;
312     }
313   }
314 }
315 
RetransmitStreamData(QuicStreamOffset offset,QuicByteCount data_length,bool,TransmissionType type)316 bool QuicCryptoStream::RetransmitStreamData(QuicStreamOffset offset,
317                                             QuicByteCount data_length,
318                                             bool /*fin*/,
319                                             TransmissionType type) {
320   QUICHE_DCHECK(type == HANDSHAKE_RETRANSMISSION || type == PTO_RETRANSMISSION);
321   QuicIntervalSet<QuicStreamOffset> retransmission(offset,
322                                                    offset + data_length);
323   // Determine the encryption level to send data. This only needs to be once as
324   // [offset, offset + data_length) is guaranteed to be in the same packet.
325   EncryptionLevel send_encryption_level = ENCRYPTION_INITIAL;
326   for (size_t i = 0; i < NUM_ENCRYPTION_LEVELS; ++i) {
327     if (retransmission.Intersects(bytes_consumed_[i])) {
328       send_encryption_level = static_cast<EncryptionLevel>(i);
329       break;
330     }
331   }
332   retransmission.Difference(bytes_acked());
333   for (const auto& interval : retransmission) {
334     QuicStreamOffset retransmission_offset = interval.min();
335     QuicByteCount retransmission_length = interval.max() - interval.min();
336     QuicConsumedData consumed = RetransmitStreamDataAtLevel(
337         retransmission_offset, retransmission_length, send_encryption_level,
338         type);
339     if (consumed.bytes_consumed < retransmission_length) {
340       // The connection is write blocked.
341       return false;
342     }
343   }
344 
345   return true;
346 }
347 
RetransmitStreamDataAtLevel(QuicStreamOffset retransmission_offset,QuicByteCount retransmission_length,EncryptionLevel encryption_level,TransmissionType type)348 QuicConsumedData QuicCryptoStream::RetransmitStreamDataAtLevel(
349     QuicStreamOffset retransmission_offset, QuicByteCount retransmission_length,
350     EncryptionLevel encryption_level, TransmissionType type) {
351   QUICHE_DCHECK(type == HANDSHAKE_RETRANSMISSION || type == PTO_RETRANSMISSION);
352   const auto consumed = stream_delegate()->WritevData(
353       id(), retransmission_length, retransmission_offset, NO_FIN, type,
354       encryption_level);
355   QUIC_DVLOG(1) << ENDPOINT << "stream " << id()
356                 << " is forced to retransmit stream data ["
357                 << retransmission_offset << ", "
358                 << retransmission_offset + retransmission_length
359                 << "), with encryption level: " << encryption_level
360                 << ", consumed: " << consumed;
361   OnStreamFrameRetransmitted(retransmission_offset, consumed.bytes_consumed,
362                              consumed.fin_consumed);
363 
364   return consumed;
365 }
366 
crypto_bytes_read() const367 uint64_t QuicCryptoStream::crypto_bytes_read() const {
368   if (!QuicVersionUsesCryptoFrames(session()->transport_version())) {
369     return stream_bytes_read();
370   }
371   uint64_t bytes_read = 0;
372   for (const CryptoSubstream& substream : substreams_) {
373     bytes_read += substream.sequencer.NumBytesConsumed();
374   }
375   return bytes_read;
376 }
377 
378 // TODO(haoyuewang) Move this test-only method under
379 // quiche/quic/test_tools.
BytesReadOnLevel(EncryptionLevel level) const380 uint64_t QuicCryptoStream::BytesReadOnLevel(EncryptionLevel level) const {
381   return substreams_[QuicUtils::GetPacketNumberSpace(level)]
382       .sequencer.NumBytesConsumed();
383 }
384 
BytesSentOnLevel(EncryptionLevel level) const385 uint64_t QuicCryptoStream::BytesSentOnLevel(EncryptionLevel level) const {
386   return substreams_[QuicUtils::GetPacketNumberSpace(level)]
387       .send_buffer.stream_bytes_written();
388 }
389 
WriteCryptoFrame(EncryptionLevel level,QuicStreamOffset offset,QuicByteCount data_length,QuicDataWriter * writer)390 bool QuicCryptoStream::WriteCryptoFrame(EncryptionLevel level,
391                                         QuicStreamOffset offset,
392                                         QuicByteCount data_length,
393                                         QuicDataWriter* writer) {
394   QUIC_BUG_IF(quic_bug_12573_4,
395               !QuicVersionUsesCryptoFrames(session()->transport_version()))
396       << "Versions less than 47 don't write CRYPTO frames (2)";
397   return substreams_[QuicUtils::GetPacketNumberSpace(level)]
398       .send_buffer.WriteStreamData(offset, data_length, writer);
399 }
400 
OnCryptoFrameLost(QuicCryptoFrame * crypto_frame)401 void QuicCryptoStream::OnCryptoFrameLost(QuicCryptoFrame* crypto_frame) {
402   QUIC_BUG_IF(quic_bug_12573_5,
403               !QuicVersionUsesCryptoFrames(session()->transport_version()))
404       << "Versions less than 47 don't lose CRYPTO frames";
405   substreams_[QuicUtils::GetPacketNumberSpace(crypto_frame->level)]
406       .send_buffer.OnStreamDataLost(crypto_frame->offset,
407                                     crypto_frame->data_length);
408 }
409 
RetransmitData(QuicCryptoFrame * crypto_frame,TransmissionType type)410 bool QuicCryptoStream::RetransmitData(QuicCryptoFrame* crypto_frame,
411                                       TransmissionType type) {
412   QUIC_BUG_IF(quic_bug_12573_6,
413               !QuicVersionUsesCryptoFrames(session()->transport_version()))
414       << "Versions less than 47 don't retransmit CRYPTO frames";
415   QuicIntervalSet<QuicStreamOffset> retransmission(
416       crypto_frame->offset, crypto_frame->offset + crypto_frame->data_length);
417   QuicStreamSendBuffer* send_buffer =
418       &substreams_[QuicUtils::GetPacketNumberSpace(crypto_frame->level)]
419            .send_buffer;
420   retransmission.Difference(send_buffer->bytes_acked());
421   if (retransmission.Empty()) {
422     return true;
423   }
424   for (const auto& interval : retransmission) {
425     size_t retransmission_offset = interval.min();
426     size_t retransmission_length = interval.max() - interval.min();
427     EncryptionLevel retransmission_encryption_level =
428         GetEncryptionLevelToSendCryptoDataOfSpace(
429             QuicUtils::GetPacketNumberSpace(crypto_frame->level));
430     size_t bytes_consumed = stream_delegate()->SendCryptoData(
431         retransmission_encryption_level, retransmission_length,
432         retransmission_offset, type);
433     send_buffer->OnStreamDataRetransmitted(retransmission_offset,
434                                            bytes_consumed);
435     if (bytes_consumed < retransmission_length) {
436       return false;
437     }
438   }
439   return true;
440 }
441 
WriteBufferedCryptoFrames()442 void QuicCryptoStream::WriteBufferedCryptoFrames() {
443   QUIC_BUG_IF(quic_bug_12573_7,
444               !QuicVersionUsesCryptoFrames(session()->transport_version()))
445       << "Versions less than 47 don't use CRYPTO frames";
446   for (uint8_t i = INITIAL_DATA; i <= APPLICATION_DATA; ++i) {
447     auto packet_number_space = static_cast<PacketNumberSpace>(i);
448     QuicStreamSendBuffer* send_buffer =
449         &substreams_[packet_number_space].send_buffer;
450     const size_t data_length =
451         send_buffer->stream_offset() - send_buffer->stream_bytes_written();
452     if (data_length == 0) {
453       // No buffered data for this encryption level.
454       continue;
455     }
456     size_t bytes_consumed = stream_delegate()->SendCryptoData(
457         GetEncryptionLevelToSendCryptoDataOfSpace(packet_number_space),
458         data_length, send_buffer->stream_bytes_written(), NOT_RETRANSMISSION);
459     send_buffer->OnStreamDataConsumed(bytes_consumed);
460     if (bytes_consumed < data_length) {
461       // Connection is write blocked.
462       break;
463     }
464   }
465 }
466 
HasBufferedCryptoFrames() const467 bool QuicCryptoStream::HasBufferedCryptoFrames() const {
468   QUIC_BUG_IF(quic_bug_12573_8,
469               !QuicVersionUsesCryptoFrames(session()->transport_version()))
470       << "Versions less than 47 don't use CRYPTO frames";
471   for (const CryptoSubstream& substream : substreams_) {
472     const QuicStreamSendBuffer& send_buffer = substream.send_buffer;
473     QUICHE_DCHECK_GE(send_buffer.stream_offset(),
474                      send_buffer.stream_bytes_written());
475     if (send_buffer.stream_offset() > send_buffer.stream_bytes_written()) {
476       return true;
477     }
478   }
479   return false;
480 }
481 
IsFrameOutstanding(EncryptionLevel level,size_t offset,size_t length) const482 bool QuicCryptoStream::IsFrameOutstanding(EncryptionLevel level, size_t offset,
483                                           size_t length) const {
484   if (!QuicVersionUsesCryptoFrames(session()->transport_version())) {
485     // This only happens if a client was originally configured for a version
486     // greater than 45, but received a version negotiation packet and is
487     // attempting to retransmit for a version less than 47. Outside of tests,
488     // this is a misconfiguration of the client, and this connection will be
489     // doomed. Return false here to avoid trying to retransmit CRYPTO frames on
490     // the wrong transport version.
491     return false;
492   }
493   return substreams_[QuicUtils::GetPacketNumberSpace(level)]
494       .send_buffer.IsStreamDataOutstanding(offset, length);
495 }
496 
IsWaitingForAcks() const497 bool QuicCryptoStream::IsWaitingForAcks() const {
498   if (!QuicVersionUsesCryptoFrames(session()->transport_version())) {
499     return QuicStream::IsWaitingForAcks();
500   }
501   for (const CryptoSubstream& substream : substreams_) {
502     if (substream.send_buffer.stream_bytes_outstanding()) {
503       return true;
504     }
505   }
506   return false;
507 }
508 
CryptoSubstream(QuicCryptoStream * crypto_stream)509 QuicCryptoStream::CryptoSubstream::CryptoSubstream(
510     QuicCryptoStream* crypto_stream)
511     : sequencer(crypto_stream),
512       send_buffer(crypto_stream->session()
513                       ->connection()
514                       ->helper()
515                       ->GetStreamSendBufferAllocator()) {}
516 
517 #undef ENDPOINT  // undef for jumbo builds
518 }  // namespace quic
519