quiche/
lib.rs

1// Copyright (C) 2018-2019, Cloudflare, Inc.
2// All rights reserved.
3//
4// Redistribution and use in source and binary forms, with or without
5// modification, are permitted provided that the following conditions are
6// met:
7//
8//     * Redistributions of source code must retain the above copyright notice,
9//       this list of conditions and the following disclaimer.
10//
11//     * Redistributions in binary form must reproduce the above copyright
12//       notice, this list of conditions and the following disclaimer in the
13//       documentation and/or other materials provided with the distribution.
14//
15// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
16// IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
17// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
18// PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
19// CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
20// EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
21// PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
22// PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
23// LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
24// NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25// SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26
27//! 🥧 Savoury implementation of the QUIC transport protocol and HTTP/3.
28//!
29//! [quiche] is an implementation of the QUIC transport protocol and HTTP/3 as
30//! specified by the [IETF]. It provides a low level API for processing QUIC
31//! packets and handling connection state. The application is responsible for
32//! providing I/O (e.g. sockets handling) as well as an event loop with support
33//! for timers.
34//!
35//! [quiche]: https://github.com/cloudflare/quiche/
36//! [ietf]: https://quicwg.org/
37//!
38//! ## Configuring connections
39//!
40//! The first step in establishing a QUIC connection using quiche is creating a
41//! [`Config`] object:
42//!
43//! ```
44//! let mut config = quiche::Config::new(quiche::PROTOCOL_VERSION)?;
45//! config.set_application_protos(&[b"example-proto"]);
46//!
47//! // Additional configuration specific to application and use case...
48//! # Ok::<(), quiche::Error>(())
49//! ```
50//!
51//! The [`Config`] object controls important aspects of the QUIC connection such
52//! as QUIC version, ALPN IDs, flow control, congestion control, idle timeout
53//! and other properties or features.
54//!
55//! QUIC is a general-purpose transport protocol and there are several
56//! configuration properties where there is no reasonable default value. For
57//! example, the permitted number of concurrent streams of any particular type
58//! is dependent on the application running over QUIC, and other use-case
59//! specific concerns.
60//!
61//! quiche defaults several properties to zero, applications most likely need
62//! to set these to something else to satisfy their needs using the following:
63//!
64//! - [`set_initial_max_streams_bidi()`]
65//! - [`set_initial_max_streams_uni()`]
66//! - [`set_initial_max_data()`]
67//! - [`set_initial_max_stream_data_bidi_local()`]
68//! - [`set_initial_max_stream_data_bidi_remote()`]
69//! - [`set_initial_max_stream_data_uni()`]
70//!
71//! [`Config`] also holds TLS configuration. This can be changed by mutators on
72//! the an existing object, or by constructing a TLS context manually and
73//! creating a configuration using [`with_boring_ssl_ctx_builder()`].
74//!
75//! A configuration object can be shared among multiple connections.
76//!
77//! ### Connection setup
78//!
79//! On the client-side the [`connect()`] utility function can be used to create
80//! a new connection, while [`accept()`] is for servers:
81//!
82//! ```
83//! # let mut config = quiche::Config::new(quiche::PROTOCOL_VERSION)?;
84//! # let server_name = "quic.tech";
85//! # let scid = quiche::ConnectionId::from_ref(&[0xba; 16]);
86//! # let peer = "127.0.0.1:1234".parse().unwrap();
87//! # let local = "127.0.0.1:4321".parse().unwrap();
88//! // Client connection.
89//! let conn =
90//!     quiche::connect(Some(&server_name), &scid, local, peer, &mut config)?;
91//!
92//! // Server connection.
93//! # let peer = "127.0.0.1:1234".parse().unwrap();
94//! # let local = "127.0.0.1:4321".parse().unwrap();
95//! let conn = quiche::accept(&scid, None, local, peer, &mut config)?;
96//! # Ok::<(), quiche::Error>(())
97//! ```
98//!
99//! In both cases, the application is responsible for generating a new source
100//! connection ID that will be used to identify the new connection.
101//!
102//! The application also need to pass the address of the remote peer of the
103//! connection: in the case of a client that would be the address of the server
104//! it is trying to connect to, and for a server that is the address of the
105//! client that initiated the connection.
106//!
107//! ## Handling incoming packets
108//!
109//! Using the connection's [`recv()`] method the application can process
110//! incoming packets that belong to that connection from the network:
111//!
112//! ```no_run
113//! # let mut buf = [0; 512];
114//! # let socket = std::net::UdpSocket::bind("127.0.0.1:0").unwrap();
115//! # let mut config = quiche::Config::new(quiche::PROTOCOL_VERSION)?;
116//! # let scid = quiche::ConnectionId::from_ref(&[0xba; 16]);
117//! # let peer = "127.0.0.1:1234".parse().unwrap();
118//! # let local = "127.0.0.1:4321".parse().unwrap();
119//! # let mut conn = quiche::accept(&scid, None, local, peer, &mut config)?;
120//! let to = socket.local_addr().unwrap();
121//!
122//! loop {
123//!     let (read, from) = socket.recv_from(&mut buf).unwrap();
124//!
125//!     let recv_info = quiche::RecvInfo { from, to };
126//!
127//!     let read = match conn.recv(&mut buf[..read], recv_info) {
128//!         Ok(v) => v,
129//!
130//!         Err(quiche::Error::Done) => {
131//!             // Done reading.
132//!             break;
133//!         },
134//!
135//!         Err(e) => {
136//!             // An error occurred, handle it.
137//!             break;
138//!         },
139//!     };
140//! }
141//! # Ok::<(), quiche::Error>(())
142//! ```
143//!
144//! The application has to pass a [`RecvInfo`] structure in order to provide
145//! additional information about the received packet (such as the address it
146//! was received from).
147//!
148//! ## Generating outgoing packets
149//!
150//! Outgoing packet are generated using the connection's [`send()`] method
151//! instead:
152//!
153//! ```no_run
154//! # let mut out = [0; 512];
155//! # let socket = std::net::UdpSocket::bind("127.0.0.1:0").unwrap();
156//! # let mut config = quiche::Config::new(quiche::PROTOCOL_VERSION)?;
157//! # let scid = quiche::ConnectionId::from_ref(&[0xba; 16]);
158//! # let peer = "127.0.0.1:1234".parse().unwrap();
159//! # let local = "127.0.0.1:4321".parse().unwrap();
160//! # let mut conn = quiche::accept(&scid, None, local, peer, &mut config)?;
161//! loop {
162//!     let (write, send_info) = match conn.send(&mut out) {
163//!         Ok(v) => v,
164//!
165//!         Err(quiche::Error::Done) => {
166//!             // Done writing.
167//!             break;
168//!         },
169//!
170//!         Err(e) => {
171//!             // An error occurred, handle it.
172//!             break;
173//!         },
174//!     };
175//!
176//!     socket.send_to(&out[..write], &send_info.to).unwrap();
177//! }
178//! # Ok::<(), quiche::Error>(())
179//! ```
180//!
181//! The application will be provided with a [`SendInfo`] structure providing
182//! additional information about the newly created packet (such as the address
183//! the packet should be sent to).
184//!
185//! When packets are sent, the application is responsible for maintaining a
186//! timer to react to time-based connection events. The timer expiration can be
187//! obtained using the connection's [`timeout()`] method.
188//!
189//! ```
190//! # let mut config = quiche::Config::new(quiche::PROTOCOL_VERSION)?;
191//! # let scid = quiche::ConnectionId::from_ref(&[0xba; 16]);
192//! # let peer = "127.0.0.1:1234".parse().unwrap();
193//! # let local = "127.0.0.1:4321".parse().unwrap();
194//! # let mut conn = quiche::accept(&scid, None, local, peer, &mut config)?;
195//! let timeout = conn.timeout();
196//! # Ok::<(), quiche::Error>(())
197//! ```
198//!
199//! The application is responsible for providing a timer implementation, which
200//! can be specific to the operating system or networking framework used. When
201//! a timer expires, the connection's [`on_timeout()`] method should be called,
202//! after which additional packets might need to be sent on the network:
203//!
204//! ```no_run
205//! # let mut out = [0; 512];
206//! # let socket = std::net::UdpSocket::bind("127.0.0.1:0").unwrap();
207//! # let mut config = quiche::Config::new(quiche::PROTOCOL_VERSION)?;
208//! # let scid = quiche::ConnectionId::from_ref(&[0xba; 16]);
209//! # let peer = "127.0.0.1:1234".parse().unwrap();
210//! # let local = "127.0.0.1:4321".parse().unwrap();
211//! # let mut conn = quiche::accept(&scid, None, local, peer, &mut config)?;
212//! // Timeout expired, handle it.
213//! conn.on_timeout();
214//!
215//! // Send more packets as needed after timeout.
216//! loop {
217//!     let (write, send_info) = match conn.send(&mut out) {
218//!         Ok(v) => v,
219//!
220//!         Err(quiche::Error::Done) => {
221//!             // Done writing.
222//!             break;
223//!         },
224//!
225//!         Err(e) => {
226//!             // An error occurred, handle it.
227//!             break;
228//!         },
229//!     };
230//!
231//!     socket.send_to(&out[..write], &send_info.to).unwrap();
232//! }
233//! # Ok::<(), quiche::Error>(())
234//! ```
235//!
236//! ### Pacing
237//!
238//! It is recommended that applications [pace] sending of outgoing packets to
239//! avoid creating packet bursts that could cause short-term congestion and
240//! losses in the network.
241//!
242//! quiche exposes pacing hints for outgoing packets through the [`at`] field
243//! of the [`SendInfo`] structure that is returned by the [`send()`] method.
244//! This field represents the time when a specific packet should be sent into
245//! the network.
246//!
247//! Applications can use these hints by artificially delaying the sending of
248//! packets through platform-specific mechanisms (such as the [`SO_TXTIME`]
249//! socket option on Linux), or custom methods (for example by using user-space
250//! timers).
251//!
252//! [pace]: https://datatracker.ietf.org/doc/html/rfc9002#section-7.7
253//! [`SO_TXTIME`]: https://man7.org/linux/man-pages/man8/tc-etf.8.html
254//!
255//! ## Sending and receiving stream data
256//!
257//! After some back and forth, the connection will complete its handshake and
258//! will be ready for sending or receiving application data.
259//!
260//! Data can be sent on a stream by using the [`stream_send()`] method:
261//!
262//! ```no_run
263//! # let mut config = quiche::Config::new(quiche::PROTOCOL_VERSION)?;
264//! # let scid = quiche::ConnectionId::from_ref(&[0xba; 16]);
265//! # let peer = "127.0.0.1:1234".parse().unwrap();
266//! # let local = "127.0.0.1:4321".parse().unwrap();
267//! # let mut conn = quiche::accept(&scid, None, local, peer, &mut config)?;
268//! if conn.is_established() {
269//!     // Handshake completed, send some data on stream 0.
270//!     conn.stream_send(0, b"hello", true)?;
271//! }
272//! # Ok::<(), quiche::Error>(())
273//! ```
274//!
275//! The application can check whether there are any readable streams by using
276//! the connection's [`readable()`] method, which returns an iterator over all
277//! the streams that have outstanding data to read.
278//!
279//! The [`stream_recv()`] method can then be used to retrieve the application
280//! data from the readable stream:
281//!
282//! ```no_run
283//! # let mut buf = [0; 512];
284//! # let mut config = quiche::Config::new(quiche::PROTOCOL_VERSION)?;
285//! # let scid = quiche::ConnectionId::from_ref(&[0xba; 16]);
286//! # let peer = "127.0.0.1:1234".parse().unwrap();
287//! # let local = "127.0.0.1:4321".parse().unwrap();
288//! # let mut conn = quiche::accept(&scid, None, local, peer, &mut config)?;
289//! if conn.is_established() {
290//!     // Iterate over readable streams.
291//!     for stream_id in conn.readable() {
292//!         // Stream is readable, read until there's no more data.
293//!         while let Ok((read, fin)) = conn.stream_recv(stream_id, &mut buf) {
294//!             println!("Got {} bytes on stream {}", read, stream_id);
295//!         }
296//!     }
297//! }
298//! # Ok::<(), quiche::Error>(())
299//! ```
300//!
301//! ## HTTP/3
302//!
303//! The quiche [HTTP/3 module] provides a high level API for sending and
304//! receiving HTTP requests and responses on top of the QUIC transport protocol.
305//!
306//! [`Config`]: https://docs.quic.tech/quiche/struct.Config.html
307//! [`set_initial_max_streams_bidi()`]: https://docs.rs/quiche/latest/quiche/struct.Config.html#method.set_initial_max_streams_bidi
308//! [`set_initial_max_streams_uni()`]: https://docs.rs/quiche/latest/quiche/struct.Config.html#method.set_initial_max_streams_uni
309//! [`set_initial_max_data()`]: https://docs.rs/quiche/latest/quiche/struct.Config.html#method.set_initial_max_data
310//! [`set_initial_max_stream_data_bidi_local()`]: https://docs.rs/quiche/latest/quiche/struct.Config.html#method.set_initial_max_stream_data_bidi_local
311//! [`set_initial_max_stream_data_bidi_remote()`]: https://docs.rs/quiche/latest/quiche/struct.Config.html#method.set_initial_max_stream_data_bidi_remote
312//! [`set_initial_max_stream_data_uni()`]: https://docs.rs/quiche/latest/quiche/struct.Config.html#method.set_initial_max_stream_data_uni
313//! [`with_boring_ssl_ctx_builder()`]: https://docs.quic.tech/quiche/struct.Config.html#method.with_boring_ssl_ctx_builder
314//! [`connect()`]: fn.connect.html
315//! [`accept()`]: fn.accept.html
316//! [`recv()`]: struct.Connection.html#method.recv
317//! [`RecvInfo`]: struct.RecvInfo.html
318//! [`send()`]: struct.Connection.html#method.send
319//! [`SendInfo`]: struct.SendInfo.html
320//! [`at`]: struct.SendInfo.html#structfield.at
321//! [`timeout()`]: struct.Connection.html#method.timeout
322//! [`on_timeout()`]: struct.Connection.html#method.on_timeout
323//! [`stream_send()`]: struct.Connection.html#method.stream_send
324//! [`readable()`]: struct.Connection.html#method.readable
325//! [`stream_recv()`]: struct.Connection.html#method.stream_recv
326//! [HTTP/3 module]: h3/index.html
327//!
328//! ## Congestion Control
329//!
330//! The quiche library provides a high-level API for configuring which
331//! congestion control algorithm to use throughout the QUIC connection.
332//!
333//! When a QUIC connection is created, the application can optionally choose
334//! which CC algorithm to use. See [`CongestionControlAlgorithm`] for currently
335//! available congestion control algorithms.
336//!
337//! For example:
338//!
339//! ```
340//! let mut config = quiche::Config::new(quiche::PROTOCOL_VERSION).unwrap();
341//! config.set_cc_algorithm(quiche::CongestionControlAlgorithm::Reno);
342//! ```
343//!
344//! Alternatively, you can configure the congestion control algorithm to use
345//! by its name.
346//!
347//! ```
348//! let mut config = quiche::Config::new(quiche::PROTOCOL_VERSION).unwrap();
349//! config.set_cc_algorithm_name("reno").unwrap();
350//! ```
351//!
352//! Note that the CC algorithm should be configured before calling [`connect()`]
353//! or [`accept()`]. Otherwise the connection will use a default CC algorithm.
354//!
355//! [`CongestionControlAlgorithm`]: enum.CongestionControlAlgorithm.html
356//!
357//! ## Feature flags
358//!
359//! quiche defines a number of [feature flags] to reduce the amount of compiled
360//! code and dependencies:
361//!
362//! * `boringssl-vendored` (default): Build the vendored BoringSSL library.
363//!
364//! * `boringssl-boring-crate`: Use the BoringSSL library provided by the
365//!   [boring] crate. It takes precedence over `boringssl-vendored` if both
366//!   features are enabled.
367//!
368//! * `pkg-config-meta`: Generate pkg-config metadata file for libquiche.
369//!
370//! * `ffi`: Build and expose the FFI API.
371//!
372//! * `qlog`: Enable support for the [qlog] logging format.
373//!
374//! [feature flags]: https://doc.rust-lang.org/cargo/reference/manifest.html#the-features-section
375//! [boring]: https://crates.io/crates/boring
376//! [qlog]: https://datatracker.ietf.org/doc/html/draft-ietf-quic-qlog-main-schema
377
378#![allow(clippy::upper_case_acronyms)]
379#![warn(missing_docs)]
380#![warn(unused_qualifications)]
381#![cfg_attr(docsrs, feature(doc_cfg))]
382
383#[macro_use]
384extern crate log;
385
386use std::cmp;
387
388use std::collections::HashSet;
389use std::collections::VecDeque;
390
391use std::convert::TryInto;
392
393use std::net::SocketAddr;
394
395use std::str::FromStr;
396
397use std::sync::Arc;
398
399use std::time::Duration;
400use std::time::Instant;
401
402#[cfg(feature = "qlog")]
403use qlog::events::connectivity::ConnectivityEventType;
404#[cfg(feature = "qlog")]
405use qlog::events::connectivity::TransportOwner;
406#[cfg(feature = "qlog")]
407use qlog::events::quic::RecoveryEventType;
408#[cfg(feature = "qlog")]
409use qlog::events::quic::TransportEventType;
410#[cfg(feature = "qlog")]
411use qlog::events::DataRecipient;
412#[cfg(feature = "qlog")]
413use qlog::events::Event;
414#[cfg(feature = "qlog")]
415use qlog::events::EventData;
416#[cfg(feature = "qlog")]
417use qlog::events::EventImportance;
418#[cfg(feature = "qlog")]
419use qlog::events::EventType;
420#[cfg(feature = "qlog")]
421use qlog::events::RawInfo;
422
423use smallvec::SmallVec;
424
425use crate::range_buf::DefaultBufFactory;
426
427use crate::recovery::OnAckReceivedOutcome;
428use crate::recovery::OnLossDetectionTimeoutOutcome;
429use crate::recovery::RecoveryOps;
430use crate::recovery::ReleaseDecision;
431
432use crate::stream::StreamPriorityKey;
433
434/// The current QUIC wire version.
435pub const PROTOCOL_VERSION: u32 = PROTOCOL_VERSION_V1;
436
437/// Supported QUIC versions.
438const PROTOCOL_VERSION_V1: u32 = 0x0000_0001;
439
440/// The maximum length of a connection ID.
441pub const MAX_CONN_ID_LEN: usize = packet::MAX_CID_LEN as usize;
442
443/// The minimum length of Initial packets sent by a client.
444pub const MIN_CLIENT_INITIAL_LEN: usize = 1200;
445
446/// The default initial RTT.
447const DEFAULT_INITIAL_RTT: Duration = Duration::from_millis(333);
448
449const PAYLOAD_MIN_LEN: usize = 4;
450
451// PATH_CHALLENGE (9 bytes) + AEAD tag (16 bytes).
452const MIN_PROBING_SIZE: usize = 25;
453
454const MAX_AMPLIFICATION_FACTOR: usize = 3;
455
456// The maximum number of tracked packet number ranges that need to be acked.
457//
458// This represents more or less how many ack blocks can fit in a typical packet.
459const MAX_ACK_RANGES: usize = 68;
460
461// The highest possible stream ID allowed.
462const MAX_STREAM_ID: u64 = 1 << 60;
463
464// The default max_datagram_size used in congestion control.
465const MAX_SEND_UDP_PAYLOAD_SIZE: usize = 1200;
466
467// The default length of DATAGRAM queues.
468const DEFAULT_MAX_DGRAM_QUEUE_LEN: usize = 0;
469
470// The default length of PATH_CHALLENGE receive queue.
471const DEFAULT_MAX_PATH_CHALLENGE_RX_QUEUE_LEN: usize = 3;
472
473// The DATAGRAM standard recommends either none or 65536 as maximum DATAGRAM
474// frames size. We enforce the recommendation for forward compatibility.
475const MAX_DGRAM_FRAME_SIZE: u64 = 65536;
476
477// The length of the payload length field.
478const PAYLOAD_LENGTH_LEN: usize = 2;
479
480// The number of undecryptable that can be buffered.
481const MAX_UNDECRYPTABLE_PACKETS: usize = 10;
482
483const RESERVED_VERSION_MASK: u32 = 0xfafafafa;
484
485// The default size of the receiver connection flow control window.
486const DEFAULT_CONNECTION_WINDOW: u64 = 48 * 1024;
487
488// The maximum size of the receiver connection flow control window.
489const MAX_CONNECTION_WINDOW: u64 = 24 * 1024 * 1024;
490
491// How much larger the connection flow control window need to be larger than
492// the stream flow control window.
493const CONNECTION_WINDOW_FACTOR: f64 = 1.5;
494
495// How many probing packet timeouts do we tolerate before considering the path
496// validation as failed.
497const MAX_PROBING_TIMEOUTS: usize = 3;
498
499// The default initial congestion window size in terms of packet count.
500const DEFAULT_INITIAL_CONGESTION_WINDOW_PACKETS: usize = 10;
501
502// The maximum data offset that can be stored in a crypto stream.
503const MAX_CRYPTO_STREAM_OFFSET: u64 = 1 << 16;
504
505// The send capacity factor.
506const TX_CAP_FACTOR: f64 = 1.0;
507
508/// Ancillary information about incoming packets.
509#[derive(Clone, Copy, Debug, PartialEq, Eq)]
510pub struct RecvInfo {
511    /// The remote address the packet was received from.
512    pub from: SocketAddr,
513
514    /// The local address the packet was received on.
515    pub to: SocketAddr,
516}
517
518/// Ancillary information about outgoing packets.
519#[derive(Clone, Copy, Debug, PartialEq, Eq)]
520pub struct SendInfo {
521    /// The local address the packet should be sent from.
522    pub from: SocketAddr,
523
524    /// The remote address the packet should be sent to.
525    pub to: SocketAddr,
526
527    /// The time to send the packet out.
528    ///
529    /// See [Pacing] for more details.
530    ///
531    /// [Pacing]: index.html#pacing
532    pub at: Instant,
533}
534
535/// The side of the stream to be shut down.
536///
537/// This should be used when calling [`stream_shutdown()`].
538///
539/// [`stream_shutdown()`]: struct.Connection.html#method.stream_shutdown
540#[repr(C)]
541#[derive(PartialEq, Eq)]
542pub enum Shutdown {
543    /// Stop receiving stream data.
544    Read  = 0,
545
546    /// Stop sending stream data.
547    Write = 1,
548}
549
550/// Qlog logging level.
551#[repr(C)]
552#[cfg(feature = "qlog")]
553#[cfg_attr(docsrs, doc(cfg(feature = "qlog")))]
554pub enum QlogLevel {
555    /// Logs any events of Core importance.
556    Core  = 0,
557
558    /// Logs any events of Core and Base importance.
559    Base  = 1,
560
561    /// Logs any events of Core, Base and Extra importance
562    Extra = 2,
563}
564
565/// Stores configuration shared between multiple connections.
566pub struct Config {
567    local_transport_params: TransportParams,
568
569    version: u32,
570
571    tls_ctx: tls::Context,
572
573    application_protos: Vec<Vec<u8>>,
574
575    grease: bool,
576
577    cc_algorithm: CongestionControlAlgorithm,
578    custom_bbr_params: Option<BbrParams>,
579    initial_congestion_window_packets: usize,
580    enable_relaxed_loss_threshold: bool,
581
582    pmtud: bool,
583
584    hystart: bool,
585
586    pacing: bool,
587    /// Send rate limit in Mbps
588    max_pacing_rate: Option<u64>,
589
590    tx_cap_factor: f64,
591
592    dgram_recv_max_queue_len: usize,
593    dgram_send_max_queue_len: usize,
594
595    path_challenge_recv_max_queue_len: usize,
596
597    max_send_udp_payload_size: usize,
598
599    max_connection_window: u64,
600    max_stream_window: u64,
601
602    max_amplification_factor: usize,
603
604    disable_dcid_reuse: bool,
605
606    track_unknown_transport_params: Option<usize>,
607
608    initial_rtt: Duration,
609}
610
611// See https://quicwg.org/base-drafts/rfc9000.html#section-15
612fn is_reserved_version(version: u32) -> bool {
613    version & RESERVED_VERSION_MASK == version
614}
615
616impl Config {
617    /// Creates a config object with the given version.
618    ///
619    /// ## Examples:
620    ///
621    /// ```
622    /// let config = quiche::Config::new(quiche::PROTOCOL_VERSION)?;
623    /// # Ok::<(), quiche::Error>(())
624    /// ```
625    pub fn new(version: u32) -> Result<Config> {
626        Self::with_tls_ctx(version, tls::Context::new()?)
627    }
628
629    /// Creates a config object with the given version and
630    /// [`SslContextBuilder`].
631    ///
632    /// This is useful for applications that wish to manually configure
633    /// [`SslContextBuilder`].
634    ///
635    /// [`SslContextBuilder`]: https://docs.rs/boring/latest/boring/ssl/struct.SslContextBuilder.html
636    #[cfg(feature = "boringssl-boring-crate")]
637    #[cfg_attr(docsrs, doc(cfg(feature = "boringssl-boring-crate")))]
638    pub fn with_boring_ssl_ctx_builder(
639        version: u32, tls_ctx_builder: boring::ssl::SslContextBuilder,
640    ) -> Result<Config> {
641        Self::with_tls_ctx(version, tls::Context::from_boring(tls_ctx_builder))
642    }
643
644    fn with_tls_ctx(version: u32, tls_ctx: tls::Context) -> Result<Config> {
645        if !is_reserved_version(version) && !version_is_supported(version) {
646            return Err(Error::UnknownVersion);
647        }
648
649        Ok(Config {
650            local_transport_params: TransportParams::default(),
651            version,
652            tls_ctx,
653            application_protos: Vec::new(),
654            grease: true,
655            cc_algorithm: CongestionControlAlgorithm::CUBIC,
656            custom_bbr_params: None,
657            initial_congestion_window_packets:
658                DEFAULT_INITIAL_CONGESTION_WINDOW_PACKETS,
659            enable_relaxed_loss_threshold: false,
660            pmtud: false,
661            hystart: true,
662            pacing: true,
663            max_pacing_rate: None,
664
665            tx_cap_factor: TX_CAP_FACTOR,
666
667            dgram_recv_max_queue_len: DEFAULT_MAX_DGRAM_QUEUE_LEN,
668            dgram_send_max_queue_len: DEFAULT_MAX_DGRAM_QUEUE_LEN,
669
670            path_challenge_recv_max_queue_len:
671                DEFAULT_MAX_PATH_CHALLENGE_RX_QUEUE_LEN,
672
673            max_send_udp_payload_size: MAX_SEND_UDP_PAYLOAD_SIZE,
674
675            max_connection_window: MAX_CONNECTION_WINDOW,
676            max_stream_window: stream::MAX_STREAM_WINDOW,
677
678            max_amplification_factor: MAX_AMPLIFICATION_FACTOR,
679
680            disable_dcid_reuse: false,
681
682            track_unknown_transport_params: None,
683            initial_rtt: DEFAULT_INITIAL_RTT,
684        })
685    }
686
687    /// Configures the given certificate chain.
688    ///
689    /// The content of `file` is parsed as a PEM-encoded leaf certificate,
690    /// followed by optional intermediate certificates.
691    ///
692    /// ## Examples:
693    ///
694    /// ```no_run
695    /// # let mut config = quiche::Config::new(0xbabababa)?;
696    /// config.load_cert_chain_from_pem_file("/path/to/cert.pem")?;
697    /// # Ok::<(), quiche::Error>(())
698    /// ```
699    pub fn load_cert_chain_from_pem_file(&mut self, file: &str) -> Result<()> {
700        self.tls_ctx.use_certificate_chain_file(file)
701    }
702
703    /// Configures the given private key.
704    ///
705    /// The content of `file` is parsed as a PEM-encoded private key.
706    ///
707    /// ## Examples:
708    ///
709    /// ```no_run
710    /// # let mut config = quiche::Config::new(0xbabababa)?;
711    /// config.load_priv_key_from_pem_file("/path/to/key.pem")?;
712    /// # Ok::<(), quiche::Error>(())
713    /// ```
714    pub fn load_priv_key_from_pem_file(&mut self, file: &str) -> Result<()> {
715        self.tls_ctx.use_privkey_file(file)
716    }
717
718    /// Specifies a file where trusted CA certificates are stored for the
719    /// purposes of certificate verification.
720    ///
721    /// The content of `file` is parsed as a PEM-encoded certificate chain.
722    ///
723    /// ## Examples:
724    ///
725    /// ```no_run
726    /// # let mut config = quiche::Config::new(0xbabababa)?;
727    /// config.load_verify_locations_from_file("/path/to/cert.pem")?;
728    /// # Ok::<(), quiche::Error>(())
729    /// ```
730    pub fn load_verify_locations_from_file(&mut self, file: &str) -> Result<()> {
731        self.tls_ctx.load_verify_locations_from_file(file)
732    }
733
734    /// Specifies a directory where trusted CA certificates are stored for the
735    /// purposes of certificate verification.
736    ///
737    /// The content of `dir` a set of PEM-encoded certificate chains.
738    ///
739    /// ## Examples:
740    ///
741    /// ```no_run
742    /// # let mut config = quiche::Config::new(0xbabababa)?;
743    /// config.load_verify_locations_from_directory("/path/to/certs")?;
744    /// # Ok::<(), quiche::Error>(())
745    /// ```
746    pub fn load_verify_locations_from_directory(
747        &mut self, dir: &str,
748    ) -> Result<()> {
749        self.tls_ctx.load_verify_locations_from_directory(dir)
750    }
751
752    /// Configures whether to verify the peer's certificate.
753    ///
754    /// This should usually be `true` for client-side connections and `false`
755    /// for server-side ones.
756    ///
757    /// Note that by default, no verification is performed.
758    ///
759    /// Also note that on the server-side, enabling verification of the peer
760    /// will trigger a certificate request and make authentication errors
761    /// fatal, but will still allow anonymous clients (i.e. clients that
762    /// don't present a certificate at all). Servers can check whether a
763    /// client presented a certificate by calling [`peer_cert()`] if they
764    /// need to.
765    ///
766    /// [`peer_cert()`]: struct.Connection.html#method.peer_cert
767    pub fn verify_peer(&mut self, verify: bool) {
768        self.tls_ctx.set_verify(verify);
769    }
770
771    /// Configures whether to do path MTU discovery.
772    ///
773    /// The default value is `false`.
774    pub fn discover_pmtu(&mut self, discover: bool) {
775        self.pmtud = discover;
776    }
777
778    /// Configures whether to send GREASE values.
779    ///
780    /// The default value is `true`.
781    pub fn grease(&mut self, grease: bool) {
782        self.grease = grease;
783    }
784
785    /// Enables logging of secrets.
786    ///
787    /// When logging is enabled, the [`set_keylog()`] method must be called on
788    /// the connection for its cryptographic secrets to be logged in the
789    /// [keylog] format to the specified writer.
790    ///
791    /// [`set_keylog()`]: struct.Connection.html#method.set_keylog
792    /// [keylog]: https://developer.mozilla.org/en-US/docs/Mozilla/Projects/NSS/Key_Log_Format
793    pub fn log_keys(&mut self) {
794        self.tls_ctx.enable_keylog();
795    }
796
797    /// Configures the session ticket key material.
798    ///
799    /// On the server this key will be used to encrypt and decrypt session
800    /// tickets, used to perform session resumption without server-side state.
801    ///
802    /// By default a key is generated internally, and rotated regularly, so
803    /// applications don't need to call this unless they need to use a
804    /// specific key (e.g. in order to support resumption across multiple
805    /// servers), in which case the application is also responsible for
806    /// rotating the key to provide forward secrecy.
807    pub fn set_ticket_key(&mut self, key: &[u8]) -> Result<()> {
808        self.tls_ctx.set_ticket_key(key)
809    }
810
811    /// Enables sending or receiving early data.
812    pub fn enable_early_data(&mut self) {
813        self.tls_ctx.set_early_data_enabled(true);
814    }
815
816    /// Configures the list of supported application protocols.
817    ///
818    /// On the client this configures the list of protocols to send to the
819    /// server as part of the ALPN extension.
820    ///
821    /// On the server this configures the list of supported protocols to match
822    /// against the client-supplied list.
823    ///
824    /// Applications must set a value, but no default is provided.
825    ///
826    /// ## Examples:
827    ///
828    /// ```
829    /// # let mut config = quiche::Config::new(0xbabababa)?;
830    /// config.set_application_protos(&[b"http/1.1", b"http/0.9"]);
831    /// # Ok::<(), quiche::Error>(())
832    /// ```
833    pub fn set_application_protos(
834        &mut self, protos_list: &[&[u8]],
835    ) -> Result<()> {
836        self.application_protos =
837            protos_list.iter().map(|s| s.to_vec()).collect();
838
839        self.tls_ctx.set_alpn(protos_list)
840    }
841
842    /// Configures the list of supported application protocols using wire
843    /// format.
844    ///
845    /// The list of protocols `protos` must be a series of non-empty, 8-bit
846    /// length-prefixed strings.
847    ///
848    /// See [`set_application_protos`](Self::set_application_protos) for more
849    /// background about application protocols.
850    ///
851    /// ## Examples:
852    ///
853    /// ```
854    /// # let mut config = quiche::Config::new(0xbabababa)?;
855    /// config.set_application_protos_wire_format(b"\x08http/1.1\x08http/0.9")?;
856    /// # Ok::<(), quiche::Error>(())
857    /// ```
858    pub fn set_application_protos_wire_format(
859        &mut self, protos: &[u8],
860    ) -> Result<()> {
861        let mut b = octets::Octets::with_slice(protos);
862
863        let mut protos_list = Vec::new();
864
865        while let Ok(proto) = b.get_bytes_with_u8_length() {
866            protos_list.push(proto.buf());
867        }
868
869        self.set_application_protos(&protos_list)
870    }
871
872    /// Sets the anti-amplification limit factor.
873    ///
874    /// The default value is `3`.
875    pub fn set_max_amplification_factor(&mut self, v: usize) {
876        self.max_amplification_factor = v;
877    }
878
879    /// Sets the send capacity factor.
880    ///
881    /// The default value is `1`.
882    pub fn set_send_capacity_factor(&mut self, v: f64) {
883        self.tx_cap_factor = v;
884    }
885
886    /// Sets the connection's initial RTT.
887    ///
888    /// The default value is `333`.
889    pub fn set_initial_rtt(&mut self, v: Duration) {
890        self.initial_rtt = v;
891    }
892
893    /// Sets the `max_idle_timeout` transport parameter, in milliseconds.
894    ///
895    /// The default value is infinite, that is, no timeout is used.
896    pub fn set_max_idle_timeout(&mut self, v: u64) {
897        self.local_transport_params.max_idle_timeout =
898            cmp::min(v, octets::MAX_VAR_INT);
899    }
900
901    /// Sets the `max_udp_payload_size transport` parameter.
902    ///
903    /// The default value is `65527`.
904    pub fn set_max_recv_udp_payload_size(&mut self, v: usize) {
905        self.local_transport_params.max_udp_payload_size =
906            cmp::min(v as u64, octets::MAX_VAR_INT);
907    }
908
909    /// Sets the maximum outgoing UDP payload size.
910    ///
911    /// The default and minimum value is `1200`.
912    pub fn set_max_send_udp_payload_size(&mut self, v: usize) {
913        self.max_send_udp_payload_size = cmp::max(v, MAX_SEND_UDP_PAYLOAD_SIZE);
914    }
915
916    /// Sets the `initial_max_data` transport parameter.
917    ///
918    /// When set to a non-zero value quiche will only allow at most `v` bytes of
919    /// incoming stream data to be buffered for the whole connection (that is,
920    /// data that is not yet read by the application) and will allow more data
921    /// to be received as the buffer is consumed by the application.
922    ///
923    /// When set to zero, either explicitly or via the default, quiche will not
924    /// give any flow control to the peer, preventing it from sending any stream
925    /// data.
926    ///
927    /// The default value is `0`.
928    pub fn set_initial_max_data(&mut self, v: u64) {
929        self.local_transport_params.initial_max_data =
930            cmp::min(v, octets::MAX_VAR_INT);
931    }
932
933    /// Sets the `initial_max_stream_data_bidi_local` transport parameter.
934    ///
935    /// When set to a non-zero value quiche will only allow at most `v` bytes
936    /// of incoming stream data to be buffered for each locally-initiated
937    /// bidirectional stream (that is, data that is not yet read by the
938    /// application) and will allow more data to be received as the buffer is
939    /// consumed by the application.
940    ///
941    /// When set to zero, either explicitly or via the default, quiche will not
942    /// give any flow control to the peer, preventing it from sending any stream
943    /// data.
944    ///
945    /// The default value is `0`.
946    pub fn set_initial_max_stream_data_bidi_local(&mut self, v: u64) {
947        self.local_transport_params
948            .initial_max_stream_data_bidi_local =
949            cmp::min(v, octets::MAX_VAR_INT);
950    }
951
952    /// Sets the `initial_max_stream_data_bidi_remote` transport parameter.
953    ///
954    /// When set to a non-zero value quiche will only allow at most `v` bytes
955    /// of incoming stream data to be buffered for each remotely-initiated
956    /// bidirectional stream (that is, data that is not yet read by the
957    /// application) and will allow more data to be received as the buffer is
958    /// consumed by the application.
959    ///
960    /// When set to zero, either explicitly or via the default, quiche will not
961    /// give any flow control to the peer, preventing it from sending any stream
962    /// data.
963    ///
964    /// The default value is `0`.
965    pub fn set_initial_max_stream_data_bidi_remote(&mut self, v: u64) {
966        self.local_transport_params
967            .initial_max_stream_data_bidi_remote =
968            cmp::min(v, octets::MAX_VAR_INT);
969    }
970
971    /// Sets the `initial_max_stream_data_uni` transport parameter.
972    ///
973    /// When set to a non-zero value quiche will only allow at most `v` bytes
974    /// of incoming stream data to be buffered for each unidirectional stream
975    /// (that is, data that is not yet read by the application) and will allow
976    /// more data to be received as the buffer is consumed by the application.
977    ///
978    /// When set to zero, either explicitly or via the default, quiche will not
979    /// give any flow control to the peer, preventing it from sending any stream
980    /// data.
981    ///
982    /// The default value is `0`.
983    pub fn set_initial_max_stream_data_uni(&mut self, v: u64) {
984        self.local_transport_params.initial_max_stream_data_uni =
985            cmp::min(v, octets::MAX_VAR_INT);
986    }
987
988    /// Sets the `initial_max_streams_bidi` transport parameter.
989    ///
990    /// When set to a non-zero value quiche will only allow `v` number of
991    /// concurrent remotely-initiated bidirectional streams to be open at any
992    /// given time and will increase the limit automatically as streams are
993    /// completed.
994    ///
995    /// When set to zero, either explicitly or via the default, quiche will not
996    /// not allow the peer to open any bidirectional streams.
997    ///
998    /// A bidirectional stream is considered completed when all incoming data
999    /// has been read by the application (up to the `fin` offset) or the
1000    /// stream's read direction has been shutdown, and all outgoing data has
1001    /// been acked by the peer (up to the `fin` offset) or the stream's write
1002    /// direction has been shutdown.
1003    ///
1004    /// The default value is `0`.
1005    pub fn set_initial_max_streams_bidi(&mut self, v: u64) {
1006        self.local_transport_params.initial_max_streams_bidi =
1007            cmp::min(v, octets::MAX_VAR_INT);
1008    }
1009
1010    /// Sets the `initial_max_streams_uni` transport parameter.
1011    ///
1012    /// When set to a non-zero value quiche will only allow `v` number of
1013    /// concurrent remotely-initiated unidirectional streams to be open at any
1014    /// given time and will increase the limit automatically as streams are
1015    /// completed.
1016    ///
1017    /// When set to zero, either explicitly or via the default, quiche will not
1018    /// not allow the peer to open any unidirectional streams.
1019    ///
1020    /// A unidirectional stream is considered completed when all incoming data
1021    /// has been read by the application (up to the `fin` offset) or the
1022    /// stream's read direction has been shutdown.
1023    ///
1024    /// The default value is `0`.
1025    pub fn set_initial_max_streams_uni(&mut self, v: u64) {
1026        self.local_transport_params.initial_max_streams_uni =
1027            cmp::min(v, octets::MAX_VAR_INT);
1028    }
1029
1030    /// Sets the `ack_delay_exponent` transport parameter.
1031    ///
1032    /// The default value is `3`.
1033    pub fn set_ack_delay_exponent(&mut self, v: u64) {
1034        self.local_transport_params.ack_delay_exponent =
1035            cmp::min(v, octets::MAX_VAR_INT);
1036    }
1037
1038    /// Sets the `max_ack_delay` transport parameter.
1039    ///
1040    /// The default value is `25`.
1041    pub fn set_max_ack_delay(&mut self, v: u64) {
1042        self.local_transport_params.max_ack_delay =
1043            cmp::min(v, octets::MAX_VAR_INT);
1044    }
1045
1046    /// Sets the `active_connection_id_limit` transport parameter.
1047    ///
1048    /// The default value is `2`. Lower values will be ignored.
1049    pub fn set_active_connection_id_limit(&mut self, v: u64) {
1050        if v >= 2 {
1051            self.local_transport_params.active_conn_id_limit =
1052                cmp::min(v, octets::MAX_VAR_INT);
1053        }
1054    }
1055
1056    /// Sets the `disable_active_migration` transport parameter.
1057    ///
1058    /// The default value is `false`.
1059    pub fn set_disable_active_migration(&mut self, v: bool) {
1060        self.local_transport_params.disable_active_migration = v;
1061    }
1062
1063    /// Sets the congestion control algorithm used.
1064    ///
1065    /// The default value is `CongestionControlAlgorithm::CUBIC`.
1066    pub fn set_cc_algorithm(&mut self, algo: CongestionControlAlgorithm) {
1067        self.cc_algorithm = algo;
1068    }
1069
1070    /// Sets custom BBR settings.
1071    ///
1072    /// This API is experimental and will be removed in the future.
1073    ///
1074    /// Currently this only applies if cc_algorithm is
1075    /// `CongestionControlAlgorithm::Bbr2Gcongestion` is set.
1076    ///
1077    /// The default value is `None`.
1078    #[cfg(feature = "internal")]
1079    #[doc(hidden)]
1080    pub fn set_custom_bbr_params(&mut self, custom_bbr_settings: BbrParams) {
1081        self.custom_bbr_params = Some(custom_bbr_settings);
1082    }
1083
1084    /// Sets the congestion control algorithm used by string.
1085    ///
1086    /// The default value is `cubic`. On error `Error::CongestionControl`
1087    /// will be returned.
1088    ///
1089    /// ## Examples:
1090    ///
1091    /// ```
1092    /// # let mut config = quiche::Config::new(0xbabababa)?;
1093    /// config.set_cc_algorithm_name("reno");
1094    /// # Ok::<(), quiche::Error>(())
1095    /// ```
1096    pub fn set_cc_algorithm_name(&mut self, name: &str) -> Result<()> {
1097        self.cc_algorithm = CongestionControlAlgorithm::from_str(name)?;
1098
1099        Ok(())
1100    }
1101
1102    /// Sets initial congestion window size in terms of packet count.
1103    ///
1104    /// The default value is 10.
1105    pub fn set_initial_congestion_window_packets(&mut self, packets: usize) {
1106        self.initial_congestion_window_packets = packets;
1107    }
1108
1109    /// Configure whether to enable relaxed loss detection on spurious loss.
1110    ///
1111    /// The default value is false.
1112    pub fn set_enable_relaxed_loss_threshold(&mut self, enable: bool) {
1113        self.enable_relaxed_loss_threshold = enable;
1114    }
1115
1116    /// Configures whether to enable HyStart++.
1117    ///
1118    /// The default value is `true`.
1119    pub fn enable_hystart(&mut self, v: bool) {
1120        self.hystart = v;
1121    }
1122
1123    /// Configures whether to enable pacing.
1124    ///
1125    /// The default value is `true`.
1126    pub fn enable_pacing(&mut self, v: bool) {
1127        self.pacing = v;
1128    }
1129
1130    /// Sets the max value for pacing rate.
1131    ///
1132    /// By default pacing rate is not limited.
1133    pub fn set_max_pacing_rate(&mut self, v: u64) {
1134        self.max_pacing_rate = Some(v);
1135    }
1136
1137    /// Configures whether to enable receiving DATAGRAM frames.
1138    ///
1139    /// When enabled, the `max_datagram_frame_size` transport parameter is set
1140    /// to 65536 as recommended by draft-ietf-quic-datagram-01.
1141    ///
1142    /// The default is `false`.
1143    pub fn enable_dgram(
1144        &mut self, enabled: bool, recv_queue_len: usize, send_queue_len: usize,
1145    ) {
1146        self.local_transport_params.max_datagram_frame_size = if enabled {
1147            Some(MAX_DGRAM_FRAME_SIZE)
1148        } else {
1149            None
1150        };
1151        self.dgram_recv_max_queue_len = recv_queue_len;
1152        self.dgram_send_max_queue_len = send_queue_len;
1153    }
1154
1155    /// Configures the max number of queued received PATH_CHALLENGE frames.
1156    ///
1157    /// When an endpoint receives a PATH_CHALLENGE frame and the queue is full,
1158    /// the frame is discarded.
1159    ///
1160    /// The default is 3.
1161    pub fn set_path_challenge_recv_max_queue_len(&mut self, queue_len: usize) {
1162        self.path_challenge_recv_max_queue_len = queue_len;
1163    }
1164
1165    /// Sets the maximum size of the connection window.
1166    ///
1167    /// The default value is MAX_CONNECTION_WINDOW (24MBytes).
1168    pub fn set_max_connection_window(&mut self, v: u64) {
1169        self.max_connection_window = v;
1170    }
1171
1172    /// Sets the maximum size of the stream window.
1173    ///
1174    /// The default value is MAX_STREAM_WINDOW (16MBytes).
1175    pub fn set_max_stream_window(&mut self, v: u64) {
1176        self.max_stream_window = v;
1177    }
1178
1179    /// Sets the initial stateless reset token.
1180    ///
1181    /// This value is only advertised by servers. Setting a stateless retry
1182    /// token as a client has no effect on the connection.
1183    ///
1184    /// The default value is `None`.
1185    pub fn set_stateless_reset_token(&mut self, v: Option<u128>) {
1186        self.local_transport_params.stateless_reset_token = v;
1187    }
1188
1189    /// Sets whether the QUIC connection should avoid reusing DCIDs over
1190    /// different paths.
1191    ///
1192    /// When set to `true`, it ensures that a destination Connection ID is never
1193    /// reused on different paths. Such behaviour may lead to connection stall
1194    /// if the peer performs a non-voluntary migration (e.g., NAT rebinding) and
1195    /// does not provide additional destination Connection IDs to handle such
1196    /// event.
1197    ///
1198    /// The default value is `false`.
1199    pub fn set_disable_dcid_reuse(&mut self, v: bool) {
1200        self.disable_dcid_reuse = v;
1201    }
1202
1203    /// Enables tracking unknown transport parameters.
1204    ///
1205    /// Specify the maximum number of bytes used to track unknown transport
1206    /// parameters. The size includes the identifier and its value. If storing a
1207    /// transport parameter would cause the limit to be exceeded, it is quietly
1208    /// dropped.
1209    ///
1210    /// The default is that the feature is disabled.
1211    pub fn enable_track_unknown_transport_parameters(&mut self, size: usize) {
1212        self.track_unknown_transport_params = Some(size);
1213    }
1214}
1215
1216/// Tracks the health of the tx_buffered value.
1217#[derive(Clone, Copy, Debug, Default, PartialEq)]
1218pub enum TxBufferTrackingState {
1219    /// The send buffer is in a good state
1220    #[default]
1221    Ok,
1222    /// The send buffer is in an inconsistent state, which could lead to
1223    /// connection stalls or excess buffering due to bugs we haven't
1224    /// tracked down yet.
1225    Inconsistent,
1226}
1227
1228/// A QUIC connection.
1229pub struct Connection<F = DefaultBufFactory>
1230where
1231    F: BufFactory,
1232{
1233    /// QUIC wire version used for the connection.
1234    version: u32,
1235
1236    /// Connection Identifiers.
1237    ids: cid::ConnectionIdentifiers,
1238
1239    /// Unique opaque ID for the connection that can be used for logging.
1240    trace_id: String,
1241
1242    /// Packet number spaces.
1243    pkt_num_spaces: [packet::PktNumSpace; packet::Epoch::count()],
1244
1245    /// The crypto context.
1246    crypto_ctx: [packet::CryptoContext; packet::Epoch::count()],
1247
1248    /// Next packet number.
1249    next_pkt_num: u64,
1250
1251    // TODO
1252    // combine with `next_pkt_num`
1253    /// Track the packet skip context
1254    pkt_num_manager: packet::PktNumManager,
1255
1256    /// Peer's transport parameters.
1257    peer_transport_params: TransportParams,
1258
1259    /// If tracking unknown transport parameters from a peer, how much space to
1260    /// use in bytes.
1261    peer_transport_params_track_unknown: Option<usize>,
1262
1263    /// Local transport parameters.
1264    local_transport_params: TransportParams,
1265
1266    /// TLS handshake state.
1267    handshake: tls::Handshake,
1268
1269    /// Serialized TLS session buffer.
1270    ///
1271    /// This field is populated when a new session ticket is processed on the
1272    /// client. On the server this is empty.
1273    session: Option<Vec<u8>>,
1274
1275    /// The configuration for recovery.
1276    recovery_config: recovery::RecoveryConfig,
1277
1278    /// The path manager.
1279    paths: path::PathMap,
1280
1281    /// PATH_CHALLENGE receive queue max length.
1282    path_challenge_recv_max_queue_len: usize,
1283
1284    /// Total number of received PATH_CHALLENGE frames.
1285    path_challenge_rx_count: u64,
1286
1287    /// List of supported application protocols.
1288    application_protos: Vec<Vec<u8>>,
1289
1290    /// Total number of received packets.
1291    recv_count: usize,
1292
1293    /// Total number of sent packets.
1294    sent_count: usize,
1295
1296    /// Total number of lost packets.
1297    lost_count: usize,
1298
1299    /// Total number of lost packets that were later acked.
1300    spurious_lost_count: usize,
1301
1302    /// Total number of packets sent with data retransmitted.
1303    retrans_count: usize,
1304
1305    /// Total number of sent DATAGRAM frames.
1306    dgram_sent_count: usize,
1307
1308    /// Total number of received DATAGRAM frames.
1309    dgram_recv_count: usize,
1310
1311    /// Total number of bytes received from the peer.
1312    rx_data: u64,
1313
1314    /// Receiver flow controller.
1315    flow_control: flowcontrol::FlowControl,
1316
1317    /// Whether we send MAX_DATA frame.
1318    almost_full: bool,
1319
1320    /// Number of stream data bytes that can be buffered.
1321    tx_cap: usize,
1322
1323    /// The send capacity factor.
1324    tx_cap_factor: f64,
1325
1326    /// Number of bytes buffered in the send buffer.
1327    tx_buffered: usize,
1328
1329    /// Tracks the health of tx_buffered.
1330    tx_buffered_state: TxBufferTrackingState,
1331
1332    /// Total number of bytes sent to the peer.
1333    tx_data: u64,
1334
1335    /// Peer's flow control limit for the connection.
1336    max_tx_data: u64,
1337
1338    /// Last tx_data before running a full send() loop.
1339    last_tx_data: u64,
1340
1341    /// Total number of bytes retransmitted over the connection.
1342    /// This counts only STREAM and CRYPTO data.
1343    stream_retrans_bytes: u64,
1344
1345    /// Total number of bytes sent over the connection.
1346    sent_bytes: u64,
1347
1348    /// Total number of bytes received over the connection.
1349    recv_bytes: u64,
1350
1351    /// Total number of bytes sent acked over the connection.
1352    acked_bytes: u64,
1353
1354    /// Total number of bytes sent lost over the connection.
1355    lost_bytes: u64,
1356
1357    /// Streams map, indexed by stream ID.
1358    streams: stream::StreamMap<F>,
1359
1360    /// Peer's original destination connection ID. Used by the client to
1361    /// validate the server's transport parameter.
1362    odcid: Option<ConnectionId<'static>>,
1363
1364    /// Peer's retry source connection ID. Used by the client during stateless
1365    /// retry to validate the server's transport parameter.
1366    rscid: Option<ConnectionId<'static>>,
1367
1368    /// Received address verification token.
1369    token: Option<Vec<u8>>,
1370
1371    /// Error code and reason to be sent to the peer in a CONNECTION_CLOSE
1372    /// frame.
1373    local_error: Option<ConnectionError>,
1374
1375    /// Error code and reason received from the peer in a CONNECTION_CLOSE
1376    /// frame.
1377    peer_error: Option<ConnectionError>,
1378
1379    /// The connection-level limit at which send blocking occurred.
1380    blocked_limit: Option<u64>,
1381
1382    /// Idle timeout expiration time.
1383    idle_timer: Option<Instant>,
1384
1385    /// Draining timeout expiration time.
1386    draining_timer: Option<Instant>,
1387
1388    /// List of raw packets that were received before they could be decrypted.
1389    undecryptable_pkts: VecDeque<(Vec<u8>, RecvInfo)>,
1390
1391    /// The negotiated ALPN protocol.
1392    alpn: Vec<u8>,
1393
1394    /// Whether this is a server-side connection.
1395    is_server: bool,
1396
1397    /// Whether the initial secrets have been derived.
1398    derived_initial_secrets: bool,
1399
1400    /// Whether a version negotiation packet has already been received. Only
1401    /// relevant for client connections.
1402    did_version_negotiation: bool,
1403
1404    /// Whether stateless retry has been performed.
1405    did_retry: bool,
1406
1407    /// Whether the peer already updated its connection ID.
1408    got_peer_conn_id: bool,
1409
1410    /// Whether the peer verified our initial address.
1411    peer_verified_initial_address: bool,
1412
1413    /// Whether the peer's transport parameters were parsed.
1414    parsed_peer_transport_params: bool,
1415
1416    /// Whether the connection handshake has been completed.
1417    handshake_completed: bool,
1418
1419    /// Whether the HANDSHAKE_DONE frame has been sent.
1420    handshake_done_sent: bool,
1421
1422    /// Whether the HANDSHAKE_DONE frame has been acked.
1423    handshake_done_acked: bool,
1424
1425    /// Whether the connection handshake has been confirmed.
1426    handshake_confirmed: bool,
1427
1428    /// Key phase bit used for outgoing protected packets.
1429    key_phase: bool,
1430
1431    /// Whether an ack-eliciting packet has been sent since last receiving a
1432    /// packet.
1433    ack_eliciting_sent: bool,
1434
1435    /// Whether the connection is closed.
1436    closed: bool,
1437
1438    /// Whether the connection was timed out.
1439    timed_out: bool,
1440
1441    /// Whether to send GREASE.
1442    grease: bool,
1443
1444    /// TLS keylog writer.
1445    keylog: Option<Box<dyn std::io::Write + Send + Sync>>,
1446
1447    #[cfg(feature = "qlog")]
1448    qlog: QlogInfo,
1449
1450    /// DATAGRAM queues.
1451    dgram_recv_queue: dgram::DatagramQueue,
1452    dgram_send_queue: dgram::DatagramQueue,
1453
1454    /// Whether to emit DATAGRAM frames in the next packet.
1455    emit_dgram: bool,
1456
1457    /// Whether the connection should prevent from reusing destination
1458    /// Connection IDs when the peer migrates.
1459    disable_dcid_reuse: bool,
1460
1461    /// The number of streams reset by local.
1462    reset_stream_local_count: u64,
1463
1464    /// The number of streams stopped by local.
1465    stopped_stream_local_count: u64,
1466
1467    /// The number of streams reset by remote.
1468    reset_stream_remote_count: u64,
1469
1470    /// The number of streams stopped by remote.
1471    stopped_stream_remote_count: u64,
1472
1473    /// The number of DATA_BLOCKED frames sent due to hitting the connection
1474    /// flow control limit.
1475    data_blocked_sent_count: u64,
1476
1477    /// The number of STREAM_DATA_BLOCKED frames sent due to a stream hitting
1478    /// the stream flow control limit.
1479    stream_data_blocked_sent_count: u64,
1480
1481    /// The number of DATA_BLOCKED frames received from the remote endpoint.
1482    data_blocked_recv_count: u64,
1483
1484    /// The number of STREAM_DATA_BLOCKED frames received from the remote
1485    /// endpoint.
1486    stream_data_blocked_recv_count: u64,
1487
1488    /// The anti-amplification limit factor.
1489    max_amplification_factor: usize,
1490}
1491
1492/// Creates a new server-side connection.
1493///
1494/// The `scid` parameter represents the server's source connection ID, while
1495/// the optional `odcid` parameter represents the original destination ID the
1496/// client sent before a stateless retry (this is only required when using
1497/// the [`retry()`] function).
1498///
1499/// [`retry()`]: fn.retry.html
1500///
1501/// ## Examples:
1502///
1503/// ```no_run
1504/// # let mut config = quiche::Config::new(0xbabababa)?;
1505/// # let scid = quiche::ConnectionId::from_ref(&[0xba; 16]);
1506/// # let local = "127.0.0.1:0".parse().unwrap();
1507/// # let peer = "127.0.0.1:1234".parse().unwrap();
1508/// let conn = quiche::accept(&scid, None, local, peer, &mut config)?;
1509/// # Ok::<(), quiche::Error>(())
1510/// ```
1511#[inline]
1512pub fn accept(
1513    scid: &ConnectionId, odcid: Option<&ConnectionId>, local: SocketAddr,
1514    peer: SocketAddr, config: &mut Config,
1515) -> Result<Connection> {
1516    let conn = Connection::new(scid, odcid, local, peer, config, true)?;
1517
1518    Ok(conn)
1519}
1520
1521/// Creates a new server-side connection, with a custom buffer generation
1522/// method.
1523///
1524/// The buffers generated can be anything that can be drereferenced as a byte
1525/// slice. See [`accept`] and [`BufFactory`] for more info.
1526#[inline]
1527pub fn accept_with_buf_factory<F: BufFactory>(
1528    scid: &ConnectionId, odcid: Option<&ConnectionId>, local: SocketAddr,
1529    peer: SocketAddr, config: &mut Config,
1530) -> Result<Connection<F>> {
1531    let conn = Connection::new(scid, odcid, local, peer, config, true)?;
1532
1533    Ok(conn)
1534}
1535
1536/// Creates a new client-side connection.
1537///
1538/// The `scid` parameter is used as the connection's source connection ID,
1539/// while the optional `server_name` parameter is used to verify the peer's
1540/// certificate.
1541///
1542/// ## Examples:
1543///
1544/// ```no_run
1545/// # let mut config = quiche::Config::new(0xbabababa)?;
1546/// # let server_name = "quic.tech";
1547/// # let scid = quiche::ConnectionId::from_ref(&[0xba; 16]);
1548/// # let local = "127.0.0.1:4321".parse().unwrap();
1549/// # let peer = "127.0.0.1:1234".parse().unwrap();
1550/// let conn =
1551///     quiche::connect(Some(&server_name), &scid, local, peer, &mut config)?;
1552/// # Ok::<(), quiche::Error>(())
1553/// ```
1554#[inline]
1555pub fn connect(
1556    server_name: Option<&str>, scid: &ConnectionId, local: SocketAddr,
1557    peer: SocketAddr, config: &mut Config,
1558) -> Result<Connection> {
1559    let mut conn = Connection::new(scid, None, local, peer, config, false)?;
1560
1561    if let Some(server_name) = server_name {
1562        conn.handshake.set_host_name(server_name)?;
1563    }
1564
1565    Ok(conn)
1566}
1567
1568/// Creates a new client-side connection, with a custom buffer generation
1569/// method.
1570///
1571/// The buffers generated can be anything that can be drereferenced as a byte
1572/// slice. See [`connect`] and [`BufFactory`] for more info.
1573#[inline]
1574pub fn connect_with_buffer_factory<F: BufFactory>(
1575    server_name: Option<&str>, scid: &ConnectionId, local: SocketAddr,
1576    peer: SocketAddr, config: &mut Config,
1577) -> Result<Connection<F>> {
1578    let mut conn = Connection::new(scid, None, local, peer, config, false)?;
1579
1580    if let Some(server_name) = server_name {
1581        conn.handshake.set_host_name(server_name)?;
1582    }
1583
1584    Ok(conn)
1585}
1586
1587/// Writes a version negotiation packet.
1588///
1589/// The `scid` and `dcid` parameters are the source connection ID and the
1590/// destination connection ID extracted from the received client's Initial
1591/// packet that advertises an unsupported version.
1592///
1593/// ## Examples:
1594///
1595/// ```no_run
1596/// # let mut buf = [0; 512];
1597/// # let mut out = [0; 512];
1598/// # let socket = std::net::UdpSocket::bind("127.0.0.1:0").unwrap();
1599/// let (len, src) = socket.recv_from(&mut buf).unwrap();
1600///
1601/// let hdr =
1602///     quiche::Header::from_slice(&mut buf[..len], quiche::MAX_CONN_ID_LEN)?;
1603///
1604/// if hdr.version != quiche::PROTOCOL_VERSION {
1605///     let len = quiche::negotiate_version(&hdr.scid, &hdr.dcid, &mut out)?;
1606///     socket.send_to(&out[..len], &src).unwrap();
1607/// }
1608/// # Ok::<(), quiche::Error>(())
1609/// ```
1610#[inline]
1611pub fn negotiate_version(
1612    scid: &ConnectionId, dcid: &ConnectionId, out: &mut [u8],
1613) -> Result<usize> {
1614    packet::negotiate_version(scid, dcid, out)
1615}
1616
1617/// Writes a stateless retry packet.
1618///
1619/// The `scid` and `dcid` parameters are the source connection ID and the
1620/// destination connection ID extracted from the received client's Initial
1621/// packet, while `new_scid` is the server's new source connection ID and
1622/// `token` is the address validation token the client needs to echo back.
1623///
1624/// The application is responsible for generating the address validation
1625/// token to be sent to the client, and verifying tokens sent back by the
1626/// client. The generated token should include the `dcid` parameter, such
1627/// that it can be later extracted from the token and passed to the
1628/// [`accept()`] function as its `odcid` parameter.
1629///
1630/// [`accept()`]: fn.accept.html
1631///
1632/// ## Examples:
1633///
1634/// ```no_run
1635/// # let mut config = quiche::Config::new(0xbabababa)?;
1636/// # let mut buf = [0; 512];
1637/// # let mut out = [0; 512];
1638/// # let scid = quiche::ConnectionId::from_ref(&[0xba; 16]);
1639/// # let socket = std::net::UdpSocket::bind("127.0.0.1:0").unwrap();
1640/// # let local = socket.local_addr().unwrap();
1641/// # fn mint_token(hdr: &quiche::Header, src: &std::net::SocketAddr) -> Vec<u8> {
1642/// #     vec![]
1643/// # }
1644/// # fn validate_token<'a>(src: &std::net::SocketAddr, token: &'a [u8]) -> Option<quiche::ConnectionId<'a>> {
1645/// #     None
1646/// # }
1647/// let (len, peer) = socket.recv_from(&mut buf).unwrap();
1648///
1649/// let hdr = quiche::Header::from_slice(&mut buf[..len], quiche::MAX_CONN_ID_LEN)?;
1650///
1651/// let token = hdr.token.as_ref().unwrap();
1652///
1653/// // No token sent by client, create a new one.
1654/// if token.is_empty() {
1655///     let new_token = mint_token(&hdr, &peer);
1656///
1657///     let len = quiche::retry(
1658///         &hdr.scid, &hdr.dcid, &scid, &new_token, hdr.version, &mut out,
1659///     )?;
1660///
1661///     socket.send_to(&out[..len], &peer).unwrap();
1662///     return Ok(());
1663/// }
1664///
1665/// // Client sent token, validate it.
1666/// let odcid = validate_token(&peer, token);
1667///
1668/// if odcid.is_none() {
1669///     // Invalid address validation token.
1670///     return Ok(());
1671/// }
1672///
1673/// let conn = quiche::accept(&scid, odcid.as_ref(), local, peer, &mut config)?;
1674/// # Ok::<(), quiche::Error>(())
1675/// ```
1676#[inline]
1677pub fn retry(
1678    scid: &ConnectionId, dcid: &ConnectionId, new_scid: &ConnectionId,
1679    token: &[u8], version: u32, out: &mut [u8],
1680) -> Result<usize> {
1681    packet::retry(scid, dcid, new_scid, token, version, out)
1682}
1683
1684/// Returns true if the given protocol version is supported.
1685#[inline]
1686pub fn version_is_supported(version: u32) -> bool {
1687    matches!(version, PROTOCOL_VERSION_V1)
1688}
1689
1690/// Pushes a frame to the output packet if there is enough space.
1691///
1692/// Returns `true` on success, `false` otherwise. In case of failure it means
1693/// there is no room to add the frame in the packet. You may retry to add the
1694/// frame later.
1695macro_rules! push_frame_to_pkt {
1696    ($out:expr, $frames:expr, $frame:expr, $left:expr) => {{
1697        if $frame.wire_len() <= $left {
1698            $left -= $frame.wire_len();
1699
1700            $frame.to_bytes(&mut $out)?;
1701
1702            $frames.push($frame);
1703
1704            true
1705        } else {
1706            false
1707        }
1708    }};
1709}
1710
1711/// Executes the provided body if the qlog feature is enabled, quiche has been
1712/// configured with a log writer, the event's importance is within the
1713/// configured level.
1714macro_rules! qlog_with_type {
1715    ($ty:expr, $qlog:expr, $qlog_streamer_ref:ident, $body:block) => {{
1716        #[cfg(feature = "qlog")]
1717        {
1718            if EventImportance::from($ty).is_contained_in(&$qlog.level) {
1719                if let Some($qlog_streamer_ref) = &mut $qlog.streamer {
1720                    $body
1721                }
1722            }
1723        }
1724    }};
1725}
1726
1727#[cfg(feature = "qlog")]
1728const QLOG_PARAMS_SET: EventType =
1729    EventType::TransportEventType(TransportEventType::ParametersSet);
1730
1731#[cfg(feature = "qlog")]
1732const QLOG_PACKET_RX: EventType =
1733    EventType::TransportEventType(TransportEventType::PacketReceived);
1734
1735#[cfg(feature = "qlog")]
1736const QLOG_PACKET_TX: EventType =
1737    EventType::TransportEventType(TransportEventType::PacketSent);
1738
1739#[cfg(feature = "qlog")]
1740const QLOG_DATA_MV: EventType =
1741    EventType::TransportEventType(TransportEventType::DataMoved);
1742
1743#[cfg(feature = "qlog")]
1744const QLOG_METRICS: EventType =
1745    EventType::RecoveryEventType(RecoveryEventType::MetricsUpdated);
1746
1747#[cfg(feature = "qlog")]
1748const QLOG_CONNECTION_CLOSED: EventType =
1749    EventType::ConnectivityEventType(ConnectivityEventType::ConnectionClosed);
1750
1751#[cfg(feature = "qlog")]
1752struct QlogInfo {
1753    streamer: Option<qlog::streamer::QlogStreamer>,
1754    logged_peer_params: bool,
1755    level: EventImportance,
1756}
1757
1758#[cfg(feature = "qlog")]
1759impl Default for QlogInfo {
1760    fn default() -> Self {
1761        QlogInfo {
1762            streamer: None,
1763            logged_peer_params: false,
1764            level: EventImportance::Base,
1765        }
1766    }
1767}
1768
1769impl<F: BufFactory> Connection<F> {
1770    fn new(
1771        scid: &ConnectionId, odcid: Option<&ConnectionId>, local: SocketAddr,
1772        peer: SocketAddr, config: &mut Config, is_server: bool,
1773    ) -> Result<Connection<F>> {
1774        let tls = config.tls_ctx.new_handshake()?;
1775        Connection::with_tls(scid, odcid, local, peer, config, tls, is_server)
1776    }
1777
1778    fn with_tls(
1779        scid: &ConnectionId, odcid: Option<&ConnectionId>, local: SocketAddr,
1780        peer: SocketAddr, config: &Config, tls: tls::Handshake, is_server: bool,
1781    ) -> Result<Connection<F>> {
1782        let max_rx_data = config.local_transport_params.initial_max_data;
1783
1784        let scid_as_hex: Vec<String> =
1785            scid.iter().map(|b| format!("{b:02x}")).collect();
1786
1787        let reset_token = if is_server {
1788            config.local_transport_params.stateless_reset_token
1789        } else {
1790            None
1791        };
1792
1793        let recovery_config = recovery::RecoveryConfig::from_config(config);
1794
1795        let mut path = path::Path::new(
1796            local,
1797            peer,
1798            &recovery_config,
1799            config.path_challenge_recv_max_queue_len,
1800            true,
1801            Some(config),
1802        );
1803
1804        // If we did stateless retry assume the peer's address is verified.
1805        path.verified_peer_address = odcid.is_some();
1806        // Assume clients validate the server's address implicitly.
1807        path.peer_verified_local_address = is_server;
1808
1809        // Do not allocate more than the number of active CIDs.
1810        let paths = path::PathMap::new(
1811            path,
1812            config.local_transport_params.active_conn_id_limit as usize,
1813            is_server,
1814        );
1815
1816        let active_path_id = paths.get_active_path_id()?;
1817
1818        let ids = cid::ConnectionIdentifiers::new(
1819            config.local_transport_params.active_conn_id_limit as usize,
1820            scid,
1821            active_path_id,
1822            reset_token,
1823        );
1824
1825        let mut conn = Connection {
1826            version: config.version,
1827
1828            ids,
1829
1830            trace_id: scid_as_hex.join(""),
1831
1832            pkt_num_spaces: [
1833                packet::PktNumSpace::new(),
1834                packet::PktNumSpace::new(),
1835                packet::PktNumSpace::new(),
1836            ],
1837
1838            crypto_ctx: [
1839                packet::CryptoContext::new(),
1840                packet::CryptoContext::new(),
1841                packet::CryptoContext::new(),
1842            ],
1843
1844            next_pkt_num: 0,
1845
1846            pkt_num_manager: packet::PktNumManager::new(),
1847
1848            peer_transport_params: TransportParams::default(),
1849
1850            peer_transport_params_track_unknown: config
1851                .track_unknown_transport_params,
1852
1853            local_transport_params: config.local_transport_params.clone(),
1854
1855            handshake: tls,
1856
1857            session: None,
1858
1859            recovery_config,
1860
1861            paths,
1862            path_challenge_recv_max_queue_len: config
1863                .path_challenge_recv_max_queue_len,
1864            path_challenge_rx_count: 0,
1865
1866            application_protos: config.application_protos.clone(),
1867
1868            recv_count: 0,
1869            sent_count: 0,
1870            lost_count: 0,
1871            spurious_lost_count: 0,
1872            retrans_count: 0,
1873            dgram_sent_count: 0,
1874            dgram_recv_count: 0,
1875            sent_bytes: 0,
1876            recv_bytes: 0,
1877            acked_bytes: 0,
1878            lost_bytes: 0,
1879
1880            rx_data: 0,
1881            flow_control: flowcontrol::FlowControl::new(
1882                max_rx_data,
1883                cmp::min(max_rx_data / 2 * 3, DEFAULT_CONNECTION_WINDOW),
1884                config.max_connection_window,
1885            ),
1886            almost_full: false,
1887
1888            tx_cap: 0,
1889            tx_cap_factor: config.tx_cap_factor,
1890
1891            tx_buffered: 0,
1892            tx_buffered_state: TxBufferTrackingState::Ok,
1893
1894            tx_data: 0,
1895            max_tx_data: 0,
1896            last_tx_data: 0,
1897
1898            stream_retrans_bytes: 0,
1899
1900            streams: stream::StreamMap::new(
1901                config.local_transport_params.initial_max_streams_bidi,
1902                config.local_transport_params.initial_max_streams_uni,
1903                config.max_stream_window,
1904            ),
1905
1906            odcid: None,
1907
1908            rscid: None,
1909
1910            token: None,
1911
1912            local_error: None,
1913
1914            peer_error: None,
1915
1916            blocked_limit: None,
1917
1918            idle_timer: None,
1919
1920            draining_timer: None,
1921
1922            undecryptable_pkts: VecDeque::new(),
1923
1924            alpn: Vec::new(),
1925
1926            is_server,
1927
1928            derived_initial_secrets: false,
1929
1930            did_version_negotiation: false,
1931
1932            did_retry: false,
1933
1934            got_peer_conn_id: false,
1935
1936            // Assume clients validate the server's address implicitly.
1937            peer_verified_initial_address: is_server,
1938
1939            parsed_peer_transport_params: false,
1940
1941            handshake_completed: false,
1942
1943            handshake_done_sent: false,
1944            handshake_done_acked: false,
1945
1946            handshake_confirmed: false,
1947
1948            key_phase: false,
1949
1950            ack_eliciting_sent: false,
1951
1952            closed: false,
1953
1954            timed_out: false,
1955
1956            grease: config.grease,
1957
1958            keylog: None,
1959
1960            #[cfg(feature = "qlog")]
1961            qlog: Default::default(),
1962
1963            dgram_recv_queue: dgram::DatagramQueue::new(
1964                config.dgram_recv_max_queue_len,
1965            ),
1966
1967            dgram_send_queue: dgram::DatagramQueue::new(
1968                config.dgram_send_max_queue_len,
1969            ),
1970
1971            emit_dgram: true,
1972
1973            disable_dcid_reuse: config.disable_dcid_reuse,
1974
1975            reset_stream_local_count: 0,
1976            stopped_stream_local_count: 0,
1977            reset_stream_remote_count: 0,
1978            stopped_stream_remote_count: 0,
1979
1980            data_blocked_sent_count: 0,
1981            stream_data_blocked_sent_count: 0,
1982            data_blocked_recv_count: 0,
1983            stream_data_blocked_recv_count: 0,
1984
1985            max_amplification_factor: config.max_amplification_factor,
1986        };
1987
1988        if let Some(odcid) = odcid {
1989            conn.local_transport_params
1990                .original_destination_connection_id = Some(odcid.to_vec().into());
1991
1992            conn.local_transport_params.retry_source_connection_id =
1993                Some(conn.ids.get_scid(0)?.cid.to_vec().into());
1994
1995            conn.did_retry = true;
1996        }
1997
1998        conn.local_transport_params.initial_source_connection_id =
1999            Some(conn.ids.get_scid(0)?.cid.to_vec().into());
2000
2001        conn.handshake.init(is_server)?;
2002
2003        conn.handshake
2004            .use_legacy_codepoint(config.version != PROTOCOL_VERSION_V1);
2005
2006        conn.encode_transport_params()?;
2007
2008        // Derive initial secrets for the client. We can do this here because
2009        // we already generated the random destination connection ID.
2010        if !is_server {
2011            let mut dcid = [0; 16];
2012            rand::rand_bytes(&mut dcid[..]);
2013
2014            let (aead_open, aead_seal) = crypto::derive_initial_key_material(
2015                &dcid,
2016                conn.version,
2017                conn.is_server,
2018                false,
2019            )?;
2020
2021            let reset_token = conn.peer_transport_params.stateless_reset_token;
2022            conn.set_initial_dcid(
2023                dcid.to_vec().into(),
2024                reset_token,
2025                active_path_id,
2026            )?;
2027
2028            conn.crypto_ctx[packet::Epoch::Initial].crypto_open = Some(aead_open);
2029            conn.crypto_ctx[packet::Epoch::Initial].crypto_seal = Some(aead_seal);
2030
2031            conn.derived_initial_secrets = true;
2032        }
2033
2034        Ok(conn)
2035    }
2036
2037    /// Sets keylog output to the designated [`Writer`].
2038    ///
2039    /// This needs to be called as soon as the connection is created, to avoid
2040    /// missing some early logs.
2041    ///
2042    /// [`Writer`]: https://doc.rust-lang.org/std/io/trait.Write.html
2043    #[inline]
2044    pub fn set_keylog(&mut self, writer: Box<dyn std::io::Write + Send + Sync>) {
2045        self.keylog = Some(writer);
2046    }
2047
2048    /// Sets qlog output to the designated [`Writer`].
2049    ///
2050    /// Only events included in `QlogLevel::Base` are written. The serialization
2051    /// format is JSON-SEQ.
2052    ///
2053    /// This needs to be called as soon as the connection is created, to avoid
2054    /// missing some early logs.
2055    ///
2056    /// [`Writer`]: https://doc.rust-lang.org/std/io/trait.Write.html
2057    #[cfg(feature = "qlog")]
2058    #[cfg_attr(docsrs, doc(cfg(feature = "qlog")))]
2059    pub fn set_qlog(
2060        &mut self, writer: Box<dyn std::io::Write + Send + Sync>, title: String,
2061        description: String,
2062    ) {
2063        self.set_qlog_with_level(writer, title, description, QlogLevel::Base)
2064    }
2065
2066    /// Sets qlog output to the designated [`Writer`].
2067    ///
2068    /// Only qlog events included in the specified `QlogLevel` are written. The
2069    /// serialization format is JSON-SEQ.
2070    ///
2071    /// This needs to be called as soon as the connection is created, to avoid
2072    /// missing some early logs.
2073    ///
2074    /// [`Writer`]: https://doc.rust-lang.org/std/io/trait.Write.html
2075    #[cfg(feature = "qlog")]
2076    #[cfg_attr(docsrs, doc(cfg(feature = "qlog")))]
2077    pub fn set_qlog_with_level(
2078        &mut self, writer: Box<dyn std::io::Write + Send + Sync>, title: String,
2079        description: String, qlog_level: QlogLevel,
2080    ) {
2081        let vp = if self.is_server {
2082            qlog::VantagePointType::Server
2083        } else {
2084            qlog::VantagePointType::Client
2085        };
2086
2087        let level = match qlog_level {
2088            QlogLevel::Core => EventImportance::Core,
2089
2090            QlogLevel::Base => EventImportance::Base,
2091
2092            QlogLevel::Extra => EventImportance::Extra,
2093        };
2094
2095        self.qlog.level = level;
2096
2097        let trace = qlog::TraceSeq::new(
2098            qlog::VantagePoint {
2099                name: None,
2100                ty: vp,
2101                flow: None,
2102            },
2103            Some(title.to_string()),
2104            Some(description.to_string()),
2105            Some(qlog::Configuration {
2106                time_offset: Some(0.0),
2107                original_uris: None,
2108            }),
2109            None,
2110        );
2111
2112        let mut streamer = qlog::streamer::QlogStreamer::new(
2113            qlog::QLOG_VERSION.to_string(),
2114            Some(title),
2115            Some(description),
2116            None,
2117            Instant::now(),
2118            trace,
2119            self.qlog.level,
2120            writer,
2121        );
2122
2123        streamer.start_log().ok();
2124
2125        let ev_data = self
2126            .local_transport_params
2127            .to_qlog(TransportOwner::Local, self.handshake.cipher());
2128
2129        // This event occurs very early, so just mark the relative time as 0.0.
2130        streamer.add_event(Event::with_time(0.0, ev_data)).ok();
2131
2132        self.qlog.streamer = Some(streamer);
2133    }
2134
2135    /// Returns a mutable reference to the QlogStreamer, if it exists.
2136    #[cfg(feature = "qlog")]
2137    #[cfg_attr(docsrs, doc(cfg(feature = "qlog")))]
2138    pub fn qlog_streamer(&mut self) -> Option<&mut qlog::streamer::QlogStreamer> {
2139        self.qlog.streamer.as_mut()
2140    }
2141
2142    /// Configures the given session for resumption.
2143    ///
2144    /// On the client, this can be used to offer the given serialized session,
2145    /// as returned by [`session()`], for resumption.
2146    ///
2147    /// This must only be called immediately after creating a connection, that
2148    /// is, before any packet is sent or received.
2149    ///
2150    /// [`session()`]: struct.Connection.html#method.session
2151    #[inline]
2152    pub fn set_session(&mut self, session: &[u8]) -> Result<()> {
2153        let mut b = octets::Octets::with_slice(session);
2154
2155        let session_len = b.get_u64()? as usize;
2156        let session_bytes = b.get_bytes(session_len)?;
2157
2158        self.handshake.set_session(session_bytes.as_ref())?;
2159
2160        let raw_params_len = b.get_u64()? as usize;
2161        let raw_params_bytes = b.get_bytes(raw_params_len)?;
2162
2163        let peer_params = TransportParams::decode(
2164            raw_params_bytes.as_ref(),
2165            self.is_server,
2166            self.peer_transport_params_track_unknown,
2167        )?;
2168
2169        self.process_peer_transport_params(peer_params)?;
2170
2171        Ok(())
2172    }
2173
2174    /// Sets the `max_idle_timeout` transport parameter, in milliseconds.
2175    ///
2176    /// This must only be called immediately after creating a connection, that
2177    /// is, before any packet is sent or received.
2178    ///
2179    /// The default value is infinite, that is, no timeout is used unless
2180    /// already configured when creating the connection.
2181    pub fn set_max_idle_timeout(&mut self, v: u64) -> Result<()> {
2182        self.local_transport_params.max_idle_timeout =
2183            cmp::min(v, octets::MAX_VAR_INT);
2184
2185        self.encode_transport_params()
2186    }
2187
2188    /// Sets the congestion control algorithm used.
2189    ///
2190    /// This function can only be called inside one of BoringSSL's handshake
2191    /// callbacks, before any packet has been sent. Calling this function any
2192    /// other time will have no effect.
2193    ///
2194    /// See [`Config::set_cc_algorithm()`].
2195    ///
2196    /// [`Config::set_cc_algorithm()`]: struct.Config.html#method.set_cc_algorithm
2197    #[cfg(feature = "boringssl-boring-crate")]
2198    #[cfg_attr(docsrs, doc(cfg(feature = "boringssl-boring-crate")))]
2199    pub fn set_cc_algorithm_in_handshake(
2200        ssl: &mut boring::ssl::SslRef, algo: CongestionControlAlgorithm,
2201    ) -> Result<()> {
2202        let ex_data = tls::ExData::from_ssl_ref(ssl).ok_or(Error::TlsFail)?;
2203
2204        ex_data.recovery_config.cc_algorithm = algo;
2205
2206        Ok(())
2207    }
2208
2209    /// Sets custom BBR settings.
2210    ///
2211    /// This API is experimental and will be removed in the future.
2212    ///
2213    /// Currently this only applies if cc_algorithm is
2214    /// `CongestionControlAlgorithm::Bbr2Gcongestion` is set.
2215    ///
2216    /// This function can only be called inside one of BoringSSL's handshake
2217    /// callbacks, before any packet has been sent. Calling this function any
2218    /// other time will have no effect.
2219    ///
2220    /// See [`Config::set_custom_bbr_settings()`].
2221    ///
2222    /// [`Config::set_custom_bbr_settings()`]: struct.Config.html#method.set_custom_bbr_settings
2223    #[cfg(all(feature = "boringssl-boring-crate", feature = "internal"))]
2224    #[cfg_attr(docsrs, doc(cfg(feature = "boringssl-boring-crate")))]
2225    #[doc(hidden)]
2226    pub fn set_custom_bbr_settings_in_handshake(
2227        ssl: &mut boring::ssl::SslRef, custom_bbr_params: BbrParams,
2228    ) -> Result<()> {
2229        let ex_data = tls::ExData::from_ssl_ref(ssl).ok_or(Error::TlsFail)?;
2230
2231        ex_data.recovery_config.custom_bbr_params = Some(custom_bbr_params);
2232
2233        Ok(())
2234    }
2235
2236    /// Sets the congestion control algorithm used by string.
2237    ///
2238    /// This function can only be called inside one of BoringSSL's handshake
2239    /// callbacks, before any packet has been sent. Calling this function any
2240    /// other time will have no effect.
2241    ///
2242    /// See [`Config::set_cc_algorithm_name()`].
2243    ///
2244    /// [`Config::set_cc_algorithm_name()`]: struct.Config.html#method.set_cc_algorithm_name
2245    #[cfg(feature = "boringssl-boring-crate")]
2246    #[cfg_attr(docsrs, doc(cfg(feature = "boringssl-boring-crate")))]
2247    pub fn set_cc_algorithm_name_in_handshake(
2248        ssl: &mut boring::ssl::SslRef, name: &str,
2249    ) -> Result<()> {
2250        let cc_algo = CongestionControlAlgorithm::from_str(name)?;
2251        Self::set_cc_algorithm_in_handshake(ssl, cc_algo)
2252    }
2253
2254    /// Sets initial congestion window size in terms of packet count.
2255    ///
2256    /// This function can only be called inside one of BoringSSL's handshake
2257    /// callbacks, before any packet has been sent. Calling this function any
2258    /// other time will have no effect.
2259    ///
2260    /// See [`Config::set_initial_congestion_window_packets()`].
2261    ///
2262    /// [`Config::set_initial_congestion_window_packets()`]: struct.Config.html#method.set_initial_congestion_window_packets
2263    #[cfg(feature = "boringssl-boring-crate")]
2264    #[cfg_attr(docsrs, doc(cfg(feature = "boringssl-boring-crate")))]
2265    pub fn set_initial_congestion_window_packets_in_handshake(
2266        ssl: &mut boring::ssl::SslRef, packets: usize,
2267    ) -> Result<()> {
2268        let ex_data = tls::ExData::from_ssl_ref(ssl).ok_or(Error::TlsFail)?;
2269
2270        ex_data.recovery_config.initial_congestion_window_packets = packets;
2271
2272        Ok(())
2273    }
2274
2275    /// Configure whether to enable relaxed loss detection on spurious loss.
2276    ///
2277    /// This function can only be called inside one of BoringSSL's handshake
2278    /// callbacks, before any packet has been sent. Calling this function any
2279    /// other time will have no effect.
2280    ///
2281    /// See [`Config::set_enable_relaxed_loss_threshold()`].
2282    ///
2283    /// [`Config::set_enable_relaxed_loss_threshold()`]: struct.Config.html#method.set_enable_relaxed_loss_threshold
2284    #[cfg(feature = "boringssl-boring-crate")]
2285    #[cfg_attr(docsrs, doc(cfg(feature = "boringssl-boring-crate")))]
2286    pub fn set_enable_relaxed_loss_threshold_in_handshake(
2287        ssl: &mut boring::ssl::SslRef, enable: bool,
2288    ) -> Result<()> {
2289        let ex_data = tls::ExData::from_ssl_ref(ssl).ok_or(Error::TlsFail)?;
2290
2291        ex_data.recovery_config.enable_relaxed_loss_threshold = enable;
2292
2293        Ok(())
2294    }
2295
2296    /// Configures whether to enable HyStart++.
2297    ///
2298    /// This function can only be called inside one of BoringSSL's handshake
2299    /// callbacks, before any packet has been sent. Calling this function any
2300    /// other time will have no effect.
2301    ///
2302    /// See [`Config::enable_hystart()`].
2303    ///
2304    /// [`Config::enable_hystart()`]: struct.Config.html#method.enable_hystart
2305    #[cfg(feature = "boringssl-boring-crate")]
2306    #[cfg_attr(docsrs, doc(cfg(feature = "boringssl-boring-crate")))]
2307    pub fn set_hystart_in_handshake(
2308        ssl: &mut boring::ssl::SslRef, v: bool,
2309    ) -> Result<()> {
2310        let ex_data = tls::ExData::from_ssl_ref(ssl).ok_or(Error::TlsFail)?;
2311
2312        ex_data.recovery_config.hystart = v;
2313
2314        Ok(())
2315    }
2316
2317    /// Configures whether to enable pacing.
2318    ///
2319    /// This function can only be called inside one of BoringSSL's handshake
2320    /// callbacks, before any packet has been sent. Calling this function any
2321    /// other time will have no effect.
2322    ///
2323    /// See [`Config::enable_pacing()`].
2324    ///
2325    /// [`Config::enable_pacing()`]: struct.Config.html#method.enable_pacing
2326    #[cfg(feature = "boringssl-boring-crate")]
2327    #[cfg_attr(docsrs, doc(cfg(feature = "boringssl-boring-crate")))]
2328    pub fn set_pacing_in_handshake(
2329        ssl: &mut boring::ssl::SslRef, v: bool,
2330    ) -> Result<()> {
2331        let ex_data = tls::ExData::from_ssl_ref(ssl).ok_or(Error::TlsFail)?;
2332
2333        ex_data.recovery_config.pacing = v;
2334
2335        Ok(())
2336    }
2337
2338    /// Sets the max value for pacing rate.
2339    ///
2340    /// This function can only be called inside one of BoringSSL's handshake
2341    /// callbacks, before any packet has been sent. Calling this function any
2342    /// other time will have no effect.
2343    ///
2344    /// See [`Config::set_max_pacing_rate()`].
2345    ///
2346    /// [`Config::set_max_pacing_rate()`]: struct.Config.html#method.set_max_pacing_rate
2347    #[cfg(feature = "boringssl-boring-crate")]
2348    #[cfg_attr(docsrs, doc(cfg(feature = "boringssl-boring-crate")))]
2349    pub fn set_max_pacing_rate_in_handshake(
2350        ssl: &mut boring::ssl::SslRef, v: Option<u64>,
2351    ) -> Result<()> {
2352        let ex_data = tls::ExData::from_ssl_ref(ssl).ok_or(Error::TlsFail)?;
2353
2354        ex_data.recovery_config.max_pacing_rate = v;
2355
2356        Ok(())
2357    }
2358
2359    /// Sets the maximum outgoing UDP payload size.
2360    ///
2361    /// This function can only be called inside one of BoringSSL's handshake
2362    /// callbacks, before any packet has been sent. Calling this function any
2363    /// other time will have no effect.
2364    ///
2365    /// See [`Config::set_max_send_udp_payload_size()`].
2366    ///
2367    /// [`Config::set_max_send_udp_payload_size()`]: struct.Config.html#method.set_max_send_udp_payload_size
2368    #[cfg(feature = "boringssl-boring-crate")]
2369    #[cfg_attr(docsrs, doc(cfg(feature = "boringssl-boring-crate")))]
2370    pub fn set_max_send_udp_payload_size_in_handshake(
2371        ssl: &mut boring::ssl::SslRef, v: usize,
2372    ) -> Result<()> {
2373        let ex_data = tls::ExData::from_ssl_ref(ssl).ok_or(Error::TlsFail)?;
2374
2375        ex_data.recovery_config.max_send_udp_payload_size = v;
2376
2377        Ok(())
2378    }
2379
2380    /// Sets the send capacity factor.
2381    ///
2382    /// This function can only be called inside one of BoringSSL's handshake
2383    /// callbacks, before any packet has been sent. Calling this function any
2384    /// other time will have no effect.
2385    ///
2386    /// See [`Config::set_send_capacity_factor()`].
2387    ///
2388    /// [`Config::set_max_send_udp_payload_size()`]: struct.Config.html#method.set_send_capacity_factor
2389    #[cfg(feature = "boringssl-boring-crate")]
2390    #[cfg_attr(docsrs, doc(cfg(feature = "boringssl-boring-crate")))]
2391    pub fn set_send_capacity_factor_in_handshake(
2392        ssl: &mut boring::ssl::SslRef, v: f64,
2393    ) -> Result<()> {
2394        let ex_data = tls::ExData::from_ssl_ref(ssl).ok_or(Error::TlsFail)?;
2395
2396        ex_data.tx_cap_factor = v;
2397
2398        Ok(())
2399    }
2400
2401    /// Configures whether to do path MTU discovery.
2402    ///
2403    /// This function can only be called inside one of BoringSSL's handshake
2404    /// callbacks, before any packet has been sent. Calling this function any
2405    /// other time will have no effect.
2406    ///
2407    /// See [`Config::discover_pmtu()`].
2408    ///
2409    /// [`Config::discover_pmtu()`]: struct.Config.html#method.discover_pmtu
2410    #[cfg(feature = "boringssl-boring-crate")]
2411    #[cfg_attr(docsrs, doc(cfg(feature = "boringssl-boring-crate")))]
2412    pub fn set_discover_pmtu_in_handshake(
2413        ssl: &mut boring::ssl::SslRef, discover: bool,
2414    ) -> Result<()> {
2415        let ex_data = tls::ExData::from_ssl_ref(ssl).ok_or(Error::TlsFail)?;
2416
2417        ex_data.pmtud = Some(discover);
2418
2419        Ok(())
2420    }
2421
2422    /// Sets the `max_idle_timeout` transport parameter, in milliseconds.
2423    ///
2424    /// This function can only be called inside one of BoringSSL's handshake
2425    /// callbacks, before any packet has been sent. Calling this function any
2426    /// other time will have no effect.
2427    ///
2428    /// See [`Config::set_max_idle_timeout()`].
2429    ///
2430    /// [`Config::set_max_idle_timeout()`]: struct.Config.html#method.set_max_idle_timeout
2431    #[cfg(feature = "boringssl-boring-crate")]
2432    #[cfg_attr(docsrs, doc(cfg(feature = "boringssl-boring-crate")))]
2433    pub fn set_max_idle_timeout_in_handshake(
2434        ssl: &mut boring::ssl::SslRef, v: u64,
2435    ) -> Result<()> {
2436        let ex_data = tls::ExData::from_ssl_ref(ssl).ok_or(Error::TlsFail)?;
2437
2438        ex_data.local_transport_params.max_idle_timeout = v;
2439
2440        Self::set_transport_parameters_in_hanshake(
2441            ex_data.local_transport_params.clone(),
2442            ex_data.is_server,
2443            ssl,
2444        )
2445    }
2446
2447    /// Sets the `initial_max_streams_bidi` transport parameter.
2448    ///
2449    /// This function can only be called inside one of BoringSSL's handshake
2450    /// callbacks, before any packet has been sent. Calling this function any
2451    /// other time will have no effect.
2452    ///
2453    /// See [`Config::set_initial_max_streams_bidi()`].
2454    ///
2455    /// [`Config::set_initial_max_streams_bidi()`]: struct.Config.html#method.set_initial_max_streams_bidi
2456    #[cfg(feature = "boringssl-boring-crate")]
2457    #[cfg_attr(docsrs, doc(cfg(feature = "boringssl-boring-crate")))]
2458    pub fn set_initial_max_streams_bidi_in_handshake(
2459        ssl: &mut boring::ssl::SslRef, v: u64,
2460    ) -> Result<()> {
2461        let ex_data = tls::ExData::from_ssl_ref(ssl).ok_or(Error::TlsFail)?;
2462
2463        ex_data.local_transport_params.initial_max_streams_bidi = v;
2464
2465        Self::set_transport_parameters_in_hanshake(
2466            ex_data.local_transport_params.clone(),
2467            ex_data.is_server,
2468            ssl,
2469        )
2470    }
2471
2472    #[cfg(feature = "boringssl-boring-crate")]
2473    fn set_transport_parameters_in_hanshake(
2474        params: TransportParams, is_server: bool, ssl: &mut boring::ssl::SslRef,
2475    ) -> Result<()> {
2476        use foreign_types_shared::ForeignTypeRef;
2477
2478        // In order to apply the new parameter to the TLS state before TPs are
2479        // written into a TLS message, we need to re-encode all TPs immediately.
2480        //
2481        // Since we don't have direct access to the main `Connection` object, we
2482        // need to re-create the `Handshake` state from the `SslRef`.
2483        //
2484        // SAFETY: the `Handshake` object must not be drop()ed, otherwise it
2485        // would free the underlying BoringSSL structure.
2486        let mut handshake =
2487            unsafe { tls::Handshake::from_ptr(ssl.as_ptr() as _) };
2488        handshake.set_quic_transport_params(&params, is_server)?;
2489
2490        // Avoid running `drop(handshake)` as that would free the underlying
2491        // handshake state.
2492        std::mem::forget(handshake);
2493
2494        Ok(())
2495    }
2496
2497    /// Processes QUIC packets received from the peer.
2498    ///
2499    /// On success the number of bytes processed from the input buffer is
2500    /// returned. On error the connection will be closed by calling [`close()`]
2501    /// with the appropriate error code.
2502    ///
2503    /// Coalesced packets will be processed as necessary.
2504    ///
2505    /// Note that the contents of the input buffer `buf` might be modified by
2506    /// this function due to, for example, in-place decryption.
2507    ///
2508    /// [`close()`]: struct.Connection.html#method.close
2509    ///
2510    /// ## Examples:
2511    ///
2512    /// ```no_run
2513    /// # let mut buf = [0; 512];
2514    /// # let socket = std::net::UdpSocket::bind("127.0.0.1:0").unwrap();
2515    /// # let mut config = quiche::Config::new(quiche::PROTOCOL_VERSION)?;
2516    /// # let scid = quiche::ConnectionId::from_ref(&[0xba; 16]);
2517    /// # let peer = "127.0.0.1:1234".parse().unwrap();
2518    /// # let local = socket.local_addr().unwrap();
2519    /// # let mut conn = quiche::accept(&scid, None, local, peer, &mut config)?;
2520    /// loop {
2521    ///     let (read, from) = socket.recv_from(&mut buf).unwrap();
2522    ///
2523    ///     let recv_info = quiche::RecvInfo {
2524    ///         from,
2525    ///         to: local,
2526    ///     };
2527    ///
2528    ///     let read = match conn.recv(&mut buf[..read], recv_info) {
2529    ///         Ok(v) => v,
2530    ///
2531    ///         Err(e) => {
2532    ///             // An error occurred, handle it.
2533    ///             break;
2534    ///         },
2535    ///     };
2536    /// }
2537    /// # Ok::<(), quiche::Error>(())
2538    /// ```
2539    pub fn recv(&mut self, buf: &mut [u8], info: RecvInfo) -> Result<usize> {
2540        let len = buf.len();
2541
2542        if len == 0 {
2543            return Err(Error::BufferTooShort);
2544        }
2545
2546        let recv_pid = self.paths.path_id_from_addrs(&(info.to, info.from));
2547
2548        if let Some(recv_pid) = recv_pid {
2549            let recv_path = self.paths.get_mut(recv_pid)?;
2550
2551            // Keep track of how many bytes we received from the client, so we
2552            // can limit bytes sent back before address validation, to a
2553            // multiple of this. The limit needs to be increased early on, so
2554            // that if there is an error there is enough credit to send a
2555            // CONNECTION_CLOSE.
2556            //
2557            // It doesn't matter if the packets received were valid or not, we
2558            // only need to track the total amount of bytes received.
2559            //
2560            // Note that we also need to limit the number of bytes we sent on a
2561            // path if we are not the host that initiated its usage.
2562            if self.is_server && !recv_path.verified_peer_address {
2563                recv_path.max_send_bytes += len * self.max_amplification_factor;
2564            }
2565        } else if !self.is_server {
2566            // If a client receives packets from an unknown server address,
2567            // the client MUST discard these packets.
2568            trace!(
2569                "{} client received packet from unknown address {:?}, dropping",
2570                self.trace_id,
2571                info,
2572            );
2573
2574            return Ok(len);
2575        }
2576
2577        let mut done = 0;
2578        let mut left = len;
2579
2580        // Process coalesced packets.
2581        while left > 0 {
2582            let read = match self.recv_single(
2583                &mut buf[len - left..len],
2584                &info,
2585                recv_pid,
2586            ) {
2587                Ok(v) => v,
2588
2589                Err(Error::Done) => {
2590                    // If the packet can't be processed or decrypted, check if
2591                    // it's a stateless reset.
2592                    if self.is_stateless_reset(&buf[len - left..len]) {
2593                        trace!("{} packet is a stateless reset", self.trace_id);
2594
2595                        self.mark_closed();
2596                    }
2597
2598                    left
2599                },
2600
2601                Err(e) => {
2602                    // In case of error processing the incoming packet, close
2603                    // the connection.
2604                    self.close(false, e.to_wire(), b"").ok();
2605                    return Err(e);
2606                },
2607            };
2608
2609            done += read;
2610            left -= read;
2611        }
2612
2613        // Even though the packet was previously "accepted", it
2614        // should be safe to forward the error, as it also comes
2615        // from the `recv()` method.
2616        self.process_undecrypted_0rtt_packets()?;
2617
2618        Ok(done)
2619    }
2620
2621    fn process_undecrypted_0rtt_packets(&mut self) -> Result<()> {
2622        // Process previously undecryptable 0-RTT packets if the decryption key
2623        // is now available.
2624        if self.crypto_ctx[packet::Epoch::Application]
2625            .crypto_0rtt_open
2626            .is_some()
2627        {
2628            while let Some((mut pkt, info)) = self.undecryptable_pkts.pop_front()
2629            {
2630                if let Err(e) = self.recv(&mut pkt, info) {
2631                    self.undecryptable_pkts.clear();
2632
2633                    return Err(e);
2634                }
2635            }
2636        }
2637        Ok(())
2638    }
2639
2640    /// Returns true if a QUIC packet is a stateless reset.
2641    fn is_stateless_reset(&self, buf: &[u8]) -> bool {
2642        // If the packet is too small, then we just throw it away.
2643        let buf_len = buf.len();
2644        if buf_len < 21 {
2645            return false;
2646        }
2647
2648        // TODO: we should iterate over all active destination connection IDs
2649        // and check against their reset token.
2650        match self.peer_transport_params.stateless_reset_token {
2651            Some(token) => {
2652                let token_len = 16;
2653
2654                crypto::verify_slices_are_equal(
2655                    &token.to_be_bytes(),
2656                    &buf[buf_len - token_len..buf_len],
2657                )
2658                .is_ok()
2659            },
2660
2661            None => false,
2662        }
2663    }
2664
2665    /// Processes a single QUIC packet received from the peer.
2666    ///
2667    /// On success the number of bytes processed from the input buffer is
2668    /// returned. When the [`Done`] error is returned, processing of the
2669    /// remainder of the incoming UDP datagram should be interrupted.
2670    ///
2671    /// Note that a server might observe a new 4-tuple, preventing to
2672    /// know in advance to which path the incoming packet belongs to (`recv_pid`
2673    /// is `None`). As a client, packets from unknown 4-tuple are dropped
2674    /// beforehand (see `recv()`).
2675    ///
2676    /// On error, an error other than [`Done`] is returned.
2677    ///
2678    /// [`Done`]: enum.Error.html#variant.Done
2679    fn recv_single(
2680        &mut self, buf: &mut [u8], info: &RecvInfo, recv_pid: Option<usize>,
2681    ) -> Result<usize> {
2682        let now = Instant::now();
2683
2684        if buf.is_empty() {
2685            return Err(Error::Done);
2686        }
2687
2688        if self.is_closed() || self.is_draining() {
2689            return Err(Error::Done);
2690        }
2691
2692        let is_closing = self.local_error.is_some();
2693
2694        if is_closing {
2695            return Err(Error::Done);
2696        }
2697
2698        let buf_len = buf.len();
2699
2700        let mut b = octets::OctetsMut::with_slice(buf);
2701
2702        let mut hdr = Header::from_bytes(&mut b, self.source_id().len())
2703            .map_err(|e| {
2704                drop_pkt_on_err(
2705                    e,
2706                    self.recv_count,
2707                    self.is_server,
2708                    &self.trace_id,
2709                )
2710            })?;
2711
2712        if hdr.ty == Type::VersionNegotiation {
2713            // Version negotiation packets can only be sent by the server.
2714            if self.is_server {
2715                return Err(Error::Done);
2716            }
2717
2718            // Ignore duplicate version negotiation.
2719            if self.did_version_negotiation {
2720                return Err(Error::Done);
2721            }
2722
2723            // Ignore version negotiation if any other packet has already been
2724            // successfully processed.
2725            if self.recv_count > 0 {
2726                return Err(Error::Done);
2727            }
2728
2729            if hdr.dcid != self.source_id() {
2730                return Err(Error::Done);
2731            }
2732
2733            if hdr.scid != self.destination_id() {
2734                return Err(Error::Done);
2735            }
2736
2737            trace!("{} rx pkt {:?}", self.trace_id, hdr);
2738
2739            let versions = hdr.versions.ok_or(Error::Done)?;
2740
2741            // Ignore version negotiation if the version already selected is
2742            // listed.
2743            if versions.contains(&self.version) {
2744                return Err(Error::Done);
2745            }
2746
2747            let supported_versions =
2748                versions.iter().filter(|&&v| version_is_supported(v));
2749
2750            let mut found_version = false;
2751
2752            for &v in supported_versions {
2753                found_version = true;
2754
2755                // The final version takes precedence over draft ones.
2756                if v == PROTOCOL_VERSION_V1 {
2757                    self.version = v;
2758                    break;
2759                }
2760
2761                self.version = cmp::max(self.version, v);
2762            }
2763
2764            if !found_version {
2765                // We don't support any of the versions offered.
2766                //
2767                // While a man-in-the-middle attacker might be able to
2768                // inject a version negotiation packet that triggers this
2769                // failure, the window of opportunity is very small and
2770                // this error is quite useful for debugging, so don't just
2771                // ignore the packet.
2772                return Err(Error::UnknownVersion);
2773            }
2774
2775            self.did_version_negotiation = true;
2776
2777            // Derive Initial secrets based on the new version.
2778            let (aead_open, aead_seal) = crypto::derive_initial_key_material(
2779                &self.destination_id(),
2780                self.version,
2781                self.is_server,
2782                true,
2783            )?;
2784
2785            // Reset connection state to force sending another Initial packet.
2786            self.drop_epoch_state(packet::Epoch::Initial, now);
2787            self.got_peer_conn_id = false;
2788            self.handshake.clear()?;
2789
2790            self.crypto_ctx[packet::Epoch::Initial].crypto_open = Some(aead_open);
2791            self.crypto_ctx[packet::Epoch::Initial].crypto_seal = Some(aead_seal);
2792
2793            self.handshake
2794                .use_legacy_codepoint(self.version != PROTOCOL_VERSION_V1);
2795
2796            // Encode transport parameters again, as the new version might be
2797            // using a different format.
2798            self.encode_transport_params()?;
2799
2800            return Err(Error::Done);
2801        }
2802
2803        if hdr.ty == Type::Retry {
2804            // Retry packets can only be sent by the server.
2805            if self.is_server {
2806                return Err(Error::Done);
2807            }
2808
2809            // Ignore duplicate retry.
2810            if self.did_retry {
2811                return Err(Error::Done);
2812            }
2813
2814            // Check if Retry packet is valid.
2815            if packet::verify_retry_integrity(
2816                &b,
2817                &self.destination_id(),
2818                self.version,
2819            )
2820            .is_err()
2821            {
2822                return Err(Error::Done);
2823            }
2824
2825            trace!("{} rx pkt {:?}", self.trace_id, hdr);
2826
2827            self.token = hdr.token;
2828            self.did_retry = true;
2829
2830            // Remember peer's new connection ID.
2831            self.odcid = Some(self.destination_id().into_owned());
2832
2833            self.set_initial_dcid(
2834                hdr.scid.clone(),
2835                None,
2836                self.paths.get_active_path_id()?,
2837            )?;
2838
2839            self.rscid = Some(self.destination_id().into_owned());
2840
2841            // Derive Initial secrets using the new connection ID.
2842            let (aead_open, aead_seal) = crypto::derive_initial_key_material(
2843                &hdr.scid,
2844                self.version,
2845                self.is_server,
2846                true,
2847            )?;
2848
2849            // Reset connection state to force sending another Initial packet.
2850            self.drop_epoch_state(packet::Epoch::Initial, now);
2851            self.got_peer_conn_id = false;
2852            self.handshake.clear()?;
2853
2854            self.crypto_ctx[packet::Epoch::Initial].crypto_open = Some(aead_open);
2855            self.crypto_ctx[packet::Epoch::Initial].crypto_seal = Some(aead_seal);
2856
2857            return Err(Error::Done);
2858        }
2859
2860        if self.is_server && !self.did_version_negotiation {
2861            if !version_is_supported(hdr.version) {
2862                return Err(Error::UnknownVersion);
2863            }
2864
2865            self.version = hdr.version;
2866            self.did_version_negotiation = true;
2867
2868            self.handshake
2869                .use_legacy_codepoint(self.version != PROTOCOL_VERSION_V1);
2870
2871            // Encode transport parameters again, as the new version might be
2872            // using a different format.
2873            self.encode_transport_params()?;
2874        }
2875
2876        if hdr.ty != Type::Short && hdr.version != self.version {
2877            // At this point version negotiation was already performed, so
2878            // ignore packets that don't match the connection's version.
2879            return Err(Error::Done);
2880        }
2881
2882        // Long header packets have an explicit payload length, but short
2883        // packets don't so just use the remaining capacity in the buffer.
2884        let payload_len = if hdr.ty == Type::Short {
2885            b.cap()
2886        } else {
2887            b.get_varint().map_err(|e| {
2888                drop_pkt_on_err(
2889                    e.into(),
2890                    self.recv_count,
2891                    self.is_server,
2892                    &self.trace_id,
2893                )
2894            })? as usize
2895        };
2896
2897        // Make sure the buffer is same or larger than an explicit
2898        // payload length.
2899        if payload_len > b.cap() {
2900            return Err(drop_pkt_on_err(
2901                Error::InvalidPacket,
2902                self.recv_count,
2903                self.is_server,
2904                &self.trace_id,
2905            ));
2906        }
2907
2908        // Derive initial secrets on the server.
2909        if !self.derived_initial_secrets {
2910            let (aead_open, aead_seal) = crypto::derive_initial_key_material(
2911                &hdr.dcid,
2912                self.version,
2913                self.is_server,
2914                false,
2915            )?;
2916
2917            self.crypto_ctx[packet::Epoch::Initial].crypto_open = Some(aead_open);
2918            self.crypto_ctx[packet::Epoch::Initial].crypto_seal = Some(aead_seal);
2919
2920            self.derived_initial_secrets = true;
2921        }
2922
2923        // Select packet number space epoch based on the received packet's type.
2924        let epoch = hdr.ty.to_epoch()?;
2925
2926        // Select AEAD context used to open incoming packet.
2927        let aead = if hdr.ty == Type::ZeroRTT {
2928            // Only use 0-RTT key if incoming packet is 0-RTT.
2929            self.crypto_ctx[epoch].crypto_0rtt_open.as_ref()
2930        } else {
2931            // Otherwise use the packet number space's main key.
2932            self.crypto_ctx[epoch].crypto_open.as_ref()
2933        };
2934
2935        // Finally, discard packet if no usable key is available.
2936        let mut aead = match aead {
2937            Some(v) => v,
2938
2939            None => {
2940                if hdr.ty == Type::ZeroRTT &&
2941                    self.undecryptable_pkts.len() < MAX_UNDECRYPTABLE_PACKETS &&
2942                    !self.is_established()
2943                {
2944                    // Buffer 0-RTT packets when the required read key is not
2945                    // available yet, and process them later.
2946                    //
2947                    // TODO: in the future we might want to buffer other types
2948                    // of undecryptable packets as well.
2949                    let pkt_len = b.off() + payload_len;
2950                    let pkt = (b.buf()[..pkt_len]).to_vec();
2951
2952                    self.undecryptable_pkts.push_back((pkt, *info));
2953                    return Ok(pkt_len);
2954                }
2955
2956                let e = drop_pkt_on_err(
2957                    Error::CryptoFail,
2958                    self.recv_count,
2959                    self.is_server,
2960                    &self.trace_id,
2961                );
2962
2963                return Err(e);
2964            },
2965        };
2966
2967        let aead_tag_len = aead.alg().tag_len();
2968
2969        packet::decrypt_hdr(&mut b, &mut hdr, aead).map_err(|e| {
2970            drop_pkt_on_err(e, self.recv_count, self.is_server, &self.trace_id)
2971        })?;
2972
2973        let pn = packet::decode_pkt_num(
2974            self.pkt_num_spaces[epoch].largest_rx_pkt_num,
2975            hdr.pkt_num,
2976            hdr.pkt_num_len,
2977        );
2978
2979        let pn_len = hdr.pkt_num_len;
2980
2981        trace!(
2982            "{} rx pkt {:?} len={} pn={} {}",
2983            self.trace_id,
2984            hdr,
2985            payload_len,
2986            pn,
2987            AddrTupleFmt(info.from, info.to)
2988        );
2989
2990        #[cfg(feature = "qlog")]
2991        let mut qlog_frames = vec![];
2992
2993        // Check for key update.
2994        let mut aead_next = None;
2995
2996        if self.handshake_confirmed &&
2997            hdr.ty != Type::ZeroRTT &&
2998            hdr.key_phase != self.key_phase
2999        {
3000            // Check if this packet arrived before key update.
3001            if let Some(key_update) = self.crypto_ctx[epoch]
3002                .key_update
3003                .as_ref()
3004                .and_then(|key_update| {
3005                    (pn < key_update.pn_on_update).then_some(key_update)
3006                })
3007            {
3008                aead = &key_update.crypto_open;
3009            } else {
3010                trace!("{} peer-initiated key update", self.trace_id);
3011
3012                aead_next = Some((
3013                    self.crypto_ctx[epoch]
3014                        .crypto_open
3015                        .as_ref()
3016                        .unwrap()
3017                        .derive_next_packet_key()?,
3018                    self.crypto_ctx[epoch]
3019                        .crypto_seal
3020                        .as_ref()
3021                        .unwrap()
3022                        .derive_next_packet_key()?,
3023                ));
3024
3025                // `aead_next` is always `Some()` at this point, so the `unwrap()`
3026                // will never fail.
3027                aead = &aead_next.as_ref().unwrap().0;
3028            }
3029        }
3030
3031        let mut payload = packet::decrypt_pkt(
3032            &mut b,
3033            pn,
3034            pn_len,
3035            payload_len,
3036            aead,
3037        )
3038        .map_err(|e| {
3039            drop_pkt_on_err(e, self.recv_count, self.is_server, &self.trace_id)
3040        })?;
3041
3042        if self.pkt_num_spaces[epoch].recv_pkt_num.contains(pn) {
3043            trace!("{} ignored duplicate packet {}", self.trace_id, pn);
3044            return Err(Error::Done);
3045        }
3046
3047        // Packets with no frames are invalid.
3048        if payload.cap() == 0 {
3049            return Err(Error::InvalidPacket);
3050        }
3051
3052        // Now that we decrypted the packet, let's see if we can map it to an
3053        // existing path.
3054        let recv_pid = if hdr.ty == Type::Short && self.got_peer_conn_id {
3055            let pkt_dcid = ConnectionId::from_ref(&hdr.dcid);
3056            self.get_or_create_recv_path_id(recv_pid, &pkt_dcid, buf_len, info)?
3057        } else {
3058            // During handshake, we are on the initial path.
3059            self.paths.get_active_path_id()?
3060        };
3061
3062        // The key update is verified once a packet is successfully decrypted
3063        // using the new keys.
3064        if let Some((open_next, seal_next)) = aead_next {
3065            if !self.crypto_ctx[epoch]
3066                .key_update
3067                .as_ref()
3068                .is_none_or(|prev| prev.update_acked)
3069            {
3070                // Peer has updated keys twice without awaiting confirmation.
3071                return Err(Error::KeyUpdate);
3072            }
3073
3074            trace!("{} key update verified", self.trace_id);
3075
3076            let _ = self.crypto_ctx[epoch].crypto_seal.replace(seal_next);
3077
3078            let open_prev = self.crypto_ctx[epoch]
3079                .crypto_open
3080                .replace(open_next)
3081                .unwrap();
3082
3083            let recv_path = self.paths.get_mut(recv_pid)?;
3084
3085            self.crypto_ctx[epoch].key_update = Some(packet::KeyUpdate {
3086                crypto_open: open_prev,
3087                pn_on_update: pn,
3088                update_acked: false,
3089                timer: now + (recv_path.recovery.pto() * 3),
3090            });
3091
3092            self.key_phase = !self.key_phase;
3093
3094            qlog_with_type!(QLOG_PACKET_RX, self.qlog, q, {
3095                let trigger = Some(
3096                    qlog::events::security::KeyUpdateOrRetiredTrigger::RemoteUpdate,
3097                );
3098
3099                let ev_data_client =
3100                    EventData::KeyUpdated(qlog::events::security::KeyUpdated {
3101                        key_type:
3102                            qlog::events::security::KeyType::Client1RttSecret,
3103                        trigger: trigger.clone(),
3104                        ..Default::default()
3105                    });
3106
3107                q.add_event_data_with_instant(ev_data_client, now).ok();
3108
3109                let ev_data_server =
3110                    EventData::KeyUpdated(qlog::events::security::KeyUpdated {
3111                        key_type:
3112                            qlog::events::security::KeyType::Server1RttSecret,
3113                        trigger,
3114                        ..Default::default()
3115                    });
3116
3117                q.add_event_data_with_instant(ev_data_server, now).ok();
3118            });
3119        }
3120
3121        if !self.is_server && !self.got_peer_conn_id {
3122            if self.odcid.is_none() {
3123                self.odcid = Some(self.destination_id().into_owned());
3124            }
3125
3126            // Replace the randomly generated destination connection ID with
3127            // the one supplied by the server.
3128            self.set_initial_dcid(
3129                hdr.scid.clone(),
3130                self.peer_transport_params.stateless_reset_token,
3131                recv_pid,
3132            )?;
3133
3134            self.got_peer_conn_id = true;
3135        }
3136
3137        if self.is_server && !self.got_peer_conn_id {
3138            self.set_initial_dcid(hdr.scid.clone(), None, recv_pid)?;
3139
3140            if !self.did_retry {
3141                self.local_transport_params
3142                    .original_destination_connection_id =
3143                    Some(hdr.dcid.to_vec().into());
3144
3145                self.encode_transport_params()?;
3146            }
3147
3148            self.got_peer_conn_id = true;
3149        }
3150
3151        // To avoid sending an ACK in response to an ACK-only packet, we need
3152        // to keep track of whether this packet contains any frame other than
3153        // ACK and PADDING.
3154        let mut ack_elicited = false;
3155
3156        // Process packet payload. If a frame cannot be processed, store the
3157        // error and stop further packet processing.
3158        let mut frame_processing_err = None;
3159
3160        // To know if the peer migrated the connection, we need to keep track
3161        // whether this is a non-probing packet.
3162        let mut probing = true;
3163
3164        // Process packet payload.
3165        while payload.cap() > 0 {
3166            let frame = frame::Frame::from_bytes(&mut payload, hdr.ty)?;
3167
3168            qlog_with_type!(QLOG_PACKET_RX, self.qlog, _q, {
3169                qlog_frames.push(frame.to_qlog());
3170            });
3171
3172            if frame.ack_eliciting() {
3173                ack_elicited = true;
3174            }
3175
3176            if !frame.probing() {
3177                probing = false;
3178            }
3179
3180            if let Err(e) = self.process_frame(frame, &hdr, recv_pid, epoch, now)
3181            {
3182                frame_processing_err = Some(e);
3183                break;
3184            }
3185        }
3186
3187        qlog_with_type!(QLOG_PACKET_RX, self.qlog, q, {
3188            let packet_size = b.len();
3189
3190            let qlog_pkt_hdr = qlog::events::quic::PacketHeader::with_type(
3191                hdr.ty.to_qlog(),
3192                Some(pn),
3193                Some(hdr.version),
3194                Some(&hdr.scid),
3195                Some(&hdr.dcid),
3196            );
3197
3198            let qlog_raw_info = RawInfo {
3199                length: Some(packet_size as u64),
3200                payload_length: Some(payload_len as u64),
3201                data: None,
3202            };
3203
3204            let ev_data =
3205                EventData::PacketReceived(qlog::events::quic::PacketReceived {
3206                    header: qlog_pkt_hdr,
3207                    frames: Some(qlog_frames),
3208                    raw: Some(qlog_raw_info),
3209                    ..Default::default()
3210                });
3211
3212            q.add_event_data_with_instant(ev_data, now).ok();
3213        });
3214
3215        qlog_with_type!(QLOG_PACKET_RX, self.qlog, q, {
3216            let recv_path = self.paths.get_mut(recv_pid)?;
3217            recv_path.recovery.maybe_qlog(q, now);
3218        });
3219
3220        if let Some(e) = frame_processing_err {
3221            // Any frame error is terminal, so now just return.
3222            return Err(e);
3223        }
3224
3225        // Only log the remote transport parameters once the connection is
3226        // established (i.e. after frames have been fully parsed) and only
3227        // once per connection.
3228        if self.is_established() {
3229            qlog_with_type!(QLOG_PARAMS_SET, self.qlog, q, {
3230                if !self.qlog.logged_peer_params {
3231                    let ev_data = self
3232                        .peer_transport_params
3233                        .to_qlog(TransportOwner::Remote, self.handshake.cipher());
3234
3235                    q.add_event_data_with_instant(ev_data, now).ok();
3236
3237                    self.qlog.logged_peer_params = true;
3238                }
3239            });
3240        }
3241
3242        // Process acked frames. Note that several packets from several paths
3243        // might have been acked by the received packet.
3244        for (_, p) in self.paths.iter_mut() {
3245            while let Some(acked) = p.recovery.next_acked_frame(epoch) {
3246                match acked {
3247                    frame::Frame::Ping {
3248                        mtu_probe: Some(mtu_probe),
3249                    } =>
3250                        if let Some(pmtud) = p.pmtud.as_mut() {
3251                            trace!(
3252                                "{} pmtud probe acked; probe size {:?}",
3253                                self.trace_id,
3254                                mtu_probe
3255                            );
3256
3257                            // Ensure the probe is within the supported MTU range
3258                            // before updating the max datagram size
3259                            if let Some(current_mtu) =
3260                                pmtud.successful_probe(mtu_probe)
3261                            {
3262                                qlog_with_type!(
3263                                    EventType::ConnectivityEventType(
3264                                        ConnectivityEventType::MtuUpdated
3265                                    ),
3266                                    self.qlog,
3267                                    q,
3268                                    {
3269                                        let pmtu_data = EventData::MtuUpdated(
3270                                            qlog::events::connectivity::MtuUpdated {
3271                                                old: Some(
3272                                                    p.recovery.max_datagram_size()
3273                                                        as u16,
3274                                                ),
3275                                                new: current_mtu as u16,
3276                                                done: Some(true),
3277                                            },
3278                                        );
3279
3280                                        q.add_event_data_with_instant(
3281                                            pmtu_data, now,
3282                                        )
3283                                        .ok();
3284                                    }
3285                                );
3286
3287                                p.recovery
3288                                    .pmtud_update_max_datagram_size(current_mtu);
3289                            }
3290                        },
3291
3292                    frame::Frame::ACK { ranges, .. } => {
3293                        // Stop acknowledging packets less than or equal to the
3294                        // largest acknowledged in the sent ACK frame that, in
3295                        // turn, got acked.
3296                        if let Some(largest_acked) = ranges.last() {
3297                            self.pkt_num_spaces[epoch]
3298                                .recv_pkt_need_ack
3299                                .remove_until(largest_acked);
3300                        }
3301                    },
3302
3303                    frame::Frame::CryptoHeader { offset, length } => {
3304                        self.crypto_ctx[epoch]
3305                            .crypto_stream
3306                            .send
3307                            .ack_and_drop(offset, length);
3308                    },
3309
3310                    frame::Frame::StreamHeader {
3311                        stream_id,
3312                        offset,
3313                        length,
3314                        ..
3315                    } => {
3316                        // Update tx_buffered and emit qlog before checking if the
3317                        // stream still exists.  The client does need to ACK
3318                        // frames that were received after the client sends a
3319                        // ResetStream.
3320                        self.tx_buffered =
3321                            self.tx_buffered.saturating_sub(length);
3322
3323                        qlog_with_type!(QLOG_DATA_MV, self.qlog, q, {
3324                            let ev_data = EventData::DataMoved(
3325                                qlog::events::quic::DataMoved {
3326                                    stream_id: Some(stream_id),
3327                                    offset: Some(offset),
3328                                    length: Some(length as u64),
3329                                    from: Some(DataRecipient::Transport),
3330                                    to: Some(DataRecipient::Dropped),
3331                                    ..Default::default()
3332                                },
3333                            );
3334
3335                            q.add_event_data_with_instant(ev_data, now).ok();
3336                        });
3337
3338                        let stream = match self.streams.get_mut(stream_id) {
3339                            Some(v) => v,
3340
3341                            None => continue,
3342                        };
3343
3344                        stream.send.ack_and_drop(offset, length);
3345
3346                        let priority_key = Arc::clone(&stream.priority_key);
3347
3348                        // Only collect the stream if it is complete and not
3349                        // readable or writable.
3350                        //
3351                        // If it is readable, it will get collected when
3352                        // stream_recv() is next used.
3353                        //
3354                        // If it is writable, it might mean that the stream
3355                        // has been stopped by the peer (i.e. a STOP_SENDING
3356                        // frame is received), in which case before collecting
3357                        // the stream we will need to propagate the
3358                        // `StreamStopped` error to the application. It will
3359                        // instead get collected when one of stream_capacity(),
3360                        // stream_writable(), stream_send(), ... is next called.
3361                        //
3362                        // Note that we can't use `is_writable()` here because
3363                        // it returns false if the stream is stopped. Instead,
3364                        // since the stream is marked as writable when a
3365                        // STOP_SENDING frame is received, we check the writable
3366                        // queue directly instead.
3367                        let is_writable = priority_key.writable.is_linked() &&
3368                            // Ensure that the stream is actually stopped.
3369                            stream.send.is_stopped();
3370
3371                        let is_complete = stream.is_complete();
3372                        let is_readable = stream.is_readable();
3373
3374                        if is_complete && !is_readable && !is_writable {
3375                            let local = stream.local;
3376                            self.streams.collect(stream_id, local);
3377                        }
3378                    },
3379
3380                    frame::Frame::HandshakeDone => {
3381                        // Explicitly set this to true, so that if the frame was
3382                        // already scheduled for retransmission, it is aborted.
3383                        self.handshake_done_sent = true;
3384
3385                        self.handshake_done_acked = true;
3386                    },
3387
3388                    frame::Frame::ResetStream { stream_id, .. } => {
3389                        let stream = match self.streams.get_mut(stream_id) {
3390                            Some(v) => v,
3391
3392                            None => continue,
3393                        };
3394
3395                        let priority_key = Arc::clone(&stream.priority_key);
3396
3397                        // Only collect the stream if it is complete and not
3398                        // readable or writable.
3399                        //
3400                        // If it is readable, it will get collected when
3401                        // stream_recv() is next used.
3402                        //
3403                        // If it is writable, it might mean that the stream
3404                        // has been stopped by the peer (i.e. a STOP_SENDING
3405                        // frame is received), in which case before collecting
3406                        // the stream we will need to propagate the
3407                        // `StreamStopped` error to the application. It will
3408                        // instead get collected when one of stream_capacity(),
3409                        // stream_writable(), stream_send(), ... is next called.
3410                        //
3411                        // Note that we can't use `is_writable()` here because
3412                        // it returns false if the stream is stopped. Instead,
3413                        // since the stream is marked as writable when a
3414                        // STOP_SENDING frame is received, we check the writable
3415                        // queue directly instead.
3416                        let is_writable = priority_key.writable.is_linked() &&
3417                            // Ensure that the stream is actually stopped.
3418                            stream.send.is_stopped();
3419
3420                        let is_complete = stream.is_complete();
3421                        let is_readable = stream.is_readable();
3422
3423                        if is_complete && !is_readable && !is_writable {
3424                            let local = stream.local;
3425                            self.streams.collect(stream_id, local);
3426                        }
3427                    },
3428
3429                    _ => (),
3430                }
3431            }
3432        }
3433
3434        // Now that we processed all the frames, if there is a path that has no
3435        // Destination CID, try to allocate one.
3436        let no_dcid = self
3437            .paths
3438            .iter_mut()
3439            .filter(|(_, p)| p.active_dcid_seq.is_none());
3440
3441        for (pid, p) in no_dcid {
3442            if self.ids.zero_length_dcid() {
3443                p.active_dcid_seq = Some(0);
3444                continue;
3445            }
3446
3447            let dcid_seq = match self.ids.lowest_available_dcid_seq() {
3448                Some(seq) => seq,
3449                None => break,
3450            };
3451
3452            self.ids.link_dcid_to_path_id(dcid_seq, pid)?;
3453
3454            p.active_dcid_seq = Some(dcid_seq);
3455        }
3456
3457        // We only record the time of arrival of the largest packet number
3458        // that still needs to be acked, to be used for ACK delay calculation.
3459        if self.pkt_num_spaces[epoch].recv_pkt_need_ack.last() < Some(pn) {
3460            self.pkt_num_spaces[epoch].largest_rx_pkt_time = now;
3461        }
3462
3463        self.pkt_num_spaces[epoch].recv_pkt_num.insert(pn);
3464
3465        self.pkt_num_spaces[epoch].recv_pkt_need_ack.push_item(pn);
3466
3467        self.pkt_num_spaces[epoch].ack_elicited =
3468            cmp::max(self.pkt_num_spaces[epoch].ack_elicited, ack_elicited);
3469
3470        self.pkt_num_spaces[epoch].largest_rx_pkt_num =
3471            cmp::max(self.pkt_num_spaces[epoch].largest_rx_pkt_num, pn);
3472
3473        if !probing {
3474            self.pkt_num_spaces[epoch].largest_rx_non_probing_pkt_num = cmp::max(
3475                self.pkt_num_spaces[epoch].largest_rx_non_probing_pkt_num,
3476                pn,
3477            );
3478
3479            // Did the peer migrated to another path?
3480            let active_path_id = self.paths.get_active_path_id()?;
3481
3482            if self.is_server &&
3483                recv_pid != active_path_id &&
3484                self.pkt_num_spaces[epoch].largest_rx_non_probing_pkt_num == pn
3485            {
3486                self.on_peer_migrated(recv_pid, self.disable_dcid_reuse, now)?;
3487            }
3488        }
3489
3490        if let Some(idle_timeout) = self.idle_timeout() {
3491            self.idle_timer = Some(now + idle_timeout);
3492        }
3493
3494        // Update send capacity.
3495        self.update_tx_cap();
3496
3497        self.recv_count += 1;
3498        self.paths.get_mut(recv_pid)?.recv_count += 1;
3499
3500        let read = b.off() + aead_tag_len;
3501
3502        self.recv_bytes += read as u64;
3503        self.paths.get_mut(recv_pid)?.recv_bytes += read as u64;
3504
3505        // An Handshake packet has been received from the client and has been
3506        // successfully processed, so we can drop the initial state and consider
3507        // the client's address to be verified.
3508        if self.is_server && hdr.ty == Type::Handshake {
3509            self.drop_epoch_state(packet::Epoch::Initial, now);
3510
3511            self.paths.get_mut(recv_pid)?.verified_peer_address = true;
3512        }
3513
3514        self.ack_eliciting_sent = false;
3515
3516        Ok(read)
3517    }
3518
3519    /// Writes a single QUIC packet to be sent to the peer.
3520    ///
3521    /// On success the number of bytes written to the output buffer is
3522    /// returned, or [`Done`] if there was nothing to write.
3523    ///
3524    /// The application should call `send()` multiple times until [`Done`] is
3525    /// returned, indicating that there are no more packets to send. It is
3526    /// recommended that `send()` be called in the following cases:
3527    ///
3528    ///  * When the application receives QUIC packets from the peer (that is,
3529    ///    any time [`recv()`] is also called).
3530    ///
3531    ///  * When the connection timer expires (that is, any time [`on_timeout()`]
3532    ///    is also called).
3533    ///
3534    ///  * When the application sends data to the peer (for example, any time
3535    ///    [`stream_send()`] or [`stream_shutdown()`] are called).
3536    ///
3537    ///  * When the application receives data from the peer (for example any
3538    ///    time [`stream_recv()`] is called).
3539    ///
3540    /// Once [`is_draining()`] returns `true`, it is no longer necessary to call
3541    /// `send()` and all calls will return [`Done`].
3542    ///
3543    /// [`Done`]: enum.Error.html#variant.Done
3544    /// [`recv()`]: struct.Connection.html#method.recv
3545    /// [`on_timeout()`]: struct.Connection.html#method.on_timeout
3546    /// [`stream_send()`]: struct.Connection.html#method.stream_send
3547    /// [`stream_shutdown()`]: struct.Connection.html#method.stream_shutdown
3548    /// [`stream_recv()`]: struct.Connection.html#method.stream_recv
3549    /// [`is_draining()`]: struct.Connection.html#method.is_draining
3550    ///
3551    /// ## Examples:
3552    ///
3553    /// ```no_run
3554    /// # let mut out = [0; 512];
3555    /// # let socket = std::net::UdpSocket::bind("127.0.0.1:0").unwrap();
3556    /// # let mut config = quiche::Config::new(quiche::PROTOCOL_VERSION)?;
3557    /// # let scid = quiche::ConnectionId::from_ref(&[0xba; 16]);
3558    /// # let peer = "127.0.0.1:1234".parse().unwrap();
3559    /// # let local = socket.local_addr().unwrap();
3560    /// # let mut conn = quiche::accept(&scid, None, local, peer, &mut config)?;
3561    /// loop {
3562    ///     let (write, send_info) = match conn.send(&mut out) {
3563    ///         Ok(v) => v,
3564    ///
3565    ///         Err(quiche::Error::Done) => {
3566    ///             // Done writing.
3567    ///             break;
3568    ///         },
3569    ///
3570    ///         Err(e) => {
3571    ///             // An error occurred, handle it.
3572    ///             break;
3573    ///         },
3574    ///     };
3575    ///
3576    ///     socket.send_to(&out[..write], &send_info.to).unwrap();
3577    /// }
3578    /// # Ok::<(), quiche::Error>(())
3579    /// ```
3580    pub fn send(&mut self, out: &mut [u8]) -> Result<(usize, SendInfo)> {
3581        self.send_on_path(out, None, None)
3582    }
3583
3584    /// Writes a single QUIC packet to be sent to the peer from the specified
3585    /// local address `from` to the destination address `to`.
3586    ///
3587    /// The behavior of this method differs depending on the value of the `from`
3588    /// and `to` parameters:
3589    ///
3590    ///  * If both are `Some`, then the method only consider the 4-tuple
3591    ///    (`from`, `to`). Application can monitor the 4-tuple availability,
3592    ///    either by monitoring [`path_event_next()`] events or by relying on
3593    ///    the [`paths_iter()`] method. If the provided 4-tuple does not exist
3594    ///    on the connection (anymore), it returns an [`InvalidState`].
3595    ///
3596    ///  * If `from` is `Some` and `to` is `None`, then the method only
3597    ///    considers sending packets on paths having `from` as local address.
3598    ///
3599    ///  * If `to` is `Some` and `from` is `None`, then the method only
3600    ///    considers sending packets on paths having `to` as peer address.
3601    ///
3602    ///  * If both are `None`, all available paths are considered.
3603    ///
3604    /// On success the number of bytes written to the output buffer is
3605    /// returned, or [`Done`] if there was nothing to write.
3606    ///
3607    /// The application should call `send_on_path()` multiple times until
3608    /// [`Done`] is returned, indicating that there are no more packets to
3609    /// send. It is recommended that `send_on_path()` be called in the
3610    /// following cases:
3611    ///
3612    ///  * When the application receives QUIC packets from the peer (that is,
3613    ///    any time [`recv()`] is also called).
3614    ///
3615    ///  * When the connection timer expires (that is, any time [`on_timeout()`]
3616    ///    is also called).
3617    ///
3618    ///  * When the application sends data to the peer (for examples, any time
3619    ///    [`stream_send()`] or [`stream_shutdown()`] are called).
3620    ///
3621    ///  * When the application receives data from the peer (for example any
3622    ///    time [`stream_recv()`] is called).
3623    ///
3624    /// Once [`is_draining()`] returns `true`, it is no longer necessary to call
3625    /// `send_on_path()` and all calls will return [`Done`].
3626    ///
3627    /// [`Done`]: enum.Error.html#variant.Done
3628    /// [`InvalidState`]: enum.Error.html#InvalidState
3629    /// [`recv()`]: struct.Connection.html#method.recv
3630    /// [`on_timeout()`]: struct.Connection.html#method.on_timeout
3631    /// [`stream_send()`]: struct.Connection.html#method.stream_send
3632    /// [`stream_shutdown()`]: struct.Connection.html#method.stream_shutdown
3633    /// [`stream_recv()`]: struct.Connection.html#method.stream_recv
3634    /// [`path_event_next()`]: struct.Connection.html#method.path_event_next
3635    /// [`paths_iter()`]: struct.Connection.html#method.paths_iter
3636    /// [`is_draining()`]: struct.Connection.html#method.is_draining
3637    ///
3638    /// ## Examples:
3639    ///
3640    /// ```no_run
3641    /// # let mut out = [0; 512];
3642    /// # let socket = std::net::UdpSocket::bind("127.0.0.1:0").unwrap();
3643    /// # let mut config = quiche::Config::new(quiche::PROTOCOL_VERSION)?;
3644    /// # let scid = quiche::ConnectionId::from_ref(&[0xba; 16]);
3645    /// # let peer = "127.0.0.1:1234".parse().unwrap();
3646    /// # let local = socket.local_addr().unwrap();
3647    /// # let mut conn = quiche::accept(&scid, None, local, peer, &mut config)?;
3648    /// loop {
3649    ///     let (write, send_info) = match conn.send_on_path(&mut out, Some(local), Some(peer)) {
3650    ///         Ok(v) => v,
3651    ///
3652    ///         Err(quiche::Error::Done) => {
3653    ///             // Done writing.
3654    ///             break;
3655    ///         },
3656    ///
3657    ///         Err(e) => {
3658    ///             // An error occurred, handle it.
3659    ///             break;
3660    ///         },
3661    ///     };
3662    ///
3663    ///     socket.send_to(&out[..write], &send_info.to).unwrap();
3664    /// }
3665    /// # Ok::<(), quiche::Error>(())
3666    /// ```
3667    pub fn send_on_path(
3668        &mut self, out: &mut [u8], from: Option<SocketAddr>,
3669        to: Option<SocketAddr>,
3670    ) -> Result<(usize, SendInfo)> {
3671        if out.is_empty() {
3672            return Err(Error::BufferTooShort);
3673        }
3674
3675        if self.is_closed() || self.is_draining() {
3676            return Err(Error::Done);
3677        }
3678
3679        let now = Instant::now();
3680
3681        if self.local_error.is_none() {
3682            self.do_handshake(now)?;
3683        }
3684
3685        // Forwarding the error value here could confuse
3686        // applications, as they may not expect getting a `recv()`
3687        // error when calling `send()`.
3688        //
3689        // We simply fall-through to sending packets, which should
3690        // take care of terminating the connection as needed.
3691        let _ = self.process_undecrypted_0rtt_packets();
3692
3693        // There's no point in trying to send a packet if the Initial secrets
3694        // have not been derived yet, so return early.
3695        if !self.derived_initial_secrets {
3696            return Err(Error::Done);
3697        }
3698
3699        let mut has_initial = false;
3700
3701        let mut done = 0;
3702
3703        // Limit output packet size to respect the sender and receiver's
3704        // maximum UDP payload size limit.
3705        let mut left = cmp::min(out.len(), self.max_send_udp_payload_size());
3706
3707        let send_pid = match (from, to) {
3708            (Some(f), Some(t)) => self
3709                .paths
3710                .path_id_from_addrs(&(f, t))
3711                .ok_or(Error::InvalidState)?,
3712
3713            _ => self.get_send_path_id(from, to)?,
3714        };
3715
3716        let send_path = self.paths.get_mut(send_pid)?;
3717
3718        // Update max datagram size to allow path MTU discovery probe to be sent.
3719        if let Some(pmtud) = send_path.pmtud.as_mut() {
3720            if pmtud.should_probe() {
3721                let size = if self.handshake_confirmed || self.handshake_completed
3722                {
3723                    pmtud.get_probe_size()
3724                } else {
3725                    pmtud.get_current_mtu()
3726                };
3727
3728                send_path.recovery.pmtud_update_max_datagram_size(size);
3729
3730                left =
3731                    cmp::min(out.len(), send_path.recovery.max_datagram_size());
3732            }
3733        }
3734
3735        // Limit data sent by the server based on the amount of data received
3736        // from the client before its address is validated.
3737        if !send_path.verified_peer_address && self.is_server {
3738            left = cmp::min(left, send_path.max_send_bytes);
3739        }
3740
3741        // Generate coalesced packets.
3742        while left > 0 {
3743            let (ty, written) = match self.send_single(
3744                &mut out[done..done + left],
3745                send_pid,
3746                has_initial,
3747                now,
3748            ) {
3749                Ok(v) => v,
3750
3751                Err(Error::BufferTooShort) | Err(Error::Done) => break,
3752
3753                Err(e) => return Err(e),
3754            };
3755
3756            done += written;
3757            left -= written;
3758
3759            match ty {
3760                Type::Initial => has_initial = true,
3761
3762                // No more packets can be coalesced after a 1-RTT.
3763                Type::Short => break,
3764
3765                _ => (),
3766            };
3767
3768            // When sending multiple PTO probes, don't coalesce them together,
3769            // so they are sent on separate UDP datagrams.
3770            if let Ok(epoch) = ty.to_epoch() {
3771                if self.paths.get_mut(send_pid)?.recovery.loss_probes(epoch) > 0 {
3772                    break;
3773                }
3774            }
3775
3776            // Don't coalesce packets that must go on different paths.
3777            if !(from.is_some() && to.is_some()) &&
3778                self.get_send_path_id(from, to)? != send_pid
3779            {
3780                break;
3781            }
3782        }
3783
3784        if done == 0 {
3785            self.last_tx_data = self.tx_data;
3786
3787            return Err(Error::Done);
3788        }
3789
3790        if has_initial && left > 0 && done < MIN_CLIENT_INITIAL_LEN {
3791            let pad_len = cmp::min(left, MIN_CLIENT_INITIAL_LEN - done);
3792
3793            // Fill padding area with null bytes, to avoid leaking information
3794            // in case the application reuses the packet buffer.
3795            out[done..done + pad_len].fill(0);
3796
3797            done += pad_len;
3798        }
3799
3800        let send_path = self.paths.get(send_pid)?;
3801
3802        let info = SendInfo {
3803            from: send_path.local_addr(),
3804            to: send_path.peer_addr(),
3805
3806            at: send_path.recovery.get_packet_send_time(now),
3807        };
3808
3809        Ok((done, info))
3810    }
3811
3812    fn send_single(
3813        &mut self, out: &mut [u8], send_pid: usize, has_initial: bool,
3814        now: Instant,
3815    ) -> Result<(Type, usize)> {
3816        if out.is_empty() {
3817            return Err(Error::BufferTooShort);
3818        }
3819
3820        if self.is_draining() {
3821            return Err(Error::Done);
3822        }
3823
3824        let is_closing = self.local_error.is_some();
3825
3826        let out_len = out.len();
3827
3828        let mut b = octets::OctetsMut::with_slice(out);
3829
3830        let pkt_type = self.write_pkt_type(send_pid)?;
3831
3832        let max_dgram_len = if !self.dgram_send_queue.is_empty() {
3833            self.dgram_max_writable_len()
3834        } else {
3835            None
3836        };
3837
3838        let epoch = pkt_type.to_epoch()?;
3839        let pkt_space = &mut self.pkt_num_spaces[epoch];
3840        let crypto_ctx = &mut self.crypto_ctx[epoch];
3841
3842        // Process lost frames. There might be several paths having lost frames.
3843        for (_, p) in self.paths.iter_mut() {
3844            while let Some(lost) = p.recovery.next_lost_frame(epoch) {
3845                match lost {
3846                    frame::Frame::CryptoHeader { offset, length } => {
3847                        crypto_ctx.crypto_stream.send.retransmit(offset, length);
3848
3849                        self.stream_retrans_bytes += length as u64;
3850                        p.stream_retrans_bytes += length as u64;
3851
3852                        self.retrans_count += 1;
3853                        p.retrans_count += 1;
3854                    },
3855
3856                    frame::Frame::StreamHeader {
3857                        stream_id,
3858                        offset,
3859                        length,
3860                        fin,
3861                    } => {
3862                        let stream = match self.streams.get_mut(stream_id) {
3863                            // Only retransmit data if the stream is not closed
3864                            // or stopped.
3865                            Some(v) if !v.send.is_stopped() => v,
3866
3867                            // Data on a closed stream will not be retransmitted
3868                            // or acked after it is declared lost, so update
3869                            // tx_buffered and qlog.
3870                            _ => {
3871                                self.tx_buffered =
3872                                    self.tx_buffered.saturating_sub(length);
3873
3874                                qlog_with_type!(QLOG_DATA_MV, self.qlog, q, {
3875                                    let ev_data = EventData::DataMoved(
3876                                        qlog::events::quic::DataMoved {
3877                                            stream_id: Some(stream_id),
3878                                            offset: Some(offset),
3879                                            length: Some(length as u64),
3880                                            from: Some(DataRecipient::Transport),
3881                                            to: Some(DataRecipient::Dropped),
3882                                            ..Default::default()
3883                                        },
3884                                    );
3885
3886                                    q.add_event_data_with_instant(ev_data, now)
3887                                        .ok();
3888                                });
3889
3890                                continue;
3891                            },
3892                        };
3893
3894                        let was_flushable = stream.is_flushable();
3895
3896                        let empty_fin = length == 0 && fin;
3897
3898                        stream.send.retransmit(offset, length);
3899
3900                        // If the stream is now flushable push it to the
3901                        // flushable queue, but only if it wasn't already
3902                        // queued.
3903                        //
3904                        // Consider the stream flushable also when we are
3905                        // sending a zero-length frame that has the fin flag
3906                        // set.
3907                        if (stream.is_flushable() || empty_fin) && !was_flushable
3908                        {
3909                            let priority_key = Arc::clone(&stream.priority_key);
3910                            self.streams.insert_flushable(&priority_key);
3911                        }
3912
3913                        self.stream_retrans_bytes += length as u64;
3914                        p.stream_retrans_bytes += length as u64;
3915
3916                        self.retrans_count += 1;
3917                        p.retrans_count += 1;
3918                    },
3919
3920                    frame::Frame::ACK { .. } => {
3921                        pkt_space.ack_elicited = true;
3922                    },
3923
3924                    frame::Frame::ResetStream {
3925                        stream_id,
3926                        error_code,
3927                        final_size,
3928                    } =>
3929                        if self.streams.get(stream_id).is_some() {
3930                            self.streams
3931                                .insert_reset(stream_id, error_code, final_size);
3932                        },
3933
3934                    // Retransmit HANDSHAKE_DONE only if it hasn't been acked at
3935                    // least once already.
3936                    frame::Frame::HandshakeDone if !self.handshake_done_acked => {
3937                        self.handshake_done_sent = false;
3938                    },
3939
3940                    frame::Frame::MaxStreamData { stream_id, .. } => {
3941                        if self.streams.get(stream_id).is_some() {
3942                            self.streams.insert_almost_full(stream_id);
3943                        }
3944                    },
3945
3946                    frame::Frame::MaxData { .. } => {
3947                        self.almost_full = true;
3948                    },
3949
3950                    frame::Frame::NewConnectionId { seq_num, .. } => {
3951                        self.ids.mark_advertise_new_scid_seq(seq_num, true);
3952                    },
3953
3954                    frame::Frame::RetireConnectionId { seq_num } => {
3955                        self.ids.mark_retire_dcid_seq(seq_num, true)?;
3956                    },
3957
3958                    frame::Frame::Ping {
3959                        mtu_probe: Some(failed_probe),
3960                    } =>
3961                        if let Some(pmtud) = p.pmtud.as_mut() {
3962                            trace!("pmtud probe dropped: {failed_probe}");
3963                            pmtud.failed_probe(failed_probe);
3964                        },
3965
3966                    _ => (),
3967                }
3968            }
3969        }
3970        self.check_tx_buffered_invariant();
3971
3972        let is_app_limited = self.delivery_rate_check_if_app_limited();
3973        let n_paths = self.paths.len();
3974        let path = self.paths.get_mut(send_pid)?;
3975        let flow_control = &mut self.flow_control;
3976        let pkt_space = &mut self.pkt_num_spaces[epoch];
3977        let crypto_ctx = &mut self.crypto_ctx[epoch];
3978        let pkt_num_manager = &mut self.pkt_num_manager;
3979
3980        let mut left = if let Some(pmtud) = path.pmtud.as_mut() {
3981            // Limit output buffer size by estimated path MTU.
3982            cmp::min(pmtud.get_current_mtu(), b.cap())
3983        } else {
3984            b.cap()
3985        };
3986
3987        if pkt_num_manager.should_skip_pn(self.handshake_completed) {
3988            pkt_num_manager.set_skip_pn(Some(self.next_pkt_num));
3989            self.next_pkt_num += 1;
3990        };
3991        let pn = self.next_pkt_num;
3992
3993        let largest_acked_pkt =
3994            path.recovery.get_largest_acked_on_epoch(epoch).unwrap_or(0);
3995        let pn_len = packet::pkt_num_len(pn, largest_acked_pkt);
3996
3997        // The AEAD overhead at the current encryption level.
3998        let crypto_overhead = crypto_ctx.crypto_overhead().ok_or(Error::Done)?;
3999
4000        let dcid_seq = path.active_dcid_seq.ok_or(Error::OutOfIdentifiers)?;
4001
4002        let dcid =
4003            ConnectionId::from_ref(self.ids.get_dcid(dcid_seq)?.cid.as_ref());
4004
4005        let scid = if let Some(scid_seq) = path.active_scid_seq {
4006            ConnectionId::from_ref(self.ids.get_scid(scid_seq)?.cid.as_ref())
4007        } else if pkt_type == Type::Short {
4008            ConnectionId::default()
4009        } else {
4010            return Err(Error::InvalidState);
4011        };
4012
4013        let hdr = Header {
4014            ty: pkt_type,
4015
4016            version: self.version,
4017
4018            dcid,
4019            scid,
4020
4021            pkt_num: 0,
4022            pkt_num_len: pn_len,
4023
4024            // Only clone token for Initial packets, as other packets don't have
4025            // this field (Retry doesn't count, as it's not encoded as part of
4026            // this code path).
4027            token: if pkt_type == Type::Initial {
4028                self.token.clone()
4029            } else {
4030                None
4031            },
4032
4033            versions: None,
4034            key_phase: self.key_phase,
4035        };
4036
4037        hdr.to_bytes(&mut b)?;
4038
4039        let hdr_trace = if log::max_level() == log::LevelFilter::Trace {
4040            Some(format!("{hdr:?}"))
4041        } else {
4042            None
4043        };
4044
4045        let hdr_ty = hdr.ty;
4046
4047        #[cfg(feature = "qlog")]
4048        let qlog_pkt_hdr = self.qlog.streamer.as_ref().map(|_q| {
4049            qlog::events::quic::PacketHeader::with_type(
4050                hdr.ty.to_qlog(),
4051                Some(pn),
4052                Some(hdr.version),
4053                Some(&hdr.scid),
4054                Some(&hdr.dcid),
4055            )
4056        });
4057
4058        // Calculate the space required for the packet, including the header
4059        // the payload length, the packet number and the AEAD overhead.
4060        let mut overhead = b.off() + pn_len + crypto_overhead;
4061
4062        // We assume that the payload length, which is only present in long
4063        // header packets, can always be encoded with a 2-byte varint.
4064        if pkt_type != Type::Short {
4065            overhead += PAYLOAD_LENGTH_LEN;
4066        }
4067
4068        // Make sure we have enough space left for the packet overhead.
4069        match left.checked_sub(overhead) {
4070            Some(v) => left = v,
4071
4072            None => {
4073                // We can't send more because there isn't enough space available
4074                // in the output buffer.
4075                //
4076                // This usually happens when we try to send a new packet but
4077                // failed because cwnd is almost full. In such case app_limited
4078                // is set to false here to make cwnd grow when ACK is received.
4079                path.recovery.update_app_limited(false);
4080                return Err(Error::Done);
4081            },
4082        }
4083
4084        // Make sure there is enough space for the minimum payload length.
4085        if left < PAYLOAD_MIN_LEN {
4086            path.recovery.update_app_limited(false);
4087            return Err(Error::Done);
4088        }
4089
4090        let mut frames: SmallVec<[frame::Frame; 1]> = SmallVec::new();
4091
4092        let mut ack_eliciting = false;
4093        let mut in_flight = false;
4094        let mut is_pmtud_probe = false;
4095        let mut has_data = false;
4096
4097        // Whether or not we should explicitly elicit an ACK via PING frame if we
4098        // implicitly elicit one otherwise.
4099        let ack_elicit_required = path.recovery.should_elicit_ack(epoch);
4100
4101        let header_offset = b.off();
4102
4103        // Reserve space for payload length in advance. Since we don't yet know
4104        // what the final length will be, we reserve 2 bytes in all cases.
4105        //
4106        // Only long header packets have an explicit length field.
4107        if pkt_type != Type::Short {
4108            b.skip(PAYLOAD_LENGTH_LEN)?;
4109        }
4110
4111        packet::encode_pkt_num(pn, pn_len, &mut b)?;
4112
4113        let payload_offset = b.off();
4114
4115        let cwnd_available =
4116            path.recovery.cwnd_available().saturating_sub(overhead);
4117
4118        let left_before_packing_ack_frame = left;
4119
4120        // Create ACK frame.
4121        //
4122        // When we need to explicitly elicit an ACK via PING later, go ahead and
4123        // generate an ACK (if there's anything to ACK) since we're going to
4124        // send a packet with PING anyways, even if we haven't received anything
4125        // ACK eliciting.
4126        if pkt_space.recv_pkt_need_ack.len() > 0 &&
4127            (pkt_space.ack_elicited || ack_elicit_required) &&
4128            (!is_closing ||
4129                (pkt_type == Type::Handshake &&
4130                    self.local_error
4131                        .as_ref()
4132                        .is_some_and(|le| le.is_app))) &&
4133            path.active()
4134        {
4135            #[cfg(not(feature = "fuzzing"))]
4136            let ack_delay = pkt_space.largest_rx_pkt_time.elapsed();
4137
4138            #[cfg(not(feature = "fuzzing"))]
4139            let ack_delay = ack_delay.as_micros() as u64 /
4140                2_u64
4141                    .pow(self.local_transport_params.ack_delay_exponent as u32);
4142
4143            // pseudo-random reproducible ack delays when fuzzing
4144            #[cfg(feature = "fuzzing")]
4145            let ack_delay = rand::rand_u8() as u64 + 1;
4146
4147            let frame = frame::Frame::ACK {
4148                ack_delay,
4149                ranges: pkt_space.recv_pkt_need_ack.clone(),
4150                ecn_counts: None, // sending ECN is not supported at this time
4151            };
4152
4153            // When a PING frame needs to be sent, avoid sending the ACK if
4154            // there is not enough cwnd available for both (note that PING
4155            // frames are always 1 byte, so we just need to check that the
4156            // ACK's length is lower than cwnd).
4157            if pkt_space.ack_elicited || frame.wire_len() < cwnd_available {
4158                // ACK-only packets are not congestion controlled so ACKs must
4159                // be bundled considering the buffer capacity only, and not the
4160                // available cwnd.
4161                if push_frame_to_pkt!(b, frames, frame, left) {
4162                    pkt_space.ack_elicited = false;
4163                }
4164            }
4165        }
4166
4167        // Limit output packet size by congestion window size.
4168        left = cmp::min(
4169            left,
4170            // Bytes consumed by ACK frames.
4171            cwnd_available.saturating_sub(left_before_packing_ack_frame - left),
4172        );
4173
4174        let mut challenge_data = None;
4175
4176        let active_path = self.paths.get_active_mut()?;
4177
4178        if pkt_type == Type::Short {
4179            // Create PMTUD probe.
4180            //
4181            // In order to send a PMTUD probe the current `left` value, which was
4182            // already limited by the current PMTU measure, needs to be ignored,
4183            // but the outgoing packet still needs to be limited by
4184            // the output buffer size, as well as the congestion
4185            // window.
4186            //
4187            // In addition, the PMTUD probe is only generated when the handshake
4188            // is confirmed, to avoid interfering with the handshake
4189            // (e.g. due to the anti-amplification limits).
4190            let should_probe_pmtu = active_path.should_send_pmtu_probe(
4191                self.handshake_confirmed,
4192                self.handshake_completed,
4193                out_len,
4194                is_closing,
4195                frames.is_empty(),
4196            );
4197
4198            if should_probe_pmtu {
4199                if let Some(pmtud) = active_path.pmtud.as_mut() {
4200                    let probe_size = pmtud.get_probe_size();
4201                    trace!(
4202                        "{} sending pmtud probe pmtu_probe={} estimated_pmtu={}",
4203                        self.trace_id,
4204                        probe_size,
4205                        pmtud.get_current_mtu(),
4206                    );
4207
4208                    left = probe_size;
4209
4210                    match left.checked_sub(overhead) {
4211                        Some(v) => left = v,
4212
4213                        None => {
4214                            // We can't send more because there isn't enough space
4215                            // available in the output buffer.
4216                            //
4217                            // This usually happens when we try to send a new
4218                            // packet but failed
4219                            // because cwnd is almost full.
4220                            //
4221                            // In such case app_limited is set to false here to
4222                            // make cwnd grow when ACK
4223                            // is received.
4224                            active_path.recovery.update_app_limited(false);
4225                            return Err(Error::Done);
4226                        },
4227                    }
4228
4229                    let frame = frame::Frame::Padding {
4230                        len: probe_size - overhead - 1,
4231                    };
4232
4233                    if push_frame_to_pkt!(b, frames, frame, left) {
4234                        let frame = frame::Frame::Ping {
4235                            mtu_probe: Some(probe_size),
4236                        };
4237
4238                        if push_frame_to_pkt!(b, frames, frame, left) {
4239                            ack_eliciting = true;
4240                            in_flight = true;
4241                        }
4242                    }
4243
4244                    // Reset probe flag after sending to prevent duplicate probes
4245                    // in a single flight.
4246                    pmtud.set_in_flight(true);
4247                    is_pmtud_probe = true;
4248                }
4249            }
4250
4251            let path = self.paths.get_mut(send_pid)?;
4252            // Create PATH_RESPONSE frame if needed.
4253            // We do not try to ensure that these are really sent.
4254            while let Some(challenge) = path.pop_received_challenge() {
4255                let frame = frame::Frame::PathResponse { data: challenge };
4256
4257                if push_frame_to_pkt!(b, frames, frame, left) {
4258                    ack_eliciting = true;
4259                    in_flight = true;
4260                } else {
4261                    // If there are other pending PATH_RESPONSE, don't lose them
4262                    // now.
4263                    break;
4264                }
4265            }
4266
4267            // Create PATH_CHALLENGE frame if needed.
4268            if path.validation_requested() {
4269                // TODO: ensure that data is unique over paths.
4270                let data = rand::rand_u64().to_be_bytes();
4271
4272                let frame = frame::Frame::PathChallenge { data };
4273
4274                if push_frame_to_pkt!(b, frames, frame, left) {
4275                    // Let's notify the path once we know the packet size.
4276                    challenge_data = Some(data);
4277
4278                    ack_eliciting = true;
4279                    in_flight = true;
4280                }
4281            }
4282
4283            if let Some(key_update) = crypto_ctx.key_update.as_mut() {
4284                key_update.update_acked = true;
4285            }
4286        }
4287
4288        let path = self.paths.get_mut(send_pid)?;
4289
4290        if pkt_type == Type::Short && !is_closing {
4291            // Create NEW_CONNECTION_ID frames as needed.
4292            while let Some(seq_num) = self.ids.next_advertise_new_scid_seq() {
4293                let frame = self.ids.get_new_connection_id_frame_for(seq_num)?;
4294
4295                if push_frame_to_pkt!(b, frames, frame, left) {
4296                    self.ids.mark_advertise_new_scid_seq(seq_num, false);
4297
4298                    ack_eliciting = true;
4299                    in_flight = true;
4300                } else {
4301                    break;
4302                }
4303            }
4304        }
4305
4306        if pkt_type == Type::Short && !is_closing && path.active() {
4307            // Create HANDSHAKE_DONE frame.
4308            // self.should_send_handshake_done() but without the need to borrow
4309            if self.handshake_completed &&
4310                !self.handshake_done_sent &&
4311                self.is_server
4312            {
4313                let frame = frame::Frame::HandshakeDone;
4314
4315                if push_frame_to_pkt!(b, frames, frame, left) {
4316                    self.handshake_done_sent = true;
4317
4318                    ack_eliciting = true;
4319                    in_flight = true;
4320                }
4321            }
4322
4323            // Create MAX_STREAMS_BIDI frame.
4324            if self.streams.should_update_max_streams_bidi() {
4325                let frame = frame::Frame::MaxStreamsBidi {
4326                    max: self.streams.max_streams_bidi_next(),
4327                };
4328
4329                if push_frame_to_pkt!(b, frames, frame, left) {
4330                    self.streams.update_max_streams_bidi();
4331
4332                    ack_eliciting = true;
4333                    in_flight = true;
4334                }
4335            }
4336
4337            // Create MAX_STREAMS_UNI frame.
4338            if self.streams.should_update_max_streams_uni() {
4339                let frame = frame::Frame::MaxStreamsUni {
4340                    max: self.streams.max_streams_uni_next(),
4341                };
4342
4343                if push_frame_to_pkt!(b, frames, frame, left) {
4344                    self.streams.update_max_streams_uni();
4345
4346                    ack_eliciting = true;
4347                    in_flight = true;
4348                }
4349            }
4350
4351            // Create DATA_BLOCKED frame.
4352            if let Some(limit) = self.blocked_limit {
4353                let frame = frame::Frame::DataBlocked { limit };
4354
4355                if push_frame_to_pkt!(b, frames, frame, left) {
4356                    self.blocked_limit = None;
4357                    self.data_blocked_sent_count =
4358                        self.data_blocked_sent_count.saturating_add(1);
4359
4360                    ack_eliciting = true;
4361                    in_flight = true;
4362                }
4363            }
4364
4365            // Create MAX_STREAM_DATA frames as needed.
4366            for stream_id in self.streams.almost_full() {
4367                let stream = match self.streams.get_mut(stream_id) {
4368                    Some(v) => v,
4369
4370                    None => {
4371                        // The stream doesn't exist anymore, so remove it from
4372                        // the almost full set.
4373                        self.streams.remove_almost_full(stream_id);
4374                        continue;
4375                    },
4376                };
4377
4378                // Autotune the stream window size.
4379                stream.recv.autotune_window(now, path.recovery.rtt());
4380
4381                let frame = frame::Frame::MaxStreamData {
4382                    stream_id,
4383                    max: stream.recv.max_data_next(),
4384                };
4385
4386                if push_frame_to_pkt!(b, frames, frame, left) {
4387                    let recv_win = stream.recv.window();
4388
4389                    stream.recv.update_max_data(now);
4390
4391                    self.streams.remove_almost_full(stream_id);
4392
4393                    ack_eliciting = true;
4394                    in_flight = true;
4395
4396                    // Make sure the connection window always has some
4397                    // room compared to the stream window.
4398                    flow_control.ensure_window_lower_bound(
4399                        (recv_win as f64 * CONNECTION_WINDOW_FACTOR) as u64,
4400                    );
4401
4402                    // Also send MAX_DATA when MAX_STREAM_DATA is sent, to avoid a
4403                    // potential race condition.
4404                    self.almost_full = true;
4405                }
4406            }
4407
4408            // Create MAX_DATA frame as needed.
4409            if self.almost_full &&
4410                flow_control.max_data() < flow_control.max_data_next()
4411            {
4412                // Autotune the connection window size.
4413                flow_control.autotune_window(now, path.recovery.rtt());
4414
4415                let frame = frame::Frame::MaxData {
4416                    max: flow_control.max_data_next(),
4417                };
4418
4419                if push_frame_to_pkt!(b, frames, frame, left) {
4420                    self.almost_full = false;
4421
4422                    // Commits the new max_rx_data limit.
4423                    flow_control.update_max_data(now);
4424
4425                    ack_eliciting = true;
4426                    in_flight = true;
4427                }
4428            }
4429
4430            // Create STOP_SENDING frames as needed.
4431            for (stream_id, error_code) in self
4432                .streams
4433                .stopped()
4434                .map(|(&k, &v)| (k, v))
4435                .collect::<Vec<(u64, u64)>>()
4436            {
4437                let frame = frame::Frame::StopSending {
4438                    stream_id,
4439                    error_code,
4440                };
4441
4442                if push_frame_to_pkt!(b, frames, frame, left) {
4443                    self.streams.remove_stopped(stream_id);
4444
4445                    ack_eliciting = true;
4446                    in_flight = true;
4447                }
4448            }
4449
4450            // Create RESET_STREAM frames as needed.
4451            for (stream_id, (error_code, final_size)) in self
4452                .streams
4453                .reset()
4454                .map(|(&k, &v)| (k, v))
4455                .collect::<Vec<(u64, (u64, u64))>>()
4456            {
4457                let frame = frame::Frame::ResetStream {
4458                    stream_id,
4459                    error_code,
4460                    final_size,
4461                };
4462
4463                if push_frame_to_pkt!(b, frames, frame, left) {
4464                    self.streams.remove_reset(stream_id);
4465
4466                    ack_eliciting = true;
4467                    in_flight = true;
4468                }
4469            }
4470
4471            // Create STREAM_DATA_BLOCKED frames as needed.
4472            for (stream_id, limit) in self
4473                .streams
4474                .blocked()
4475                .map(|(&k, &v)| (k, v))
4476                .collect::<Vec<(u64, u64)>>()
4477            {
4478                let frame = frame::Frame::StreamDataBlocked { stream_id, limit };
4479
4480                if push_frame_to_pkt!(b, frames, frame, left) {
4481                    self.streams.remove_blocked(stream_id);
4482                    self.stream_data_blocked_sent_count =
4483                        self.stream_data_blocked_sent_count.saturating_add(1);
4484
4485                    ack_eliciting = true;
4486                    in_flight = true;
4487                }
4488            }
4489
4490            // Create RETIRE_CONNECTION_ID frames as needed.
4491            let retire_dcid_seqs = self.ids.retire_dcid_seqs();
4492
4493            for seq_num in retire_dcid_seqs {
4494                // The sequence number specified in a RETIRE_CONNECTION_ID frame
4495                // MUST NOT refer to the Destination Connection ID field of the
4496                // packet in which the frame is contained.
4497                let dcid_seq = path.active_dcid_seq.ok_or(Error::InvalidState)?;
4498
4499                if seq_num == dcid_seq {
4500                    continue;
4501                }
4502
4503                let frame = frame::Frame::RetireConnectionId { seq_num };
4504
4505                if push_frame_to_pkt!(b, frames, frame, left) {
4506                    self.ids.mark_retire_dcid_seq(seq_num, false)?;
4507
4508                    ack_eliciting = true;
4509                    in_flight = true;
4510                } else {
4511                    break;
4512                }
4513            }
4514        }
4515
4516        // Create CONNECTION_CLOSE frame. Try to send this only on the active
4517        // path, unless it is the last one available.
4518        if path.active() || n_paths == 1 {
4519            if let Some(conn_err) = self.local_error.as_ref() {
4520                if conn_err.is_app {
4521                    // Create ApplicationClose frame.
4522                    if pkt_type == Type::Short {
4523                        let frame = frame::Frame::ApplicationClose {
4524                            error_code: conn_err.error_code,
4525                            reason: conn_err.reason.clone(),
4526                        };
4527
4528                        if push_frame_to_pkt!(b, frames, frame, left) {
4529                            let pto = path.recovery.pto();
4530                            self.draining_timer = Some(now + (pto * 3));
4531
4532                            ack_eliciting = true;
4533                            in_flight = true;
4534                        }
4535                    }
4536                } else {
4537                    // Create ConnectionClose frame.
4538                    let frame = frame::Frame::ConnectionClose {
4539                        error_code: conn_err.error_code,
4540                        frame_type: 0,
4541                        reason: conn_err.reason.clone(),
4542                    };
4543
4544                    if push_frame_to_pkt!(b, frames, frame, left) {
4545                        let pto = path.recovery.pto();
4546                        self.draining_timer = Some(now + (pto * 3));
4547
4548                        ack_eliciting = true;
4549                        in_flight = true;
4550                    }
4551                }
4552            }
4553        }
4554
4555        // Create CRYPTO frame.
4556        if crypto_ctx.crypto_stream.is_flushable() &&
4557            left > frame::MAX_CRYPTO_OVERHEAD &&
4558            !is_closing &&
4559            path.active()
4560        {
4561            let crypto_off = crypto_ctx.crypto_stream.send.off_front();
4562
4563            // Encode the frame.
4564            //
4565            // Instead of creating a `frame::Frame` object, encode the frame
4566            // directly into the packet buffer.
4567            //
4568            // First we reserve some space in the output buffer for writing the
4569            // frame header (we assume the length field is always a 2-byte
4570            // varint as we don't know the value yet).
4571            //
4572            // Then we emit the data from the crypto stream's send buffer.
4573            //
4574            // Finally we go back and encode the frame header with the now
4575            // available information.
4576            let hdr_off = b.off();
4577            let hdr_len = 1 + // frame type
4578                octets::varint_len(crypto_off) + // offset
4579                2; // length, always encode as 2-byte varint
4580
4581            if let Some(max_len) = left.checked_sub(hdr_len) {
4582                let (mut crypto_hdr, mut crypto_payload) =
4583                    b.split_at(hdr_off + hdr_len)?;
4584
4585                // Write stream data into the packet buffer.
4586                let (len, _) = crypto_ctx
4587                    .crypto_stream
4588                    .send
4589                    .emit(&mut crypto_payload.as_mut()[..max_len])?;
4590
4591                // Encode the frame's header.
4592                //
4593                // Due to how `OctetsMut::split_at()` works, `crypto_hdr` starts
4594                // from the initial offset of `b` (rather than the current
4595                // offset), so it needs to be advanced to the
4596                // initial frame offset.
4597                crypto_hdr.skip(hdr_off)?;
4598
4599                frame::encode_crypto_header(
4600                    crypto_off,
4601                    len as u64,
4602                    &mut crypto_hdr,
4603                )?;
4604
4605                // Advance the packet buffer's offset.
4606                b.skip(hdr_len + len)?;
4607
4608                let frame = frame::Frame::CryptoHeader {
4609                    offset: crypto_off,
4610                    length: len,
4611                };
4612
4613                if push_frame_to_pkt!(b, frames, frame, left) {
4614                    ack_eliciting = true;
4615                    in_flight = true;
4616                    has_data = true;
4617                }
4618            }
4619        }
4620
4621        // The preference of data-bearing frame to include in a packet
4622        // is managed by `self.emit_dgram`. However, whether any frames
4623        // can be sent depends on the state of their buffers. In the case
4624        // where one type is preferred but its buffer is empty, fall back
4625        // to the other type in order not to waste this function call.
4626        let mut dgram_emitted = false;
4627        let dgrams_to_emit = max_dgram_len.is_some();
4628        let stream_to_emit = self.streams.has_flushable();
4629
4630        let mut do_dgram = self.emit_dgram && dgrams_to_emit;
4631        let do_stream = !self.emit_dgram && stream_to_emit;
4632
4633        if !do_stream && dgrams_to_emit {
4634            do_dgram = true;
4635        }
4636
4637        // Create DATAGRAM frame.
4638        if (pkt_type == Type::Short || pkt_type == Type::ZeroRTT) &&
4639            left > frame::MAX_DGRAM_OVERHEAD &&
4640            !is_closing &&
4641            path.active() &&
4642            do_dgram
4643        {
4644            if let Some(max_dgram_payload) = max_dgram_len {
4645                while let Some(len) = self.dgram_send_queue.peek_front_len() {
4646                    let hdr_off = b.off();
4647                    let hdr_len = 1 + // frame type
4648                        2; // length, always encode as 2-byte varint
4649
4650                    if (hdr_len + len) <= left {
4651                        // Front of the queue fits this packet, send it.
4652                        match self.dgram_send_queue.pop() {
4653                            Some(data) => {
4654                                // Encode the frame.
4655                                //
4656                                // Instead of creating a `frame::Frame` object,
4657                                // encode the frame directly into the packet
4658                                // buffer.
4659                                //
4660                                // First we reserve some space in the output
4661                                // buffer for writing the frame header (we
4662                                // assume the length field is always a 2-byte
4663                                // varint as we don't know the value yet).
4664                                //
4665                                // Then we emit the data from the DATAGRAM's
4666                                // buffer.
4667                                //
4668                                // Finally we go back and encode the frame
4669                                // header with the now available information.
4670                                let (mut dgram_hdr, mut dgram_payload) =
4671                                    b.split_at(hdr_off + hdr_len)?;
4672
4673                                dgram_payload.as_mut()[..len]
4674                                    .copy_from_slice(&data);
4675
4676                                // Encode the frame's header.
4677                                //
4678                                // Due to how `OctetsMut::split_at()` works,
4679                                // `dgram_hdr` starts from the initial offset
4680                                // of `b` (rather than the current offset), so
4681                                // it needs to be advanced to the initial frame
4682                                // offset.
4683                                dgram_hdr.skip(hdr_off)?;
4684
4685                                frame::encode_dgram_header(
4686                                    len as u64,
4687                                    &mut dgram_hdr,
4688                                )?;
4689
4690                                // Advance the packet buffer's offset.
4691                                b.skip(hdr_len + len)?;
4692
4693                                let frame =
4694                                    frame::Frame::DatagramHeader { length: len };
4695
4696                                if push_frame_to_pkt!(b, frames, frame, left) {
4697                                    ack_eliciting = true;
4698                                    in_flight = true;
4699                                    dgram_emitted = true;
4700                                    self.dgram_sent_count =
4701                                        self.dgram_sent_count.saturating_add(1);
4702                                    path.dgram_sent_count =
4703                                        path.dgram_sent_count.saturating_add(1);
4704                                }
4705                            },
4706
4707                            None => continue,
4708                        };
4709                    } else if len > max_dgram_payload {
4710                        // This dgram frame will never fit. Let's purge it.
4711                        self.dgram_send_queue.pop();
4712                    } else {
4713                        break;
4714                    }
4715                }
4716            }
4717        }
4718
4719        // Create a single STREAM frame for the first stream that is flushable.
4720        if (pkt_type == Type::Short || pkt_type == Type::ZeroRTT) &&
4721            left > frame::MAX_STREAM_OVERHEAD &&
4722            !is_closing &&
4723            path.active() &&
4724            !dgram_emitted
4725        {
4726            while let Some(priority_key) = self.streams.peek_flushable() {
4727                let stream_id = priority_key.id;
4728                let stream = match self.streams.get_mut(stream_id) {
4729                    // Avoid sending frames for streams that were already stopped.
4730                    //
4731                    // This might happen if stream data was buffered but not yet
4732                    // flushed on the wire when a STOP_SENDING frame is received.
4733                    Some(v) if !v.send.is_stopped() => v,
4734                    _ => {
4735                        self.streams.remove_flushable(&priority_key);
4736                        continue;
4737                    },
4738                };
4739
4740                let stream_off = stream.send.off_front();
4741
4742                // Encode the frame.
4743                //
4744                // Instead of creating a `frame::Frame` object, encode the frame
4745                // directly into the packet buffer.
4746                //
4747                // First we reserve some space in the output buffer for writing
4748                // the frame header (we assume the length field is always a
4749                // 2-byte varint as we don't know the value yet).
4750                //
4751                // Then we emit the data from the stream's send buffer.
4752                //
4753                // Finally we go back and encode the frame header with the now
4754                // available information.
4755                let hdr_off = b.off();
4756                let hdr_len = 1 + // frame type
4757                    octets::varint_len(stream_id) + // stream_id
4758                    octets::varint_len(stream_off) + // offset
4759                    2; // length, always encode as 2-byte varint
4760
4761                let max_len = match left.checked_sub(hdr_len) {
4762                    Some(v) => v,
4763                    None => {
4764                        let priority_key = Arc::clone(&stream.priority_key);
4765                        self.streams.remove_flushable(&priority_key);
4766
4767                        continue;
4768                    },
4769                };
4770
4771                let (mut stream_hdr, mut stream_payload) =
4772                    b.split_at(hdr_off + hdr_len)?;
4773
4774                // Write stream data into the packet buffer.
4775                let (len, fin) =
4776                    stream.send.emit(&mut stream_payload.as_mut()[..max_len])?;
4777
4778                // Encode the frame's header.
4779                //
4780                // Due to how `OctetsMut::split_at()` works, `stream_hdr` starts
4781                // from the initial offset of `b` (rather than the current
4782                // offset), so it needs to be advanced to the initial frame
4783                // offset.
4784                stream_hdr.skip(hdr_off)?;
4785
4786                frame::encode_stream_header(
4787                    stream_id,
4788                    stream_off,
4789                    len as u64,
4790                    fin,
4791                    &mut stream_hdr,
4792                )?;
4793
4794                // Advance the packet buffer's offset.
4795                b.skip(hdr_len + len)?;
4796
4797                let frame = frame::Frame::StreamHeader {
4798                    stream_id,
4799                    offset: stream_off,
4800                    length: len,
4801                    fin,
4802                };
4803
4804                if push_frame_to_pkt!(b, frames, frame, left) {
4805                    ack_eliciting = true;
4806                    in_flight = true;
4807                    has_data = true;
4808                }
4809
4810                let priority_key = Arc::clone(&stream.priority_key);
4811                // If the stream is no longer flushable, remove it from the queue
4812                if !stream.is_flushable() {
4813                    self.streams.remove_flushable(&priority_key);
4814                } else if stream.incremental {
4815                    // Shuffle the incremental stream to the back of the
4816                    // queue.
4817                    self.streams.remove_flushable(&priority_key);
4818                    self.streams.insert_flushable(&priority_key);
4819                }
4820
4821                #[cfg(feature = "fuzzing")]
4822                // Coalesce STREAM frames when fuzzing.
4823                if left > frame::MAX_STREAM_OVERHEAD {
4824                    continue;
4825                }
4826
4827                break;
4828            }
4829        }
4830
4831        // Alternate trying to send DATAGRAMs next time.
4832        self.emit_dgram = !dgram_emitted;
4833
4834        // If no other ack-eliciting frame is sent, include a PING frame
4835        // - if PTO probe needed; OR
4836        // - if we've sent too many non ack-eliciting packets without having
4837        // sent an ACK eliciting one; OR
4838        // - the application requested an ack-eliciting frame be sent.
4839        if (ack_elicit_required || path.needs_ack_eliciting) &&
4840            !ack_eliciting &&
4841            left >= 1 &&
4842            !is_closing
4843        {
4844            let frame = frame::Frame::Ping { mtu_probe: None };
4845
4846            if push_frame_to_pkt!(b, frames, frame, left) {
4847                ack_eliciting = true;
4848                in_flight = true;
4849            }
4850        }
4851
4852        if ack_eliciting && !is_pmtud_probe {
4853            path.needs_ack_eliciting = false;
4854            path.recovery.ping_sent(epoch);
4855        }
4856
4857        if !has_data &&
4858            !dgram_emitted &&
4859            cwnd_available > frame::MAX_STREAM_OVERHEAD
4860        {
4861            path.recovery.on_app_limited();
4862        }
4863
4864        if frames.is_empty() {
4865            // When we reach this point we are not able to write more, so set
4866            // app_limited to false.
4867            path.recovery.update_app_limited(false);
4868            return Err(Error::Done);
4869        }
4870
4871        // When coalescing a 1-RTT packet, we can't add padding in the UDP
4872        // datagram, so use PADDING frames instead.
4873        //
4874        // This is only needed if
4875        // 1) an Initial packet has already been written to the UDP datagram,
4876        // as Initial always requires padding.
4877        //
4878        // 2) this is a probing packet towards an unvalidated peer address.
4879        if (has_initial || !path.validated()) &&
4880            pkt_type == Type::Short &&
4881            left >= 1
4882        {
4883            let frame = frame::Frame::Padding { len: left };
4884
4885            if push_frame_to_pkt!(b, frames, frame, left) {
4886                in_flight = true;
4887            }
4888        }
4889
4890        // Pad payload so that it's always at least 4 bytes.
4891        if b.off() - payload_offset < PAYLOAD_MIN_LEN {
4892            let payload_len = b.off() - payload_offset;
4893
4894            let frame = frame::Frame::Padding {
4895                len: PAYLOAD_MIN_LEN - payload_len,
4896            };
4897
4898            #[allow(unused_assignments)]
4899            if push_frame_to_pkt!(b, frames, frame, left) {
4900                in_flight = true;
4901            }
4902        }
4903
4904        let payload_len = b.off() - payload_offset;
4905
4906        // Fill in payload length.
4907        if pkt_type != Type::Short {
4908            let len = pn_len + payload_len + crypto_overhead;
4909
4910            let (_, mut payload_with_len) = b.split_at(header_offset)?;
4911            payload_with_len
4912                .put_varint_with_len(len as u64, PAYLOAD_LENGTH_LEN)?;
4913        }
4914
4915        trace!(
4916            "{} tx pkt {} len={} pn={} {}",
4917            self.trace_id,
4918            hdr_trace.unwrap_or_default(),
4919            payload_len,
4920            pn,
4921            AddrTupleFmt(path.local_addr(), path.peer_addr())
4922        );
4923
4924        #[cfg(feature = "qlog")]
4925        let mut qlog_frames: SmallVec<
4926            [qlog::events::quic::QuicFrame; 1],
4927        > = SmallVec::with_capacity(frames.len());
4928
4929        for frame in &mut frames {
4930            trace!("{} tx frm {:?}", self.trace_id, frame);
4931
4932            qlog_with_type!(QLOG_PACKET_TX, self.qlog, _q, {
4933                qlog_frames.push(frame.to_qlog());
4934            });
4935        }
4936
4937        qlog_with_type!(QLOG_PACKET_TX, self.qlog, q, {
4938            if let Some(header) = qlog_pkt_hdr {
4939                // Qlog packet raw info described at
4940                // https://datatracker.ietf.org/doc/html/draft-ietf-quic-qlog-main-schema-00#section-5.1
4941                //
4942                // `length` includes packet headers and trailers (AEAD tag).
4943                let length = payload_len + payload_offset + crypto_overhead;
4944                let qlog_raw_info = RawInfo {
4945                    length: Some(length as u64),
4946                    payload_length: Some(payload_len as u64),
4947                    data: None,
4948                };
4949
4950                let send_at_time =
4951                    now.duration_since(q.start_time()).as_secs_f32() * 1000.0;
4952
4953                let ev_data =
4954                    EventData::PacketSent(qlog::events::quic::PacketSent {
4955                        header,
4956                        frames: Some(qlog_frames),
4957                        raw: Some(qlog_raw_info),
4958                        send_at_time: Some(send_at_time),
4959                        ..Default::default()
4960                    });
4961
4962                q.add_event_data_with_instant(ev_data, now).ok();
4963            }
4964        });
4965
4966        let aead = match crypto_ctx.crypto_seal {
4967            Some(ref v) => v,
4968            None => return Err(Error::InvalidState),
4969        };
4970
4971        let written = packet::encrypt_pkt(
4972            &mut b,
4973            pn,
4974            pn_len,
4975            payload_len,
4976            payload_offset,
4977            None,
4978            aead,
4979        )?;
4980
4981        let sent_pkt_has_data = if path.recovery.gcongestion_enabled() {
4982            has_data || dgram_emitted
4983        } else {
4984            has_data
4985        };
4986
4987        let sent_pkt = recovery::Sent {
4988            pkt_num: pn,
4989            frames,
4990            time_sent: now,
4991            time_acked: None,
4992            time_lost: None,
4993            size: if ack_eliciting { written } else { 0 },
4994            ack_eliciting,
4995            in_flight,
4996            delivered: 0,
4997            delivered_time: now,
4998            first_sent_time: now,
4999            is_app_limited: false,
5000            tx_in_flight: 0,
5001            lost: 0,
5002            has_data: sent_pkt_has_data,
5003            is_pmtud_probe,
5004        };
5005
5006        if in_flight && is_app_limited {
5007            path.recovery.delivery_rate_update_app_limited(true);
5008        }
5009
5010        self.next_pkt_num += 1;
5011
5012        let handshake_status = recovery::HandshakeStatus {
5013            has_handshake_keys: self.crypto_ctx[packet::Epoch::Handshake]
5014                .has_keys(),
5015            peer_verified_address: self.peer_verified_initial_address,
5016            completed: self.handshake_completed,
5017        };
5018
5019        self.on_packet_sent(send_pid, sent_pkt, epoch, handshake_status, now)?;
5020
5021        let path = self.paths.get_mut(send_pid)?;
5022        qlog_with_type!(QLOG_METRICS, self.qlog, q, {
5023            path.recovery.maybe_qlog(q, now);
5024        });
5025
5026        // Record sent packet size if we probe the path.
5027        if let Some(data) = challenge_data {
5028            path.add_challenge_sent(data, written, now);
5029        }
5030
5031        self.sent_count += 1;
5032        self.sent_bytes += written as u64;
5033        path.sent_count += 1;
5034        path.sent_bytes += written as u64;
5035
5036        if self.dgram_send_queue.byte_size() > path.recovery.cwnd_available() {
5037            path.recovery.update_app_limited(false);
5038        }
5039
5040        path.max_send_bytes = path.max_send_bytes.saturating_sub(written);
5041
5042        // On the client, drop initial state after sending an Handshake packet.
5043        if !self.is_server && hdr_ty == Type::Handshake {
5044            self.drop_epoch_state(packet::Epoch::Initial, now);
5045        }
5046
5047        // (Re)start the idle timer if we are sending the first ack-eliciting
5048        // packet since last receiving a packet.
5049        if ack_eliciting && !self.ack_eliciting_sent {
5050            if let Some(idle_timeout) = self.idle_timeout() {
5051                self.idle_timer = Some(now + idle_timeout);
5052            }
5053        }
5054
5055        if ack_eliciting {
5056            self.ack_eliciting_sent = true;
5057        }
5058
5059        Ok((pkt_type, written))
5060    }
5061
5062    fn on_packet_sent(
5063        &mut self, send_pid: usize, sent_pkt: recovery::Sent,
5064        epoch: packet::Epoch, handshake_status: recovery::HandshakeStatus,
5065        now: Instant,
5066    ) -> Result<()> {
5067        let path = self.paths.get_mut(send_pid)?;
5068
5069        // It's fine to set the skip counter based on a non-active path's values.
5070        let cwnd = path.recovery.cwnd();
5071        let max_datagram_size = path.recovery.max_datagram_size();
5072        self.pkt_num_spaces[epoch].on_packet_sent(&sent_pkt);
5073        self.pkt_num_manager.on_packet_sent(
5074            cwnd,
5075            max_datagram_size,
5076            self.handshake_completed,
5077        );
5078
5079        path.recovery.on_packet_sent(
5080            sent_pkt,
5081            epoch,
5082            handshake_status,
5083            now,
5084            &self.trace_id,
5085        );
5086
5087        Ok(())
5088    }
5089
5090    /// Returns the desired send time for the next packet.
5091    #[inline]
5092    pub fn get_next_release_time(&self) -> Option<ReleaseDecision> {
5093        Some(
5094            self.paths
5095                .get_active()
5096                .ok()?
5097                .recovery
5098                .get_next_release_time(),
5099        )
5100    }
5101
5102    /// Returns whether gcongestion is enabled.
5103    #[inline]
5104    pub fn gcongestion_enabled(&self) -> Option<bool> {
5105        Some(self.paths.get_active().ok()?.recovery.gcongestion_enabled())
5106    }
5107
5108    /// Returns the maximum pacing into the future.
5109    ///
5110    /// Equals 1/8 of the smoothed RTT, but at least 1ms and not greater than
5111    /// 5ms.
5112    pub fn max_release_into_future(&self) -> Duration {
5113        self.paths
5114            .get_active()
5115            .map(|p| p.recovery.rtt().mul_f64(0.125))
5116            .unwrap_or(Duration::from_millis(1))
5117            .max(Duration::from_millis(1))
5118            .min(Duration::from_millis(5))
5119    }
5120
5121    /// Returns whether pacing is enabled.
5122    #[inline]
5123    pub fn pacing_enabled(&self) -> bool {
5124        self.recovery_config.pacing
5125    }
5126
5127    /// Returns the size of the send quantum, in bytes.
5128    ///
5129    /// This represents the maximum size of a packet burst as determined by the
5130    /// congestion control algorithm in use.
5131    ///
5132    /// Applications can, for example, use it in conjunction with segmentation
5133    /// offloading mechanisms as the maximum limit for outgoing aggregates of
5134    /// multiple packets.
5135    #[inline]
5136    pub fn send_quantum(&self) -> usize {
5137        match self.paths.get_active() {
5138            Ok(p) => p.recovery.send_quantum(),
5139            _ => 0,
5140        }
5141    }
5142
5143    /// Returns the size of the send quantum over the given 4-tuple, in bytes.
5144    ///
5145    /// This represents the maximum size of a packet burst as determined by the
5146    /// congestion control algorithm in use.
5147    ///
5148    /// Applications can, for example, use it in conjunction with segmentation
5149    /// offloading mechanisms as the maximum limit for outgoing aggregates of
5150    /// multiple packets.
5151    ///
5152    /// If the (`local_addr`, peer_addr`) 4-tuple relates to a non-existing
5153    /// path, this method returns 0.
5154    pub fn send_quantum_on_path(
5155        &self, local_addr: SocketAddr, peer_addr: SocketAddr,
5156    ) -> usize {
5157        self.paths
5158            .path_id_from_addrs(&(local_addr, peer_addr))
5159            .and_then(|pid| self.paths.get(pid).ok())
5160            .map(|path| path.recovery.send_quantum())
5161            .unwrap_or(0)
5162    }
5163
5164    /// Reads contiguous data from a stream into the provided slice.
5165    ///
5166    /// The slice must be sized by the caller and will be populated up to its
5167    /// capacity.
5168    ///
5169    /// On success the amount of bytes read and a flag indicating the fin state
5170    /// is returned as a tuple, or [`Done`] if there is no data to read.
5171    ///
5172    /// Reading data from a stream may trigger queueing of control messages
5173    /// (e.g. MAX_STREAM_DATA). [`send()`] should be called after reading.
5174    ///
5175    /// [`Done`]: enum.Error.html#variant.Done
5176    /// [`send()`]: struct.Connection.html#method.send
5177    ///
5178    /// ## Examples:
5179    ///
5180    /// ```no_run
5181    /// # let mut buf = [0; 512];
5182    /// # let socket = std::net::UdpSocket::bind("127.0.0.1:0").unwrap();
5183    /// # let mut config = quiche::Config::new(quiche::PROTOCOL_VERSION)?;
5184    /// # let scid = quiche::ConnectionId::from_ref(&[0xba; 16]);
5185    /// # let peer = "127.0.0.1:1234".parse().unwrap();
5186    /// # let local = socket.local_addr().unwrap();
5187    /// # let mut conn = quiche::accept(&scid, None, local, peer, &mut config)?;
5188    /// # let stream_id = 0;
5189    /// while let Ok((read, fin)) = conn.stream_recv(stream_id, &mut buf) {
5190    ///     println!("Got {} bytes on stream {}", read, stream_id);
5191    /// }
5192    /// # Ok::<(), quiche::Error>(())
5193    /// ```
5194    pub fn stream_recv(
5195        &mut self, stream_id: u64, out: &mut [u8],
5196    ) -> Result<(usize, bool)> {
5197        // We can't read on our own unidirectional streams.
5198        if !stream::is_bidi(stream_id) &&
5199            stream::is_local(stream_id, self.is_server)
5200        {
5201            return Err(Error::InvalidStreamState(stream_id));
5202        }
5203
5204        let stream = self
5205            .streams
5206            .get_mut(stream_id)
5207            .ok_or(Error::InvalidStreamState(stream_id))?;
5208
5209        if !stream.is_readable() {
5210            return Err(Error::Done);
5211        }
5212
5213        let local = stream.local;
5214        let priority_key = Arc::clone(&stream.priority_key);
5215
5216        #[cfg(feature = "qlog")]
5217        let offset = stream.recv.off_front();
5218
5219        let (read, fin) = match stream.recv.emit(out) {
5220            Ok(v) => v,
5221
5222            Err(e) => {
5223                // Collect the stream if it is now complete. This can happen if
5224                // we got a `StreamReset` error which will now be propagated to
5225                // the application, so we don't need to keep the stream's state
5226                // anymore.
5227                if stream.is_complete() {
5228                    self.streams.collect(stream_id, local);
5229                }
5230
5231                self.streams.remove_readable(&priority_key);
5232                return Err(e);
5233            },
5234        };
5235
5236        self.flow_control.add_consumed(read as u64);
5237
5238        let readable = stream.is_readable();
5239
5240        let complete = stream.is_complete();
5241
5242        if stream.recv.almost_full() {
5243            self.streams.insert_almost_full(stream_id);
5244        }
5245
5246        if !readable {
5247            self.streams.remove_readable(&priority_key);
5248        }
5249
5250        if complete {
5251            self.streams.collect(stream_id, local);
5252        }
5253
5254        qlog_with_type!(QLOG_DATA_MV, self.qlog, q, {
5255            let ev_data = EventData::DataMoved(qlog::events::quic::DataMoved {
5256                stream_id: Some(stream_id),
5257                offset: Some(offset),
5258                length: Some(read as u64),
5259                from: Some(DataRecipient::Transport),
5260                to: Some(DataRecipient::Application),
5261                ..Default::default()
5262            });
5263
5264            let now = Instant::now();
5265            q.add_event_data_with_instant(ev_data, now).ok();
5266        });
5267
5268        if self.should_update_max_data() {
5269            self.almost_full = true;
5270        }
5271
5272        if priority_key.incremental && readable {
5273            // Shuffle the incremental stream to the back of the queue.
5274            self.streams.remove_readable(&priority_key);
5275            self.streams.insert_readable(&priority_key);
5276        }
5277
5278        Ok((read, fin))
5279    }
5280
5281    /// Writes data to a stream.
5282    ///
5283    /// On success the number of bytes written is returned, or [`Done`] if no
5284    /// data was written (e.g. because the stream has no capacity).
5285    ///
5286    /// Applications can provide a 0-length buffer with the fin flag set to
5287    /// true. This will lead to a 0-length FIN STREAM frame being sent at the
5288    /// latest offset. The `Ok(0)` value is only returned when the application
5289    /// provided a 0-length buffer.
5290    ///
5291    /// In addition, if the peer has signalled that it doesn't want to receive
5292    /// any more data from this stream by sending the `STOP_SENDING` frame, the
5293    /// [`StreamStopped`] error will be returned instead of any data.
5294    ///
5295    /// Note that in order to avoid buffering an infinite amount of data in the
5296    /// stream's send buffer, streams are only allowed to buffer outgoing data
5297    /// up to the amount that the peer allows it to send (that is, up to the
5298    /// stream's outgoing flow control capacity).
5299    ///
5300    /// This means that the number of written bytes returned can be lower than
5301    /// the length of the input buffer when the stream doesn't have enough
5302    /// capacity for the operation to complete. The application should retry the
5303    /// operation once the stream is reported as writable again.
5304    ///
5305    /// Applications should call this method only after the handshake is
5306    /// completed (whenever [`is_established()`] returns `true`) or during
5307    /// early data if enabled (whenever [`is_in_early_data()`] returns `true`).
5308    ///
5309    /// [`Done`]: enum.Error.html#variant.Done
5310    /// [`StreamStopped`]: enum.Error.html#variant.StreamStopped
5311    /// [`is_established()`]: struct.Connection.html#method.is_established
5312    /// [`is_in_early_data()`]: struct.Connection.html#method.is_in_early_data
5313    ///
5314    /// ## Examples:
5315    ///
5316    /// ```no_run
5317    /// # let mut buf = [0; 512];
5318    /// # let socket = std::net::UdpSocket::bind("127.0.0.1:0").unwrap();
5319    /// # let mut config = quiche::Config::new(quiche::PROTOCOL_VERSION)?;
5320    /// # let scid = quiche::ConnectionId::from_ref(&[0xba; 16]);
5321    /// # let peer = "127.0.0.1:1234".parse().unwrap();
5322    /// # let local = "127.0.0.1:4321".parse().unwrap();
5323    /// # let mut conn = quiche::accept(&scid, None, local, peer, &mut config)?;
5324    /// # let stream_id = 0;
5325    /// conn.stream_send(stream_id, b"hello", true)?;
5326    /// # Ok::<(), quiche::Error>(())
5327    /// ```
5328    pub fn stream_send(
5329        &mut self, stream_id: u64, buf: &[u8], fin: bool,
5330    ) -> Result<usize> {
5331        self.stream_do_send(
5332            stream_id,
5333            buf,
5334            fin,
5335            |stream: &mut stream::Stream<F>,
5336             buf: &[u8],
5337             cap: usize,
5338             fin: bool| {
5339                stream.send.write(&buf[..cap], fin).map(|v| (v, v))
5340            },
5341        )
5342    }
5343
5344    /// Writes data to a stream with zero copying, instead, it appends the
5345    /// provided buffer directly to the send queue if the capacity allows
5346    /// it.
5347    ///
5348    /// When a partial write happens (including when [`Error::Done`] is
5349    /// returned) the remaining (unwritten) buffer will also be returned.
5350    /// The application should retry the operation once the stream is
5351    /// reported as writable again.
5352    pub fn stream_send_zc(
5353        &mut self, stream_id: u64, buf: F::Buf, len: Option<usize>, fin: bool,
5354    ) -> Result<(usize, Option<F::Buf>)>
5355    where
5356        F::Buf: BufSplit,
5357    {
5358        self.stream_do_send(
5359            stream_id,
5360            buf,
5361            fin,
5362            |stream: &mut stream::Stream<F>,
5363             buf: F::Buf,
5364             cap: usize,
5365             fin: bool| {
5366                let len = len.unwrap_or(usize::MAX).min(cap);
5367                let (sent, remaining) = stream.send.append_buf(buf, len, fin)?;
5368                Ok((sent, (sent, remaining)))
5369            },
5370        )
5371    }
5372
5373    fn stream_do_send<B, R, SND>(
5374        &mut self, stream_id: u64, buf: B, fin: bool, write_fn: SND,
5375    ) -> Result<R>
5376    where
5377        B: AsRef<[u8]>,
5378        SND: FnOnce(&mut stream::Stream<F>, B, usize, bool) -> Result<(usize, R)>,
5379    {
5380        // We can't write on the peer's unidirectional streams.
5381        if !stream::is_bidi(stream_id) &&
5382            !stream::is_local(stream_id, self.is_server)
5383        {
5384            return Err(Error::InvalidStreamState(stream_id));
5385        }
5386
5387        let len = buf.as_ref().len();
5388
5389        // Mark the connection as blocked if the connection-level flow control
5390        // limit doesn't let us buffer all the data.
5391        //
5392        // Note that this is separate from "send capacity" as that also takes
5393        // congestion control into consideration.
5394        if self.max_tx_data - self.tx_data < len as u64 {
5395            self.blocked_limit = Some(self.max_tx_data);
5396        }
5397
5398        let cap = self.tx_cap;
5399
5400        // Get existing stream or create a new one.
5401        let stream = self.get_or_create_stream(stream_id, true)?;
5402
5403        #[cfg(feature = "qlog")]
5404        let offset = stream.send.off_back();
5405
5406        let was_writable = stream.is_writable();
5407
5408        let was_flushable = stream.is_flushable();
5409
5410        let is_complete = stream.is_complete();
5411        let is_readable = stream.is_readable();
5412
5413        let priority_key = Arc::clone(&stream.priority_key);
5414
5415        // Return early if the stream has been stopped, and collect its state
5416        // if complete.
5417        if let Err(Error::StreamStopped(e)) = stream.send.cap() {
5418            // Only collect the stream if it is complete and not readable.
5419            // If it is readable, it will get collected when stream_recv()
5420            // is used.
5421            //
5422            // The stream can't be writable if it has been stopped.
5423            if is_complete && !is_readable {
5424                let local = stream.local;
5425                self.streams.collect(stream_id, local);
5426            }
5427
5428            return Err(Error::StreamStopped(e));
5429        };
5430
5431        // Truncate the input buffer based on the connection's send capacity if
5432        // necessary.
5433        //
5434        // When the cap is zero, the method returns Ok(0) *only* when the passed
5435        // buffer is empty. We return Error::Done otherwise.
5436        if cap == 0 && len > 0 {
5437            if was_writable {
5438                // When `stream_writable_next()` returns a stream, the writable
5439                // mark is removed, but because the stream is blocked by the
5440                // connection-level send capacity it won't be marked as writable
5441                // again once the capacity increases.
5442                //
5443                // Since the stream is writable already, mark it here instead.
5444                self.streams.insert_writable(&priority_key);
5445            }
5446
5447            return Err(Error::Done);
5448        }
5449
5450        let (cap, fin, blocked_by_cap) = if cap < len {
5451            (cap, false, true)
5452        } else {
5453            (len, fin, false)
5454        };
5455
5456        let (sent, ret) = match write_fn(stream, buf, cap, fin) {
5457            Ok(v) => v,
5458
5459            Err(e) => {
5460                self.streams.remove_writable(&priority_key);
5461                return Err(e);
5462            },
5463        };
5464
5465        let incremental = stream.incremental;
5466        let priority_key = Arc::clone(&stream.priority_key);
5467
5468        let flushable = stream.is_flushable();
5469
5470        let writable = stream.is_writable();
5471
5472        let empty_fin = len == 0 && fin;
5473
5474        if sent < cap {
5475            let max_off = stream.send.max_off();
5476
5477            if stream.send.blocked_at() != Some(max_off) {
5478                stream.send.update_blocked_at(Some(max_off));
5479                self.streams.insert_blocked(stream_id, max_off);
5480            }
5481        } else {
5482            stream.send.update_blocked_at(None);
5483            self.streams.remove_blocked(stream_id);
5484        }
5485
5486        // If the stream is now flushable push it to the flushable queue, but
5487        // only if it wasn't already queued.
5488        //
5489        // Consider the stream flushable also when we are sending a zero-length
5490        // frame that has the fin flag set.
5491        if (flushable || empty_fin) && !was_flushable {
5492            self.streams.insert_flushable(&priority_key);
5493        }
5494
5495        if !writable {
5496            self.streams.remove_writable(&priority_key);
5497        } else if was_writable && blocked_by_cap {
5498            // When `stream_writable_next()` returns a stream, the writable
5499            // mark is removed, but because the stream is blocked by the
5500            // connection-level send capacity it won't be marked as writable
5501            // again once the capacity increases.
5502            //
5503            // Since the stream is writable already, mark it here instead.
5504            self.streams.insert_writable(&priority_key);
5505        }
5506
5507        self.tx_cap -= sent;
5508
5509        self.tx_data += sent as u64;
5510
5511        self.tx_buffered += sent;
5512        self.check_tx_buffered_invariant();
5513
5514        qlog_with_type!(QLOG_DATA_MV, self.qlog, q, {
5515            let ev_data = EventData::DataMoved(qlog::events::quic::DataMoved {
5516                stream_id: Some(stream_id),
5517                offset: Some(offset),
5518                length: Some(sent as u64),
5519                from: Some(DataRecipient::Application),
5520                to: Some(DataRecipient::Transport),
5521                ..Default::default()
5522            });
5523
5524            let now = Instant::now();
5525            q.add_event_data_with_instant(ev_data, now).ok();
5526        });
5527
5528        if sent == 0 && cap > 0 {
5529            return Err(Error::Done);
5530        }
5531
5532        if incremental && writable {
5533            // Shuffle the incremental stream to the back of the queue.
5534            self.streams.remove_writable(&priority_key);
5535            self.streams.insert_writable(&priority_key);
5536        }
5537
5538        Ok(ret)
5539    }
5540
5541    /// Sets the priority for a stream.
5542    ///
5543    /// A stream's priority determines the order in which stream data is sent
5544    /// on the wire (streams with lower priority are sent first). Streams are
5545    /// created with a default priority of `127`.
5546    ///
5547    /// The target stream is created if it did not exist before calling this
5548    /// method.
5549    pub fn stream_priority(
5550        &mut self, stream_id: u64, urgency: u8, incremental: bool,
5551    ) -> Result<()> {
5552        // Get existing stream or create a new one, but if the stream
5553        // has already been closed and collected, ignore the prioritization.
5554        let stream = match self.get_or_create_stream(stream_id, true) {
5555            Ok(v) => v,
5556
5557            Err(Error::Done) => return Ok(()),
5558
5559            Err(e) => return Err(e),
5560        };
5561
5562        if stream.urgency == urgency && stream.incremental == incremental {
5563            return Ok(());
5564        }
5565
5566        stream.urgency = urgency;
5567        stream.incremental = incremental;
5568
5569        let new_priority_key = Arc::new(StreamPriorityKey {
5570            urgency: stream.urgency,
5571            incremental: stream.incremental,
5572            id: stream_id,
5573            ..Default::default()
5574        });
5575
5576        let old_priority_key =
5577            std::mem::replace(&mut stream.priority_key, new_priority_key.clone());
5578
5579        self.streams
5580            .update_priority(&old_priority_key, &new_priority_key);
5581
5582        Ok(())
5583    }
5584
5585    /// Shuts down reading or writing from/to the specified stream.
5586    ///
5587    /// When the `direction` argument is set to [`Shutdown::Read`], outstanding
5588    /// data in the stream's receive buffer is dropped, and no additional data
5589    /// is added to it. Data received after calling this method is still
5590    /// validated and acked but not stored, and [`stream_recv()`] will not
5591    /// return it to the application. In addition, a `STOP_SENDING` frame will
5592    /// be sent to the peer to signal it to stop sending data.
5593    ///
5594    /// When the `direction` argument is set to [`Shutdown::Write`], outstanding
5595    /// data in the stream's send buffer is dropped, and no additional data is
5596    /// added to it. Data passed to [`stream_send()`] after calling this method
5597    /// will be ignored. In addition, a `RESET_STREAM` frame will be sent to the
5598    /// peer to signal the reset.
5599    ///
5600    /// Locally-initiated unidirectional streams can only be closed in the
5601    /// [`Shutdown::Write`] direction. Remotely-initiated unidirectional streams
5602    /// can only be closed in the [`Shutdown::Read`] direction. Using an
5603    /// incorrect direction will return [`InvalidStreamState`].
5604    ///
5605    /// [`Shutdown::Read`]: enum.Shutdown.html#variant.Read
5606    /// [`Shutdown::Write`]: enum.Shutdown.html#variant.Write
5607    /// [`stream_recv()`]: struct.Connection.html#method.stream_recv
5608    /// [`stream_send()`]: struct.Connection.html#method.stream_send
5609    /// [`InvalidStreamState`]: enum.Error.html#variant.InvalidStreamState
5610    pub fn stream_shutdown(
5611        &mut self, stream_id: u64, direction: Shutdown, err: u64,
5612    ) -> Result<()> {
5613        // Don't try to stop a local unidirectional stream.
5614        if direction == Shutdown::Read &&
5615            stream::is_local(stream_id, self.is_server) &&
5616            !stream::is_bidi(stream_id)
5617        {
5618            return Err(Error::InvalidStreamState(stream_id));
5619        }
5620
5621        // Don't try to reset a remote unidirectional stream.
5622        if direction == Shutdown::Write &&
5623            !stream::is_local(stream_id, self.is_server) &&
5624            !stream::is_bidi(stream_id)
5625        {
5626            return Err(Error::InvalidStreamState(stream_id));
5627        }
5628
5629        // Get existing stream.
5630        let stream = self.streams.get_mut(stream_id).ok_or(Error::Done)?;
5631
5632        let priority_key = Arc::clone(&stream.priority_key);
5633
5634        match direction {
5635            Shutdown::Read => {
5636                let consumed = stream.recv.shutdown()?;
5637                self.flow_control.add_consumed(consumed);
5638                if self.flow_control.should_update_max_data() {
5639                    self.almost_full = true;
5640                }
5641
5642                if !stream.recv.is_fin() {
5643                    self.streams.insert_stopped(stream_id, err);
5644                }
5645
5646                // Once shutdown, the stream is guaranteed to be non-readable.
5647                self.streams.remove_readable(&priority_key);
5648
5649                self.stopped_stream_local_count =
5650                    self.stopped_stream_local_count.saturating_add(1);
5651            },
5652
5653            Shutdown::Write => {
5654                let (final_size, unsent) = stream.send.shutdown()?;
5655
5656                // Claw back some flow control allowance from data that was
5657                // buffered but not actually sent before the stream was reset.
5658                self.tx_data = self.tx_data.saturating_sub(unsent);
5659
5660                self.tx_buffered =
5661                    self.tx_buffered.saturating_sub(unsent as usize);
5662
5663                // These drops in qlog are a bit weird, but the only way to ensure
5664                // that all bytes that are moved from App to Transport in
5665                // stream_do_send are eventually moved from Transport to Dropped.
5666                // Ideally we would add a Transport to Network transition also as
5667                // a way to indicate when bytes were transmitted vs dropped
5668                // without ever being sent.
5669                qlog_with_type!(QLOG_DATA_MV, self.qlog, q, {
5670                    let ev_data =
5671                        EventData::DataMoved(qlog::events::quic::DataMoved {
5672                            stream_id: Some(stream_id),
5673                            offset: Some(final_size),
5674                            length: Some(unsent),
5675                            from: Some(DataRecipient::Transport),
5676                            to: Some(DataRecipient::Dropped),
5677                            ..Default::default()
5678                        });
5679
5680                    q.add_event_data_with_instant(ev_data, Instant::now()).ok();
5681                });
5682
5683                // Update send capacity.
5684                self.update_tx_cap();
5685
5686                self.streams.insert_reset(stream_id, err, final_size);
5687
5688                // Once shutdown, the stream is guaranteed to be non-writable.
5689                self.streams.remove_writable(&priority_key);
5690
5691                self.reset_stream_local_count =
5692                    self.reset_stream_local_count.saturating_add(1);
5693            },
5694        }
5695
5696        Ok(())
5697    }
5698
5699    /// Returns the stream's send capacity in bytes.
5700    ///
5701    /// If the specified stream doesn't exist (including when it has already
5702    /// been completed and closed), the [`InvalidStreamState`] error will be
5703    /// returned.
5704    ///
5705    /// In addition, if the peer has signalled that it doesn't want to receive
5706    /// any more data from this stream by sending the `STOP_SENDING` frame, the
5707    /// [`StreamStopped`] error will be returned.
5708    ///
5709    /// [`InvalidStreamState`]: enum.Error.html#variant.InvalidStreamState
5710    /// [`StreamStopped`]: enum.Error.html#variant.StreamStopped
5711    #[inline]
5712    pub fn stream_capacity(&mut self, stream_id: u64) -> Result<usize> {
5713        if let Some(stream) = self.streams.get(stream_id) {
5714            let stream_cap = match stream.send.cap() {
5715                Ok(v) => v,
5716
5717                Err(Error::StreamStopped(e)) => {
5718                    // Only collect the stream if it is complete and not
5719                    // readable. If it is readable, it will get collected when
5720                    // stream_recv() is used.
5721                    if stream.is_complete() && !stream.is_readable() {
5722                        let local = stream.local;
5723                        self.streams.collect(stream_id, local);
5724                    }
5725
5726                    return Err(Error::StreamStopped(e));
5727                },
5728
5729                Err(e) => return Err(e),
5730            };
5731
5732            let cap = cmp::min(self.tx_cap, stream_cap);
5733            return Ok(cap);
5734        };
5735
5736        Err(Error::InvalidStreamState(stream_id))
5737    }
5738
5739    /// Returns the next stream that has data to read.
5740    ///
5741    /// Note that once returned by this method, a stream ID will not be returned
5742    /// again until it is "re-armed".
5743    ///
5744    /// The application will need to read all of the pending data on the stream,
5745    /// and new data has to be received before the stream is reported again.
5746    ///
5747    /// This is unlike the [`readable()`] method, that returns the same list of
5748    /// readable streams when called multiple times in succession.
5749    ///
5750    /// [`readable()`]: struct.Connection.html#method.readable
5751    pub fn stream_readable_next(&mut self) -> Option<u64> {
5752        let priority_key = self.streams.readable.front().clone_pointer()?;
5753
5754        self.streams.remove_readable(&priority_key);
5755
5756        Some(priority_key.id)
5757    }
5758
5759    /// Returns true if the stream has data that can be read.
5760    pub fn stream_readable(&self, stream_id: u64) -> bool {
5761        let stream = match self.streams.get(stream_id) {
5762            Some(v) => v,
5763
5764            None => return false,
5765        };
5766
5767        stream.is_readable()
5768    }
5769
5770    /// Returns the next stream that can be written to.
5771    ///
5772    /// Note that once returned by this method, a stream ID will not be returned
5773    /// again until it is "re-armed".
5774    ///
5775    /// This is unlike the [`writable()`] method, that returns the same list of
5776    /// writable streams when called multiple times in succession. It is not
5777    /// advised to use both `stream_writable_next()` and [`writable()`] on the
5778    /// same connection, as it may lead to unexpected results.
5779    ///
5780    /// The [`stream_writable()`] method can also be used to fine-tune when a
5781    /// stream is reported as writable again.
5782    ///
5783    /// [`stream_writable()`]: struct.Connection.html#method.stream_writable
5784    /// [`writable()`]: struct.Connection.html#method.writable
5785    pub fn stream_writable_next(&mut self) -> Option<u64> {
5786        // If there is not enough connection-level send capacity, none of the
5787        // streams are writable.
5788        if self.tx_cap == 0 {
5789            return None;
5790        }
5791
5792        let mut cursor = self.streams.writable.front();
5793
5794        while let Some(priority_key) = cursor.clone_pointer() {
5795            if let Some(stream) = self.streams.get(priority_key.id) {
5796                let cap = match stream.send.cap() {
5797                    Ok(v) => v,
5798
5799                    // Return the stream to the application immediately if it's
5800                    // stopped.
5801                    Err(_) =>
5802                        return {
5803                            self.streams.remove_writable(&priority_key);
5804
5805                            Some(priority_key.id)
5806                        },
5807                };
5808
5809                if cmp::min(self.tx_cap, cap) >= stream.send_lowat {
5810                    self.streams.remove_writable(&priority_key);
5811                    return Some(priority_key.id);
5812                }
5813            }
5814
5815            cursor.move_next();
5816        }
5817
5818        None
5819    }
5820
5821    /// Returns true if the stream has enough send capacity.
5822    ///
5823    /// When `len` more bytes can be buffered into the given stream's send
5824    /// buffer, `true` will be returned, `false` otherwise.
5825    ///
5826    /// In the latter case, if the additional data can't be buffered due to
5827    /// flow control limits, the peer will also be notified, and a "low send
5828    /// watermark" will be set for the stream, such that it is not going to be
5829    /// reported as writable again by [`stream_writable_next()`] until its send
5830    /// capacity reaches `len`.
5831    ///
5832    /// If the specified stream doesn't exist (including when it has already
5833    /// been completed and closed), the [`InvalidStreamState`] error will be
5834    /// returned.
5835    ///
5836    /// In addition, if the peer has signalled that it doesn't want to receive
5837    /// any more data from this stream by sending the `STOP_SENDING` frame, the
5838    /// [`StreamStopped`] error will be returned.
5839    ///
5840    /// [`stream_writable_next()`]: struct.Connection.html#method.stream_writable_next
5841    /// [`InvalidStreamState`]: enum.Error.html#variant.InvalidStreamState
5842    /// [`StreamStopped`]: enum.Error.html#variant.StreamStopped
5843    #[inline]
5844    pub fn stream_writable(
5845        &mut self, stream_id: u64, len: usize,
5846    ) -> Result<bool> {
5847        if self.stream_capacity(stream_id)? >= len {
5848            return Ok(true);
5849        }
5850
5851        let stream = match self.streams.get_mut(stream_id) {
5852            Some(v) => v,
5853
5854            None => return Err(Error::InvalidStreamState(stream_id)),
5855        };
5856
5857        stream.send_lowat = cmp::max(1, len);
5858
5859        let is_writable = stream.is_writable();
5860
5861        let priority_key = Arc::clone(&stream.priority_key);
5862
5863        if self.max_tx_data - self.tx_data < len as u64 {
5864            self.blocked_limit = Some(self.max_tx_data);
5865        }
5866
5867        if stream.send.cap()? < len {
5868            let max_off = stream.send.max_off();
5869            if stream.send.blocked_at() != Some(max_off) {
5870                stream.send.update_blocked_at(Some(max_off));
5871                self.streams.insert_blocked(stream_id, max_off);
5872            }
5873        } else if is_writable {
5874            // When `stream_writable_next()` returns a stream, the writable
5875            // mark is removed, but because the stream is blocked by the
5876            // connection-level send capacity it won't be marked as writable
5877            // again once the capacity increases.
5878            //
5879            // Since the stream is writable already, mark it here instead.
5880            self.streams.insert_writable(&priority_key);
5881        }
5882
5883        Ok(false)
5884    }
5885
5886    /// Returns true if all the data has been read from the specified stream.
5887    ///
5888    /// This instructs the application that all the data received from the
5889    /// peer on the stream has been read, and there won't be anymore in the
5890    /// future.
5891    ///
5892    /// Basically this returns true when the peer either set the `fin` flag
5893    /// for the stream, or sent `RESET_STREAM`.
5894    #[inline]
5895    pub fn stream_finished(&self, stream_id: u64) -> bool {
5896        let stream = match self.streams.get(stream_id) {
5897            Some(v) => v,
5898
5899            None => return true,
5900        };
5901
5902        stream.recv.is_fin()
5903    }
5904
5905    /// Returns the number of bidirectional streams that can be created
5906    /// before the peer's stream count limit is reached.
5907    ///
5908    /// This can be useful to know if it's possible to create a bidirectional
5909    /// stream without trying it first.
5910    #[inline]
5911    pub fn peer_streams_left_bidi(&self) -> u64 {
5912        self.streams.peer_streams_left_bidi()
5913    }
5914
5915    /// Returns the number of unidirectional streams that can be created
5916    /// before the peer's stream count limit is reached.
5917    ///
5918    /// This can be useful to know if it's possible to create a unidirectional
5919    /// stream without trying it first.
5920    #[inline]
5921    pub fn peer_streams_left_uni(&self) -> u64 {
5922        self.streams.peer_streams_left_uni()
5923    }
5924
5925    /// Returns an iterator over streams that have outstanding data to read.
5926    ///
5927    /// Note that the iterator will only include streams that were readable at
5928    /// the time the iterator itself was created (i.e. when `readable()` was
5929    /// called). To account for newly readable streams, the iterator needs to
5930    /// be created again.
5931    ///
5932    /// ## Examples:
5933    ///
5934    /// ```no_run
5935    /// # let mut buf = [0; 512];
5936    /// # let socket = std::net::UdpSocket::bind("127.0.0.1:0").unwrap();
5937    /// # let mut config = quiche::Config::new(quiche::PROTOCOL_VERSION)?;
5938    /// # let scid = quiche::ConnectionId::from_ref(&[0xba; 16]);
5939    /// # let peer = "127.0.0.1:1234".parse().unwrap();
5940    /// # let local = socket.local_addr().unwrap();
5941    /// # let mut conn = quiche::accept(&scid, None, local, peer, &mut config)?;
5942    /// // Iterate over readable streams.
5943    /// for stream_id in conn.readable() {
5944    ///     // Stream is readable, read until there's no more data.
5945    ///     while let Ok((read, fin)) = conn.stream_recv(stream_id, &mut buf) {
5946    ///         println!("Got {} bytes on stream {}", read, stream_id);
5947    ///     }
5948    /// }
5949    /// # Ok::<(), quiche::Error>(())
5950    /// ```
5951    #[inline]
5952    pub fn readable(&self) -> StreamIter {
5953        self.streams.readable()
5954    }
5955
5956    /// Returns an iterator over streams that can be written in priority order.
5957    ///
5958    /// The priority order is based on RFC 9218 scheduling recommendations.
5959    /// Stream priority can be controlled using [`stream_priority()`]. In order
5960    /// to support fairness requirements, each time this method is called,
5961    /// internal state is updated. Therefore the iterator ordering can change
5962    /// between calls, even if no streams were added or removed.
5963    ///
5964    /// A "writable" stream is a stream that has enough flow control capacity to
5965    /// send data to the peer. To avoid buffering an infinite amount of data,
5966    /// streams are only allowed to buffer outgoing data up to the amount that
5967    /// the peer allows to send.
5968    ///
5969    /// Note that the iterator will only include streams that were writable at
5970    /// the time the iterator itself was created (i.e. when `writable()` was
5971    /// called). To account for newly writable streams, the iterator needs to be
5972    /// created again.
5973    ///
5974    /// ## Examples:
5975    ///
5976    /// ```no_run
5977    /// # let mut buf = [0; 512];
5978    /// # let socket = std::net::UdpSocket::bind("127.0.0.1:0").unwrap();
5979    /// # let mut config = quiche::Config::new(quiche::PROTOCOL_VERSION)?;
5980    /// # let scid = quiche::ConnectionId::from_ref(&[0xba; 16]);
5981    /// # let local = socket.local_addr().unwrap();
5982    /// # let peer = "127.0.0.1:1234".parse().unwrap();
5983    /// # let mut conn = quiche::accept(&scid, None, local, peer, &mut config)?;
5984    /// // Iterate over writable streams.
5985    /// for stream_id in conn.writable() {
5986    ///     // Stream is writable, write some data.
5987    ///     if let Ok(written) = conn.stream_send(stream_id, &buf, false) {
5988    ///         println!("Written {} bytes on stream {}", written, stream_id);
5989    ///     }
5990    /// }
5991    /// # Ok::<(), quiche::Error>(())
5992    /// ```
5993    /// [`stream_priority()`]: struct.Connection.html#method.stream_priority
5994    #[inline]
5995    pub fn writable(&self) -> StreamIter {
5996        // If there is not enough connection-level send capacity, none of the
5997        // streams are writable, so return an empty iterator.
5998        if self.tx_cap == 0 {
5999            return StreamIter::default();
6000        }
6001
6002        self.streams.writable()
6003    }
6004
6005    /// Returns the maximum possible size of egress UDP payloads.
6006    ///
6007    /// This is the maximum size of UDP payloads that can be sent, and depends
6008    /// on both the configured maximum send payload size of the local endpoint
6009    /// (as configured with [`set_max_send_udp_payload_size()`]), as well as
6010    /// the transport parameter advertised by the remote peer.
6011    ///
6012    /// Note that this value can change during the lifetime of the connection,
6013    /// but should remain stable across consecutive calls to [`send()`].
6014    ///
6015    /// [`set_max_send_udp_payload_size()`]:
6016    ///     struct.Config.html#method.set_max_send_udp_payload_size
6017    /// [`send()`]: struct.Connection.html#method.send
6018    pub fn max_send_udp_payload_size(&self) -> usize {
6019        let max_datagram_size = self
6020            .paths
6021            .get_active()
6022            .ok()
6023            .map(|p| p.recovery.max_datagram_size());
6024
6025        if let Some(max_datagram_size) = max_datagram_size {
6026            if self.is_established() {
6027                // We cap the maximum packet size to 16KB or so, so that it can be
6028                // always encoded with a 2-byte varint.
6029                return cmp::min(16383, max_datagram_size);
6030            }
6031        }
6032
6033        // Allow for 1200 bytes (minimum QUIC packet size) during the
6034        // handshake.
6035        MIN_CLIENT_INITIAL_LEN
6036    }
6037
6038    /// Schedule an ack-eliciting packet on the active path.
6039    ///
6040    /// QUIC packets might not contain ack-eliciting frames during normal
6041    /// operating conditions. If the packet would already contain
6042    /// ack-eliciting frames, this method does not change any behavior.
6043    /// However, if the packet would not ordinarily contain ack-eliciting
6044    /// frames, this method ensures that a PING frame sent.
6045    ///
6046    /// Calling this method multiple times before [`send()`] has no effect.
6047    ///
6048    /// [`send()`]: struct.Connection.html#method.send
6049    pub fn send_ack_eliciting(&mut self) -> Result<()> {
6050        if self.is_closed() || self.is_draining() {
6051            return Ok(());
6052        }
6053        self.paths.get_active_mut()?.needs_ack_eliciting = true;
6054        Ok(())
6055    }
6056
6057    /// Schedule an ack-eliciting packet on the specified path.
6058    ///
6059    /// See [`send_ack_eliciting()`] for more detail. [`InvalidState`] is
6060    /// returned if there is no record of the path.
6061    ///
6062    /// [`send_ack_eliciting()`]: struct.Connection.html#method.send_ack_eliciting
6063    /// [`InvalidState`]: enum.Error.html#variant.InvalidState
6064    pub fn send_ack_eliciting_on_path(
6065        &mut self, local: SocketAddr, peer: SocketAddr,
6066    ) -> Result<()> {
6067        if self.is_closed() || self.is_draining() {
6068            return Ok(());
6069        }
6070        let path_id = self
6071            .paths
6072            .path_id_from_addrs(&(local, peer))
6073            .ok_or(Error::InvalidState)?;
6074        self.paths.get_mut(path_id)?.needs_ack_eliciting = true;
6075        Ok(())
6076    }
6077
6078    /// Reads the first received DATAGRAM.
6079    ///
6080    /// On success the DATAGRAM's data is returned along with its size.
6081    ///
6082    /// [`Done`] is returned if there is no data to read.
6083    ///
6084    /// [`BufferTooShort`] is returned if the provided buffer is too small for
6085    /// the DATAGRAM.
6086    ///
6087    /// [`Done`]: enum.Error.html#variant.Done
6088    /// [`BufferTooShort`]: enum.Error.html#variant.BufferTooShort
6089    ///
6090    /// ## Examples:
6091    ///
6092    /// ```no_run
6093    /// # let mut buf = [0; 512];
6094    /// # let socket = std::net::UdpSocket::bind("127.0.0.1:0").unwrap();
6095    /// # let mut config = quiche::Config::new(quiche::PROTOCOL_VERSION)?;
6096    /// # let scid = quiche::ConnectionId::from_ref(&[0xba; 16]);
6097    /// # let peer = "127.0.0.1:1234".parse().unwrap();
6098    /// # let local = socket.local_addr().unwrap();
6099    /// # let mut conn = quiche::accept(&scid, None, local, peer, &mut config)?;
6100    /// let mut dgram_buf = [0; 512];
6101    /// while let Ok((len)) = conn.dgram_recv(&mut dgram_buf) {
6102    ///     println!("Got {} bytes of DATAGRAM", len);
6103    /// }
6104    /// # Ok::<(), quiche::Error>(())
6105    /// ```
6106    #[inline]
6107    pub fn dgram_recv(&mut self, buf: &mut [u8]) -> Result<usize> {
6108        match self.dgram_recv_queue.pop() {
6109            Some(d) => {
6110                if d.len() > buf.len() {
6111                    return Err(Error::BufferTooShort);
6112                }
6113
6114                buf[..d.len()].copy_from_slice(&d);
6115                Ok(d.len())
6116            },
6117
6118            None => Err(Error::Done),
6119        }
6120    }
6121
6122    /// Reads the first received DATAGRAM.
6123    ///
6124    /// This is the same as [`dgram_recv()`] but returns the DATAGRAM as a
6125    /// `Vec<u8>` instead of copying into the provided buffer.
6126    ///
6127    /// [`dgram_recv()`]: struct.Connection.html#method.dgram_recv
6128    #[inline]
6129    pub fn dgram_recv_vec(&mut self) -> Result<Vec<u8>> {
6130        match self.dgram_recv_queue.pop() {
6131            Some(d) => Ok(d),
6132
6133            None => Err(Error::Done),
6134        }
6135    }
6136
6137    /// Reads the first received DATAGRAM without removing it from the queue.
6138    ///
6139    /// On success the DATAGRAM's data is returned along with the actual number
6140    /// of bytes peeked. The requested length cannot exceed the DATAGRAM's
6141    /// actual length.
6142    ///
6143    /// [`Done`] is returned if there is no data to read.
6144    ///
6145    /// [`BufferTooShort`] is returned if the provided buffer is smaller the
6146    /// number of bytes to peek.
6147    ///
6148    /// [`Done`]: enum.Error.html#variant.Done
6149    /// [`BufferTooShort`]: enum.Error.html#variant.BufferTooShort
6150    #[inline]
6151    pub fn dgram_recv_peek(&self, buf: &mut [u8], len: usize) -> Result<usize> {
6152        self.dgram_recv_queue.peek_front_bytes(buf, len)
6153    }
6154
6155    /// Returns the length of the first stored DATAGRAM.
6156    #[inline]
6157    pub fn dgram_recv_front_len(&self) -> Option<usize> {
6158        self.dgram_recv_queue.peek_front_len()
6159    }
6160
6161    /// Returns the number of items in the DATAGRAM receive queue.
6162    #[inline]
6163    pub fn dgram_recv_queue_len(&self) -> usize {
6164        self.dgram_recv_queue.len()
6165    }
6166
6167    /// Returns the total size of all items in the DATAGRAM receive queue.
6168    #[inline]
6169    pub fn dgram_recv_queue_byte_size(&self) -> usize {
6170        self.dgram_recv_queue.byte_size()
6171    }
6172
6173    /// Returns the number of items in the DATAGRAM send queue.
6174    #[inline]
6175    pub fn dgram_send_queue_len(&self) -> usize {
6176        self.dgram_send_queue.len()
6177    }
6178
6179    /// Returns the total size of all items in the DATAGRAM send queue.
6180    #[inline]
6181    pub fn dgram_send_queue_byte_size(&self) -> usize {
6182        self.dgram_send_queue.byte_size()
6183    }
6184
6185    /// Returns whether or not the DATAGRAM send queue is full.
6186    #[inline]
6187    pub fn is_dgram_send_queue_full(&self) -> bool {
6188        self.dgram_send_queue.is_full()
6189    }
6190
6191    /// Returns whether or not the DATAGRAM recv queue is full.
6192    #[inline]
6193    pub fn is_dgram_recv_queue_full(&self) -> bool {
6194        self.dgram_recv_queue.is_full()
6195    }
6196
6197    /// Sends data in a DATAGRAM frame.
6198    ///
6199    /// [`Done`] is returned if no data was written.
6200    /// [`InvalidState`] is returned if the peer does not support DATAGRAM.
6201    /// [`BufferTooShort`] is returned if the DATAGRAM frame length is larger
6202    /// than peer's supported DATAGRAM frame length. Use
6203    /// [`dgram_max_writable_len()`] to get the largest supported DATAGRAM
6204    /// frame length.
6205    ///
6206    /// Note that there is no flow control of DATAGRAM frames, so in order to
6207    /// avoid buffering an infinite amount of frames we apply an internal
6208    /// limit.
6209    ///
6210    /// [`Done`]: enum.Error.html#variant.Done
6211    /// [`InvalidState`]: enum.Error.html#variant.InvalidState
6212    /// [`BufferTooShort`]: enum.Error.html#variant.BufferTooShort
6213    /// [`dgram_max_writable_len()`]:
6214    /// struct.Connection.html#method.dgram_max_writable_len
6215    ///
6216    /// ## Examples:
6217    ///
6218    /// ```no_run
6219    /// # let mut buf = [0; 512];
6220    /// # let socket = std::net::UdpSocket::bind("127.0.0.1:0").unwrap();
6221    /// # let mut config = quiche::Config::new(quiche::PROTOCOL_VERSION)?;
6222    /// # let scid = quiche::ConnectionId::from_ref(&[0xba; 16]);
6223    /// # let peer = "127.0.0.1:1234".parse().unwrap();
6224    /// # let local = socket.local_addr().unwrap();
6225    /// # let mut conn = quiche::accept(&scid, None, local, peer, &mut config)?;
6226    /// conn.dgram_send(b"hello")?;
6227    /// # Ok::<(), quiche::Error>(())
6228    /// ```
6229    pub fn dgram_send(&mut self, buf: &[u8]) -> Result<()> {
6230        let max_payload_len = match self.dgram_max_writable_len() {
6231            Some(v) => v,
6232
6233            None => return Err(Error::InvalidState),
6234        };
6235
6236        if buf.len() > max_payload_len {
6237            return Err(Error::BufferTooShort);
6238        }
6239
6240        self.dgram_send_queue.push(buf.to_vec())?;
6241
6242        let active_path = self.paths.get_active_mut()?;
6243
6244        if self.dgram_send_queue.byte_size() >
6245            active_path.recovery.cwnd_available()
6246        {
6247            active_path.recovery.update_app_limited(false);
6248        }
6249
6250        Ok(())
6251    }
6252
6253    /// Sends data in a DATAGRAM frame.
6254    ///
6255    /// This is the same as [`dgram_send()`] but takes a `Vec<u8>` instead of
6256    /// a slice.
6257    ///
6258    /// [`dgram_send()`]: struct.Connection.html#method.dgram_send
6259    pub fn dgram_send_vec(&mut self, buf: Vec<u8>) -> Result<()> {
6260        let max_payload_len = match self.dgram_max_writable_len() {
6261            Some(v) => v,
6262
6263            None => return Err(Error::InvalidState),
6264        };
6265
6266        if buf.len() > max_payload_len {
6267            return Err(Error::BufferTooShort);
6268        }
6269
6270        self.dgram_send_queue.push(buf)?;
6271
6272        let active_path = self.paths.get_active_mut()?;
6273
6274        if self.dgram_send_queue.byte_size() >
6275            active_path.recovery.cwnd_available()
6276        {
6277            active_path.recovery.update_app_limited(false);
6278        }
6279
6280        Ok(())
6281    }
6282
6283    /// Purges queued outgoing DATAGRAMs matching the predicate.
6284    ///
6285    /// In other words, remove all elements `e` such that `f(&e)` returns true.
6286    ///
6287    /// ## Examples:
6288    /// ```no_run
6289    /// # let socket = std::net::UdpSocket::bind("127.0.0.1:0").unwrap();
6290    /// # let mut config = quiche::Config::new(quiche::PROTOCOL_VERSION)?;
6291    /// # let scid = quiche::ConnectionId::from_ref(&[0xba; 16]);
6292    /// # let peer = "127.0.0.1:1234".parse().unwrap();
6293    /// # let local = socket.local_addr().unwrap();
6294    /// # let mut conn = quiche::accept(&scid, None, local, peer, &mut config)?;
6295    /// conn.dgram_send(b"hello")?;
6296    /// conn.dgram_purge_outgoing(&|d: &[u8]| -> bool { d[0] == 0 });
6297    /// # Ok::<(), quiche::Error>(())
6298    /// ```
6299    #[inline]
6300    pub fn dgram_purge_outgoing<FN: Fn(&[u8]) -> bool>(&mut self, f: FN) {
6301        self.dgram_send_queue.purge(f);
6302    }
6303
6304    /// Returns the maximum DATAGRAM payload that can be sent.
6305    ///
6306    /// [`None`] is returned if the peer hasn't advertised a maximum DATAGRAM
6307    /// frame size.
6308    ///
6309    /// ## Examples:
6310    ///
6311    /// ```no_run
6312    /// # let mut buf = [0; 512];
6313    /// # let socket = std::net::UdpSocket::bind("127.0.0.1:0").unwrap();
6314    /// # let mut config = quiche::Config::new(quiche::PROTOCOL_VERSION)?;
6315    /// # let scid = quiche::ConnectionId::from_ref(&[0xba; 16]);
6316    /// # let peer = "127.0.0.1:1234".parse().unwrap();
6317    /// # let local = socket.local_addr().unwrap();
6318    /// # let mut conn = quiche::accept(&scid, None, local, peer, &mut config)?;
6319    /// if let Some(payload_size) = conn.dgram_max_writable_len() {
6320    ///     if payload_size > 5 {
6321    ///         conn.dgram_send(b"hello")?;
6322    ///     }
6323    /// }
6324    /// # Ok::<(), quiche::Error>(())
6325    /// ```
6326    #[inline]
6327    pub fn dgram_max_writable_len(&self) -> Option<usize> {
6328        match self.peer_transport_params.max_datagram_frame_size {
6329            None => None,
6330            Some(peer_frame_len) => {
6331                let dcid = self.destination_id();
6332                // Start from the maximum packet size...
6333                let mut max_len = self.max_send_udp_payload_size();
6334                // ...subtract the Short packet header overhead...
6335                // (1 byte of pkt_len + len of dcid)
6336                max_len = max_len.saturating_sub(1 + dcid.len());
6337                // ...subtract the packet number (max len)...
6338                max_len = max_len.saturating_sub(packet::MAX_PKT_NUM_LEN);
6339                // ...subtract the crypto overhead...
6340                max_len = max_len.saturating_sub(
6341                    self.crypto_ctx[packet::Epoch::Application]
6342                        .crypto_overhead()?,
6343                );
6344                // ...clamp to what peer can support...
6345                max_len = cmp::min(peer_frame_len as usize, max_len);
6346                // ...subtract frame overhead, checked for underflow.
6347                // (1 byte of frame type + len of length )
6348                max_len.checked_sub(1 + frame::MAX_DGRAM_OVERHEAD)
6349            },
6350        }
6351    }
6352
6353    fn dgram_enabled(&self) -> bool {
6354        self.local_transport_params
6355            .max_datagram_frame_size
6356            .is_some()
6357    }
6358
6359    /// Returns when the next timeout event will occur.
6360    ///
6361    /// Once the timeout Instant has been reached, the [`on_timeout()`] method
6362    /// should be called. A timeout of `None` means that the timer should be
6363    /// disarmed.
6364    ///
6365    /// [`on_timeout()`]: struct.Connection.html#method.on_timeout
6366    pub fn timeout_instant(&self) -> Option<Instant> {
6367        if self.is_closed() {
6368            return None;
6369        }
6370
6371        if self.is_draining() {
6372            // Draining timer takes precedence over all other timers. If it is
6373            // set it means the connection is closing so there's no point in
6374            // processing the other timers.
6375            self.draining_timer
6376        } else {
6377            // Use the lowest timer value (i.e. "sooner") among idle and loss
6378            // detection timers. If they are both unset (i.e. `None`) then the
6379            // result is `None`, but if at least one of them is set then a
6380            // `Some(...)` value is returned.
6381            let path_timer = self
6382                .paths
6383                .iter()
6384                .filter_map(|(_, p)| p.recovery.loss_detection_timer())
6385                .min();
6386
6387            let key_update_timer = self.crypto_ctx[packet::Epoch::Application]
6388                .key_update
6389                .as_ref()
6390                .map(|key_update| key_update.timer);
6391
6392            let timers = [self.idle_timer, path_timer, key_update_timer];
6393
6394            timers.iter().filter_map(|&x| x).min()
6395        }
6396    }
6397
6398    /// Returns the amount of time until the next timeout event.
6399    ///
6400    /// Once the given duration has elapsed, the [`on_timeout()`] method should
6401    /// be called. A timeout of `None` means that the timer should be disarmed.
6402    ///
6403    /// [`on_timeout()`]: struct.Connection.html#method.on_timeout
6404    pub fn timeout(&self) -> Option<Duration> {
6405        self.timeout_instant().map(|timeout| {
6406            let now = Instant::now();
6407
6408            if timeout <= now {
6409                Duration::ZERO
6410            } else {
6411                timeout.duration_since(now)
6412            }
6413        })
6414    }
6415
6416    /// Processes a timeout event.
6417    ///
6418    /// If no timeout has occurred it does nothing.
6419    pub fn on_timeout(&mut self) {
6420        let now = Instant::now();
6421
6422        if let Some(draining_timer) = self.draining_timer {
6423            if draining_timer <= now {
6424                trace!("{} draining timeout expired", self.trace_id);
6425
6426                self.mark_closed();
6427            }
6428
6429            // Draining timer takes precedence over all other timers. If it is
6430            // set it means the connection is closing so there's no point in
6431            // processing the other timers.
6432            return;
6433        }
6434
6435        if let Some(timer) = self.idle_timer {
6436            if timer <= now {
6437                trace!("{} idle timeout expired", self.trace_id);
6438
6439                self.mark_closed();
6440                self.timed_out = true;
6441                return;
6442            }
6443        }
6444
6445        if let Some(timer) = self.crypto_ctx[packet::Epoch::Application]
6446            .key_update
6447            .as_ref()
6448            .map(|key_update| key_update.timer)
6449        {
6450            if timer <= now {
6451                // Discard previous key once key update timer expired.
6452                let _ = self.crypto_ctx[packet::Epoch::Application]
6453                    .key_update
6454                    .take();
6455            }
6456        }
6457
6458        let handshake_status = self.handshake_status();
6459
6460        for (_, p) in self.paths.iter_mut() {
6461            if let Some(timer) = p.recovery.loss_detection_timer() {
6462                if timer <= now {
6463                    trace!("{} loss detection timeout expired", self.trace_id);
6464
6465                    let OnLossDetectionTimeoutOutcome {
6466                        lost_packets,
6467                        lost_bytes,
6468                    } = p.on_loss_detection_timeout(
6469                        handshake_status,
6470                        now,
6471                        self.is_server,
6472                        &self.trace_id,
6473                    );
6474
6475                    self.lost_count += lost_packets;
6476                    self.lost_bytes += lost_bytes as u64;
6477
6478                    qlog_with_type!(QLOG_METRICS, self.qlog, q, {
6479                        p.recovery.maybe_qlog(q, now);
6480                    });
6481                }
6482            }
6483        }
6484
6485        // Notify timeout events to the application.
6486        self.paths.notify_failed_validations();
6487
6488        // If the active path failed, try to find a new candidate.
6489        if self.paths.get_active_path_id().is_err() {
6490            match self.paths.find_candidate_path() {
6491                Some(pid) => {
6492                    if self.set_active_path(pid, now).is_err() {
6493                        // The connection cannot continue.
6494                        self.mark_closed();
6495                    }
6496                },
6497
6498                // The connection cannot continue.
6499                None => {
6500                    self.mark_closed();
6501                },
6502            }
6503        }
6504    }
6505
6506    /// Requests the stack to perform path validation of the proposed 4-tuple.
6507    ///
6508    /// Probing new paths requires spare Connection IDs at both the host and the
6509    /// peer sides. If it is not the case, it raises an [`OutOfIdentifiers`].
6510    ///
6511    /// The probing of new addresses can only be done by the client. The server
6512    /// can only probe network paths that were previously advertised by
6513    /// [`PathEvent::New`]. If the server tries to probe such an unseen network
6514    /// path, this call raises an [`InvalidState`].
6515    ///
6516    /// The caller might also want to probe an existing path. In such case, it
6517    /// triggers a PATH_CHALLENGE frame, but it does not require spare CIDs.
6518    ///
6519    /// A server always probes a new path it observes. Calling this method is
6520    /// hence not required to validate a new path. However, a server can still
6521    /// request an additional path validation of the proposed 4-tuple.
6522    ///
6523    /// Calling this method several times before calling [`send()`] or
6524    /// [`send_on_path()`] results in a single probe being generated. An
6525    /// application wanting to send multiple in-flight probes must call this
6526    /// method again after having sent packets.
6527    ///
6528    /// Returns the Destination Connection ID sequence number associated to that
6529    /// path.
6530    ///
6531    /// [`PathEvent::New`]: enum.PathEvent.html#variant.New
6532    /// [`OutOfIdentifiers`]: enum.Error.html#OutOfIdentifiers
6533    /// [`InvalidState`]: enum.Error.html#InvalidState
6534    /// [`send()`]: struct.Connection.html#method.send
6535    /// [`send_on_path()`]: struct.Connection.html#method.send_on_path
6536    pub fn probe_path(
6537        &mut self, local_addr: SocketAddr, peer_addr: SocketAddr,
6538    ) -> Result<u64> {
6539        // We may want to probe an existing path.
6540        let pid = match self.paths.path_id_from_addrs(&(local_addr, peer_addr)) {
6541            Some(pid) => pid,
6542            None => self.create_path_on_client(local_addr, peer_addr)?,
6543        };
6544
6545        let path = self.paths.get_mut(pid)?;
6546        path.request_validation();
6547
6548        path.active_dcid_seq.ok_or(Error::InvalidState)
6549    }
6550
6551    /// Migrates the connection to a new local address `local_addr`.
6552    ///
6553    /// The behavior is similar to [`migrate()`], with the nuance that the
6554    /// connection only changes the local address, but not the peer one.
6555    ///
6556    /// See [`migrate()`] for the full specification of this method.
6557    ///
6558    /// [`migrate()`]: struct.Connection.html#method.migrate
6559    pub fn migrate_source(&mut self, local_addr: SocketAddr) -> Result<u64> {
6560        let peer_addr = self.paths.get_active()?.peer_addr();
6561        self.migrate(local_addr, peer_addr)
6562    }
6563
6564    /// Migrates the connection over the given network path between `local_addr`
6565    /// and `peer_addr`.
6566    ///
6567    /// Connection migration can only be initiated by the client. Calling this
6568    /// method as a server returns [`InvalidState`].
6569    ///
6570    /// To initiate voluntary migration, there should be enough Connection IDs
6571    /// at both sides. If this requirement is not satisfied, this call returns
6572    /// [`OutOfIdentifiers`].
6573    ///
6574    /// Returns the Destination Connection ID associated to that migrated path.
6575    ///
6576    /// [`OutOfIdentifiers`]: enum.Error.html#OutOfIdentifiers
6577    /// [`InvalidState`]: enum.Error.html#InvalidState
6578    pub fn migrate(
6579        &mut self, local_addr: SocketAddr, peer_addr: SocketAddr,
6580    ) -> Result<u64> {
6581        if self.is_server {
6582            return Err(Error::InvalidState);
6583        }
6584
6585        // If the path already exists, mark it as the active one.
6586        let (pid, dcid_seq) = if let Some(pid) =
6587            self.paths.path_id_from_addrs(&(local_addr, peer_addr))
6588        {
6589            let path = self.paths.get_mut(pid)?;
6590
6591            // If it is already active, do nothing.
6592            if path.active() {
6593                return path.active_dcid_seq.ok_or(Error::OutOfIdentifiers);
6594            }
6595
6596            // Ensures that a Source Connection ID has been dedicated to this
6597            // path, or a free one is available. This is only required if the
6598            // host uses non-zero length Source Connection IDs.
6599            if !self.ids.zero_length_scid() &&
6600                path.active_scid_seq.is_none() &&
6601                self.ids.available_scids() == 0
6602            {
6603                return Err(Error::OutOfIdentifiers);
6604            }
6605
6606            // Ensures that the migrated path has a Destination Connection ID.
6607            let dcid_seq = if let Some(dcid_seq) = path.active_dcid_seq {
6608                dcid_seq
6609            } else {
6610                let dcid_seq = self
6611                    .ids
6612                    .lowest_available_dcid_seq()
6613                    .ok_or(Error::OutOfIdentifiers)?;
6614
6615                self.ids.link_dcid_to_path_id(dcid_seq, pid)?;
6616                path.active_dcid_seq = Some(dcid_seq);
6617
6618                dcid_seq
6619            };
6620
6621            (pid, dcid_seq)
6622        } else {
6623            let pid = self.create_path_on_client(local_addr, peer_addr)?;
6624
6625            let dcid_seq = self
6626                .paths
6627                .get(pid)?
6628                .active_dcid_seq
6629                .ok_or(Error::InvalidState)?;
6630
6631            (pid, dcid_seq)
6632        };
6633
6634        // Change the active path.
6635        self.set_active_path(pid, Instant::now())?;
6636
6637        Ok(dcid_seq)
6638    }
6639
6640    /// Provides additional source Connection IDs that the peer can use to reach
6641    /// this host.
6642    ///
6643    /// This triggers sending NEW_CONNECTION_ID frames if the provided Source
6644    /// Connection ID is not already present. In the case the caller tries to
6645    /// reuse a Connection ID with a different reset token, this raises an
6646    /// `InvalidState`.
6647    ///
6648    /// At any time, the peer cannot have more Destination Connection IDs than
6649    /// the maximum number of active Connection IDs it negotiated. In such case
6650    /// (i.e., when [`scids_left()`] returns 0), if the host agrees to
6651    /// request the removal of previous connection IDs, it sets the
6652    /// `retire_if_needed` parameter. Otherwise, an [`IdLimit`] is returned.
6653    ///
6654    /// Note that setting `retire_if_needed` does not prevent this function from
6655    /// returning an [`IdLimit`] in the case the caller wants to retire still
6656    /// unannounced Connection IDs.
6657    ///
6658    /// The caller is responsible for ensuring that the provided `scid` is not
6659    /// repeated several times over the connection. quiche ensures that as long
6660    /// as the provided Connection ID is still in use (i.e., not retired), it
6661    /// does not assign a different sequence number.
6662    ///
6663    /// Note that if the host uses zero-length Source Connection IDs, it cannot
6664    /// advertise Source Connection IDs and calling this method returns an
6665    /// [`InvalidState`].
6666    ///
6667    /// Returns the sequence number associated to the provided Connection ID.
6668    ///
6669    /// [`scids_left()`]: struct.Connection.html#method.scids_left
6670    /// [`IdLimit`]: enum.Error.html#IdLimit
6671    /// [`InvalidState`]: enum.Error.html#InvalidState
6672    pub fn new_scid(
6673        &mut self, scid: &ConnectionId, reset_token: u128, retire_if_needed: bool,
6674    ) -> Result<u64> {
6675        self.ids.new_scid(
6676            scid.to_vec().into(),
6677            Some(reset_token),
6678            true,
6679            None,
6680            retire_if_needed,
6681        )
6682    }
6683
6684    /// Returns the number of source Connection IDs that are active. This is
6685    /// only meaningful if the host uses non-zero length Source Connection IDs.
6686    pub fn active_scids(&self) -> usize {
6687        self.ids.active_source_cids()
6688    }
6689
6690    /// Returns the number of source Connection IDs that should be provided
6691    /// to the peer without exceeding the limit it advertised.
6692    ///
6693    /// This will automatically limit the number of Connection IDs to the
6694    /// minimum between the locally configured active connection ID limit,
6695    /// and the one sent by the peer.
6696    ///
6697    /// To obtain the maximum possible value allowed by the peer an application
6698    /// can instead inspect the [`peer_active_conn_id_limit`] value.
6699    ///
6700    /// [`peer_active_conn_id_limit`]: struct.Stats.html#structfield.peer_active_conn_id_limit
6701    #[inline]
6702    pub fn scids_left(&self) -> usize {
6703        let max_active_source_cids = cmp::min(
6704            self.peer_transport_params.active_conn_id_limit,
6705            self.local_transport_params.active_conn_id_limit,
6706        ) as usize;
6707
6708        max_active_source_cids - self.active_scids()
6709    }
6710
6711    /// Requests the retirement of the destination Connection ID used by the
6712    /// host to reach its peer.
6713    ///
6714    /// This triggers sending RETIRE_CONNECTION_ID frames.
6715    ///
6716    /// If the application tries to retire a non-existing Destination Connection
6717    /// ID sequence number, or if it uses zero-length Destination Connection ID,
6718    /// this method returns an [`InvalidState`].
6719    ///
6720    /// At any time, the host must have at least one Destination ID. If the
6721    /// application tries to retire the last one, or if the caller tries to
6722    /// retire the destination Connection ID used by the current active path
6723    /// while having neither spare Destination Connection IDs nor validated
6724    /// network paths, this method returns an [`OutOfIdentifiers`]. This
6725    /// behavior prevents the caller from stalling the connection due to the
6726    /// lack of validated path to send non-probing packets.
6727    ///
6728    /// [`InvalidState`]: enum.Error.html#InvalidState
6729    /// [`OutOfIdentifiers`]: enum.Error.html#OutOfIdentifiers
6730    pub fn retire_dcid(&mut self, dcid_seq: u64) -> Result<()> {
6731        if self.ids.zero_length_dcid() {
6732            return Err(Error::InvalidState);
6733        }
6734
6735        let active_path_dcid_seq = self
6736            .paths
6737            .get_active()?
6738            .active_dcid_seq
6739            .ok_or(Error::InvalidState)?;
6740
6741        let active_path_id = self.paths.get_active_path_id()?;
6742
6743        if active_path_dcid_seq == dcid_seq &&
6744            self.ids.lowest_available_dcid_seq().is_none() &&
6745            !self
6746                .paths
6747                .iter()
6748                .any(|(pid, p)| pid != active_path_id && p.usable())
6749        {
6750            return Err(Error::OutOfIdentifiers);
6751        }
6752
6753        if let Some(pid) = self.ids.retire_dcid(dcid_seq)? {
6754            // The retired Destination CID was associated to a given path. Let's
6755            // find an available DCID to associate to that path.
6756            let path = self.paths.get_mut(pid)?;
6757            let dcid_seq = self.ids.lowest_available_dcid_seq();
6758
6759            if let Some(dcid_seq) = dcid_seq {
6760                self.ids.link_dcid_to_path_id(dcid_seq, pid)?;
6761            }
6762
6763            path.active_dcid_seq = dcid_seq;
6764        }
6765
6766        Ok(())
6767    }
6768
6769    /// Processes path-specific events.
6770    ///
6771    /// On success it returns a [`PathEvent`], or `None` when there are no
6772    /// events to report. Please refer to [`PathEvent`] for the exhaustive event
6773    /// list.
6774    ///
6775    /// Note that all events are edge-triggered, meaning that once reported they
6776    /// will not be reported again by calling this method again, until the event
6777    /// is re-armed.
6778    ///
6779    /// [`PathEvent`]: enum.PathEvent.html
6780    pub fn path_event_next(&mut self) -> Option<PathEvent> {
6781        self.paths.pop_event()
6782    }
6783
6784    /// Returns the number of source Connection IDs that are retired.
6785    pub fn retired_scids(&self) -> usize {
6786        self.ids.retired_source_cids()
6787    }
6788
6789    /// Returns a source `ConnectionId` that has been retired.
6790    ///
6791    /// On success it returns a [`ConnectionId`], or `None` when there are no
6792    /// more retired connection IDs.
6793    ///
6794    /// [`ConnectionId`]: struct.ConnectionId.html
6795    pub fn retired_scid_next(&mut self) -> Option<ConnectionId<'static>> {
6796        self.ids.pop_retired_scid()
6797    }
6798
6799    /// Returns the number of spare Destination Connection IDs, i.e.,
6800    /// Destination Connection IDs that are still unused.
6801    ///
6802    /// Note that this function returns 0 if the host uses zero length
6803    /// Destination Connection IDs.
6804    pub fn available_dcids(&self) -> usize {
6805        self.ids.available_dcids()
6806    }
6807
6808    /// Returns an iterator over destination `SockAddr`s whose association
6809    /// with `from` forms a known QUIC path on which packets can be sent to.
6810    ///
6811    /// This function is typically used in combination with [`send_on_path()`].
6812    ///
6813    /// Note that the iterator includes all the possible combination of
6814    /// destination `SockAddr`s, even those whose sending is not required now.
6815    /// In other words, this is another way for the application to recall from
6816    /// past [`PathEvent::New`] events.
6817    ///
6818    /// [`PathEvent::New`]: enum.PathEvent.html#variant.New
6819    /// [`send_on_path()`]: struct.Connection.html#method.send_on_path
6820    ///
6821    /// ## Examples:
6822    ///
6823    /// ```no_run
6824    /// # let mut out = [0; 512];
6825    /// # let socket = std::net::UdpSocket::bind("127.0.0.1:0").unwrap();
6826    /// # let mut config = quiche::Config::new(quiche::PROTOCOL_VERSION)?;
6827    /// # let scid = quiche::ConnectionId::from_ref(&[0xba; 16]);
6828    /// # let local = socket.local_addr().unwrap();
6829    /// # let peer = "127.0.0.1:1234".parse().unwrap();
6830    /// # let mut conn = quiche::accept(&scid, None, local, peer, &mut config)?;
6831    /// // Iterate over possible destinations for the given local `SockAddr`.
6832    /// for dest in conn.paths_iter(local) {
6833    ///     loop {
6834    ///         let (write, send_info) =
6835    ///             match conn.send_on_path(&mut out, Some(local), Some(dest)) {
6836    ///                 Ok(v) => v,
6837    ///
6838    ///                 Err(quiche::Error::Done) => {
6839    ///                     // Done writing for this destination.
6840    ///                     break;
6841    ///                 },
6842    ///
6843    ///                 Err(e) => {
6844    ///                     // An error occurred, handle it.
6845    ///                     break;
6846    ///                 },
6847    ///             };
6848    ///
6849    ///         socket.send_to(&out[..write], &send_info.to).unwrap();
6850    ///     }
6851    /// }
6852    /// # Ok::<(), quiche::Error>(())
6853    /// ```
6854    #[inline]
6855    pub fn paths_iter(&self, from: SocketAddr) -> SocketAddrIter {
6856        // Instead of trying to identify whether packets will be sent on the
6857        // given 4-tuple, simply filter paths that cannot be used.
6858        SocketAddrIter {
6859            sockaddrs: self
6860                .paths
6861                .iter()
6862                .filter(|(_, p)| p.active_dcid_seq.is_some())
6863                .filter(|(_, p)| p.usable() || p.probing_required())
6864                .filter(|(_, p)| p.local_addr() == from)
6865                .map(|(_, p)| p.peer_addr())
6866                .collect(),
6867
6868            index: 0,
6869        }
6870    }
6871
6872    /// Closes the connection with the given error and reason.
6873    ///
6874    /// The `app` parameter specifies whether an application close should be
6875    /// sent to the peer. Otherwise a normal connection close is sent.
6876    ///
6877    /// If `app` is true but the connection is not in a state that is safe to
6878    /// send an application error (not established nor in early data), in
6879    /// accordance with [RFC
6880    /// 9000](https://www.rfc-editor.org/rfc/rfc9000.html#section-10.2.3-3), the
6881    /// error code is changed to APPLICATION_ERROR and the reason phrase is
6882    /// cleared.
6883    ///
6884    /// Returns [`Done`] if the connection had already been closed.
6885    ///
6886    /// Note that the connection will not be closed immediately. An application
6887    /// should continue calling the [`recv()`], [`send()`], [`timeout()`] and
6888    /// [`on_timeout()`] methods as normal, until the [`is_closed()`] method
6889    /// returns `true`.
6890    ///
6891    /// [`Done`]: enum.Error.html#variant.Done
6892    /// [`recv()`]: struct.Connection.html#method.recv
6893    /// [`send()`]: struct.Connection.html#method.send
6894    /// [`timeout()`]: struct.Connection.html#method.timeout
6895    /// [`on_timeout()`]: struct.Connection.html#method.on_timeout
6896    /// [`is_closed()`]: struct.Connection.html#method.is_closed
6897    pub fn close(&mut self, app: bool, err: u64, reason: &[u8]) -> Result<()> {
6898        if self.is_closed() || self.is_draining() {
6899            return Err(Error::Done);
6900        }
6901
6902        if self.local_error.is_some() {
6903            return Err(Error::Done);
6904        }
6905
6906        let is_safe_to_send_app_data =
6907            self.is_established() || self.is_in_early_data();
6908
6909        if app && !is_safe_to_send_app_data {
6910            // Clear error information.
6911            self.local_error = Some(ConnectionError {
6912                is_app: false,
6913                error_code: 0x0c,
6914                reason: vec![],
6915            });
6916        } else {
6917            self.local_error = Some(ConnectionError {
6918                is_app: app,
6919                error_code: err,
6920                reason: reason.to_vec(),
6921            });
6922        }
6923
6924        // When no packet was successfully processed close connection immediately.
6925        if self.recv_count == 0 {
6926            self.mark_closed();
6927        }
6928
6929        Ok(())
6930    }
6931
6932    /// Returns a string uniquely representing the connection.
6933    ///
6934    /// This can be used for logging purposes to differentiate between multiple
6935    /// connections.
6936    #[inline]
6937    pub fn trace_id(&self) -> &str {
6938        &self.trace_id
6939    }
6940
6941    /// Returns the negotiated ALPN protocol.
6942    ///
6943    /// If no protocol has been negotiated, the returned value is empty.
6944    #[inline]
6945    pub fn application_proto(&self) -> &[u8] {
6946        self.alpn.as_ref()
6947    }
6948
6949    /// Returns the server name requested by the client.
6950    #[inline]
6951    pub fn server_name(&self) -> Option<&str> {
6952        self.handshake.server_name()
6953    }
6954
6955    /// Returns the peer's leaf certificate (if any) as a DER-encoded buffer.
6956    #[inline]
6957    pub fn peer_cert(&self) -> Option<&[u8]> {
6958        self.handshake.peer_cert()
6959    }
6960
6961    /// Returns the peer's certificate chain (if any) as a vector of DER-encoded
6962    /// buffers.
6963    ///
6964    /// The certificate at index 0 is the peer's leaf certificate, the other
6965    /// certificates (if any) are the chain certificate authorities used to
6966    /// sign the leaf certificate.
6967    #[inline]
6968    pub fn peer_cert_chain(&self) -> Option<Vec<&[u8]>> {
6969        self.handshake.peer_cert_chain()
6970    }
6971
6972    /// Returns the serialized cryptographic session for the connection.
6973    ///
6974    /// This can be used by a client to cache a connection's session, and resume
6975    /// it later using the [`set_session()`] method.
6976    ///
6977    /// [`set_session()`]: struct.Connection.html#method.set_session
6978    #[inline]
6979    pub fn session(&self) -> Option<&[u8]> {
6980        self.session.as_deref()
6981    }
6982
6983    /// Returns the source connection ID.
6984    ///
6985    /// When there are multiple IDs, and if there is an active path, the ID used
6986    /// on that path is returned. Otherwise the oldest ID is returned.
6987    ///
6988    /// Note that the value returned can change throughout the connection's
6989    /// lifetime.
6990    #[inline]
6991    pub fn source_id(&self) -> ConnectionId<'_> {
6992        if let Ok(path) = self.paths.get_active() {
6993            if let Some(active_scid_seq) = path.active_scid_seq {
6994                if let Ok(e) = self.ids.get_scid(active_scid_seq) {
6995                    return ConnectionId::from_ref(e.cid.as_ref());
6996                }
6997            }
6998        }
6999
7000        let e = self.ids.oldest_scid();
7001        ConnectionId::from_ref(e.cid.as_ref())
7002    }
7003
7004    /// Returns all active source connection IDs.
7005    ///
7006    /// An iterator is returned for all active IDs (i.e. ones that have not
7007    /// been explicitly retired yet).
7008    #[inline]
7009    pub fn source_ids(&self) -> impl Iterator<Item = &ConnectionId<'_>> {
7010        self.ids.scids_iter()
7011    }
7012
7013    /// Returns the destination connection ID.
7014    ///
7015    /// Note that the value returned can change throughout the connection's
7016    /// lifetime.
7017    #[inline]
7018    pub fn destination_id(&self) -> ConnectionId<'_> {
7019        if let Ok(path) = self.paths.get_active() {
7020            if let Some(active_dcid_seq) = path.active_dcid_seq {
7021                if let Ok(e) = self.ids.get_dcid(active_dcid_seq) {
7022                    return ConnectionId::from_ref(e.cid.as_ref());
7023                }
7024            }
7025        }
7026
7027        let e = self.ids.oldest_dcid();
7028        ConnectionId::from_ref(e.cid.as_ref())
7029    }
7030
7031    /// Returns the PMTU for the active path if it exists.
7032    ///
7033    /// This requires no additonal packets to be sent but simply checks if PMTUD
7034    /// has completed and has found a valid PMTU.
7035    #[inline]
7036    pub fn pmtu(&self) -> Option<usize> {
7037        if let Ok(path) = self.paths.get_active() {
7038            path.pmtud.as_ref().and_then(|pmtud| pmtud.get_pmtu())
7039        } else {
7040            None
7041        }
7042    }
7043
7044    /// Revalidates the PMTU for the active path by sending a new probe packet
7045    /// of PMTU size. If the probe is dropped PMTUD will restart and find a new
7046    /// valid PMTU.
7047    #[inline]
7048    pub fn revalidate_pmtu(&mut self) {
7049        if let Ok(active_path) = self.paths.get_active_mut() {
7050            if let Some(pmtud) = active_path.pmtud.as_mut() {
7051                pmtud.revalidate_pmtu();
7052            }
7053        }
7054    }
7055
7056    /// Returns true if the connection handshake is complete.
7057    #[inline]
7058    pub fn is_established(&self) -> bool {
7059        self.handshake_completed
7060    }
7061
7062    /// Returns true if the connection is resumed.
7063    #[inline]
7064    pub fn is_resumed(&self) -> bool {
7065        self.handshake.is_resumed()
7066    }
7067
7068    /// Returns true if the connection has a pending handshake that has
7069    /// progressed enough to send or receive early data.
7070    #[inline]
7071    pub fn is_in_early_data(&self) -> bool {
7072        self.handshake.is_in_early_data()
7073    }
7074
7075    /// Returns the early data reason for the connection.
7076    ///
7077    /// This status can be useful for logging and debugging. See [BoringSSL]
7078    /// documentation for a definition of the reasons.
7079    ///
7080    /// [BoringSSL]: https://commondatastorage.googleapis.com/chromium-boringssl-docs/ssl.h.html#ssl_early_data_reason_t
7081    #[inline]
7082    pub fn early_data_reason(&self) -> u32 {
7083        self.handshake.early_data_reason()
7084    }
7085
7086    /// Returns whether there is stream or DATAGRAM data available to read.
7087    #[inline]
7088    pub fn is_readable(&self) -> bool {
7089        self.streams.has_readable() || self.dgram_recv_front_len().is_some()
7090    }
7091
7092    /// Returns whether the network path with local address `from` and remote
7093    /// address `peer` has been validated.
7094    ///
7095    /// If the 4-tuple does not exist over the connection, returns an
7096    /// [`InvalidState`].
7097    ///
7098    /// [`InvalidState`]: enum.Error.html#variant.InvalidState
7099    pub fn is_path_validated(
7100        &self, from: SocketAddr, to: SocketAddr,
7101    ) -> Result<bool> {
7102        let pid = self
7103            .paths
7104            .path_id_from_addrs(&(from, to))
7105            .ok_or(Error::InvalidState)?;
7106
7107        Ok(self.paths.get(pid)?.validated())
7108    }
7109
7110    /// Returns true if the connection is draining.
7111    ///
7112    /// If this returns `true`, the connection object cannot yet be dropped, but
7113    /// no new application data can be sent or received. An application should
7114    /// continue calling the [`recv()`], [`timeout()`], and [`on_timeout()`]
7115    /// methods as normal, until the [`is_closed()`] method returns `true`.
7116    ///
7117    /// In contrast, once `is_draining()` returns `true`, calling [`send()`]
7118    /// is not required because no new outgoing packets will be generated.
7119    ///
7120    /// [`recv()`]: struct.Connection.html#method.recv
7121    /// [`send()`]: struct.Connection.html#method.send
7122    /// [`timeout()`]: struct.Connection.html#method.timeout
7123    /// [`on_timeout()`]: struct.Connection.html#method.on_timeout
7124    /// [`is_closed()`]: struct.Connection.html#method.is_closed
7125    #[inline]
7126    pub fn is_draining(&self) -> bool {
7127        self.draining_timer.is_some()
7128    }
7129
7130    /// Returns true if the connection is closed.
7131    ///
7132    /// If this returns true, the connection object can be dropped.
7133    #[inline]
7134    pub fn is_closed(&self) -> bool {
7135        self.closed
7136    }
7137
7138    /// Returns true if the connection was closed due to the idle timeout.
7139    #[inline]
7140    pub fn is_timed_out(&self) -> bool {
7141        self.timed_out
7142    }
7143
7144    /// Returns the error received from the peer, if any.
7145    ///
7146    /// Note that a `Some` return value does not necessarily imply
7147    /// [`is_closed()`] or any other connection state.
7148    ///
7149    /// [`is_closed()`]: struct.Connection.html#method.is_closed
7150    #[inline]
7151    pub fn peer_error(&self) -> Option<&ConnectionError> {
7152        self.peer_error.as_ref()
7153    }
7154
7155    /// Returns the error [`close()`] was called with, or internally
7156    /// created quiche errors, if any.
7157    ///
7158    /// Note that a `Some` return value does not necessarily imply
7159    /// [`is_closed()`] or any other connection state.
7160    /// `Some` also does not guarantee that the error has been sent to
7161    /// or received by the peer.
7162    ///
7163    /// [`close()`]: struct.Connection.html#method.close
7164    /// [`is_closed()`]: struct.Connection.html#method.is_closed
7165    #[inline]
7166    pub fn local_error(&self) -> Option<&ConnectionError> {
7167        self.local_error.as_ref()
7168    }
7169
7170    /// Collects and returns statistics about the connection.
7171    #[inline]
7172    pub fn stats(&self) -> Stats {
7173        Stats {
7174            recv: self.recv_count,
7175            sent: self.sent_count,
7176            lost: self.lost_count,
7177            spurious_lost: self.spurious_lost_count,
7178            retrans: self.retrans_count,
7179            sent_bytes: self.sent_bytes,
7180            recv_bytes: self.recv_bytes,
7181            acked_bytes: self.acked_bytes,
7182            lost_bytes: self.lost_bytes,
7183            stream_retrans_bytes: self.stream_retrans_bytes,
7184            dgram_recv: self.dgram_recv_count,
7185            dgram_sent: self.dgram_sent_count,
7186            paths_count: self.paths.len(),
7187            reset_stream_count_local: self.reset_stream_local_count,
7188            stopped_stream_count_local: self.stopped_stream_local_count,
7189            reset_stream_count_remote: self.reset_stream_remote_count,
7190            stopped_stream_count_remote: self.stopped_stream_remote_count,
7191            data_blocked_sent_count: self.data_blocked_sent_count,
7192            stream_data_blocked_sent_count: self.stream_data_blocked_sent_count,
7193            data_blocked_recv_count: self.data_blocked_recv_count,
7194            stream_data_blocked_recv_count: self.stream_data_blocked_recv_count,
7195            path_challenge_rx_count: self.path_challenge_rx_count,
7196            bytes_in_flight_duration: self.bytes_in_flight_duration(),
7197            tx_buffered_state: self.tx_buffered_state,
7198        }
7199    }
7200
7201    /// Returns the sum of the durations when each path in the
7202    /// connection was actively sending bytes or waiting for acks.
7203    /// Note that this could result in a duration that is longer than
7204    /// the actual connection duration in cases where multiple paths
7205    /// are active for extended periods of time.  In practice only 1
7206    /// path is typically active at a time.
7207    /// TODO revisit computation if in the future multiple paths are
7208    /// often active at the same time.
7209    fn bytes_in_flight_duration(&self) -> Duration {
7210        self.paths.iter().fold(Duration::ZERO, |acc, (_, path)| {
7211            acc + path.bytes_in_flight_duration()
7212        })
7213    }
7214
7215    /// Returns reference to peer's transport parameters. Returns `None` if we
7216    /// have not yet processed the peer's transport parameters.
7217    pub fn peer_transport_params(&self) -> Option<&TransportParams> {
7218        if !self.parsed_peer_transport_params {
7219            return None;
7220        }
7221
7222        Some(&self.peer_transport_params)
7223    }
7224
7225    /// Collects and returns statistics about each known path for the
7226    /// connection.
7227    pub fn path_stats(&self) -> impl Iterator<Item = PathStats> + '_ {
7228        self.paths.iter().map(|(_, p)| p.stats())
7229    }
7230
7231    /// Returns whether or not this is a server-side connection.
7232    pub fn is_server(&self) -> bool {
7233        self.is_server
7234    }
7235
7236    fn encode_transport_params(&mut self) -> Result<()> {
7237        self.handshake.set_quic_transport_params(
7238            &self.local_transport_params,
7239            self.is_server,
7240        )
7241    }
7242
7243    fn parse_peer_transport_params(
7244        &mut self, peer_params: TransportParams,
7245    ) -> Result<()> {
7246        // Validate initial_source_connection_id.
7247        match &peer_params.initial_source_connection_id {
7248            Some(v) if v != &self.destination_id() =>
7249                return Err(Error::InvalidTransportParam),
7250
7251            Some(_) => (),
7252
7253            // initial_source_connection_id must be sent by
7254            // both endpoints.
7255            None => return Err(Error::InvalidTransportParam),
7256        }
7257
7258        // Validate original_destination_connection_id.
7259        if let Some(odcid) = &self.odcid {
7260            match &peer_params.original_destination_connection_id {
7261                Some(v) if v != odcid =>
7262                    return Err(Error::InvalidTransportParam),
7263
7264                Some(_) => (),
7265
7266                // original_destination_connection_id must be
7267                // sent by the server.
7268                None if !self.is_server =>
7269                    return Err(Error::InvalidTransportParam),
7270
7271                None => (),
7272            }
7273        }
7274
7275        // Validate retry_source_connection_id.
7276        if let Some(rscid) = &self.rscid {
7277            match &peer_params.retry_source_connection_id {
7278                Some(v) if v != rscid =>
7279                    return Err(Error::InvalidTransportParam),
7280
7281                Some(_) => (),
7282
7283                // retry_source_connection_id must be sent by
7284                // the server.
7285                None => return Err(Error::InvalidTransportParam),
7286            }
7287        }
7288
7289        self.process_peer_transport_params(peer_params)?;
7290
7291        self.parsed_peer_transport_params = true;
7292
7293        Ok(())
7294    }
7295
7296    fn process_peer_transport_params(
7297        &mut self, peer_params: TransportParams,
7298    ) -> Result<()> {
7299        self.max_tx_data = peer_params.initial_max_data;
7300
7301        // Update send capacity.
7302        self.update_tx_cap();
7303
7304        self.streams
7305            .update_peer_max_streams_bidi(peer_params.initial_max_streams_bidi);
7306        self.streams
7307            .update_peer_max_streams_uni(peer_params.initial_max_streams_uni);
7308
7309        let max_ack_delay = Duration::from_millis(peer_params.max_ack_delay);
7310
7311        self.recovery_config.max_ack_delay = max_ack_delay;
7312
7313        let active_path = self.paths.get_active_mut()?;
7314
7315        active_path.recovery.update_max_ack_delay(max_ack_delay);
7316
7317        if active_path
7318            .pmtud
7319            .as_ref()
7320            .map(|pmtud| pmtud.should_probe())
7321            .unwrap_or(false)
7322        {
7323            active_path.recovery.pmtud_update_max_datagram_size(
7324                active_path
7325                    .pmtud
7326                    .as_mut()
7327                    .expect("PMTUD existence verified above")
7328                    .get_probe_size()
7329                    .min(peer_params.max_udp_payload_size as usize),
7330            );
7331        } else {
7332            active_path.recovery.update_max_datagram_size(
7333                peer_params.max_udp_payload_size as usize,
7334            );
7335        }
7336
7337        // Record the max_active_conn_id parameter advertised by the peer.
7338        self.ids
7339            .set_source_conn_id_limit(peer_params.active_conn_id_limit);
7340
7341        self.peer_transport_params = peer_params;
7342
7343        Ok(())
7344    }
7345
7346    /// Continues the handshake.
7347    ///
7348    /// If the connection is already established, it does nothing.
7349    fn do_handshake(&mut self, now: Instant) -> Result<()> {
7350        let mut ex_data = tls::ExData {
7351            application_protos: &self.application_protos,
7352
7353            crypto_ctx: &mut self.crypto_ctx,
7354
7355            session: &mut self.session,
7356
7357            local_error: &mut self.local_error,
7358
7359            keylog: self.keylog.as_mut(),
7360
7361            trace_id: &self.trace_id,
7362
7363            local_transport_params: self.local_transport_params.clone(),
7364
7365            recovery_config: self.recovery_config,
7366
7367            tx_cap_factor: self.tx_cap_factor,
7368
7369            pmtud: None,
7370
7371            is_server: self.is_server,
7372        };
7373
7374        if self.handshake_completed {
7375            return self.handshake.process_post_handshake(&mut ex_data);
7376        }
7377
7378        match self.handshake.do_handshake(&mut ex_data) {
7379            Ok(_) => (),
7380
7381            Err(Error::Done) => {
7382                // Apply in-handshake configuration from callbacks before any
7383                // packet has been sent.
7384                if self.sent_count == 0 {
7385                    if ex_data.recovery_config != self.recovery_config {
7386                        if let Ok(path) = self.paths.get_active_mut() {
7387                            self.recovery_config = ex_data.recovery_config;
7388                            path.reinit_recovery(&self.recovery_config);
7389                        }
7390                    }
7391
7392                    if ex_data.tx_cap_factor != self.tx_cap_factor {
7393                        self.tx_cap_factor = ex_data.tx_cap_factor;
7394                    }
7395
7396                    if let Some(discover) = ex_data.pmtud {
7397                        self.paths.set_discover_pmtu_on_existing_paths(
7398                            discover,
7399                            self.recovery_config.max_send_udp_payload_size,
7400                        );
7401                    }
7402
7403                    if ex_data.local_transport_params !=
7404                        self.local_transport_params
7405                    {
7406                        self.streams.set_max_streams_bidi(
7407                            ex_data
7408                                .local_transport_params
7409                                .initial_max_streams_bidi,
7410                        );
7411
7412                        self.local_transport_params =
7413                            ex_data.local_transport_params;
7414                    }
7415                }
7416
7417                // Try to parse transport parameters as soon as the first flight
7418                // of handshake data is processed.
7419                //
7420                // This is potentially dangerous as the handshake hasn't been
7421                // completed yet, though it's required to be able to send data
7422                // in 0.5 RTT.
7423                let raw_params = self.handshake.quic_transport_params();
7424
7425                if !self.parsed_peer_transport_params && !raw_params.is_empty() {
7426                    let peer_params = TransportParams::decode(
7427                        raw_params,
7428                        self.is_server,
7429                        self.peer_transport_params_track_unknown,
7430                    )?;
7431
7432                    self.parse_peer_transport_params(peer_params)?;
7433                }
7434
7435                return Ok(());
7436            },
7437
7438            Err(e) => return Err(e),
7439        };
7440
7441        self.handshake_completed = self.handshake.is_completed();
7442
7443        self.alpn = self.handshake.alpn_protocol().to_vec();
7444
7445        let raw_params = self.handshake.quic_transport_params();
7446
7447        if !self.parsed_peer_transport_params && !raw_params.is_empty() {
7448            let peer_params = TransportParams::decode(
7449                raw_params,
7450                self.is_server,
7451                self.peer_transport_params_track_unknown,
7452            )?;
7453
7454            self.parse_peer_transport_params(peer_params)?;
7455        }
7456
7457        if self.handshake_completed {
7458            // The handshake is considered confirmed at the server when the
7459            // handshake completes, at which point we can also drop the
7460            // handshake epoch.
7461            if self.is_server {
7462                self.handshake_confirmed = true;
7463
7464                self.drop_epoch_state(packet::Epoch::Handshake, now);
7465            }
7466
7467            // Once the handshake is completed there's no point in processing
7468            // 0-RTT packets anymore, so clear the buffer now.
7469            self.undecryptable_pkts.clear();
7470
7471            trace!("{} connection established: proto={:?} cipher={:?} curve={:?} sigalg={:?} resumed={} {:?}",
7472                   &self.trace_id,
7473                   std::str::from_utf8(self.application_proto()),
7474                   self.handshake.cipher(),
7475                   self.handshake.curve(),
7476                   self.handshake.sigalg(),
7477                   self.handshake.is_resumed(),
7478                   self.peer_transport_params);
7479        }
7480
7481        Ok(())
7482    }
7483
7484    /// Selects the packet type for the next outgoing packet.
7485    fn write_pkt_type(&self, send_pid: usize) -> Result<Type> {
7486        // On error send packet in the latest epoch available, but only send
7487        // 1-RTT ones when the handshake is completed.
7488        if self
7489            .local_error
7490            .as_ref()
7491            .is_some_and(|conn_err| !conn_err.is_app)
7492        {
7493            let epoch = match self.handshake.write_level() {
7494                crypto::Level::Initial => packet::Epoch::Initial,
7495                crypto::Level::ZeroRTT => unreachable!(),
7496                crypto::Level::Handshake => packet::Epoch::Handshake,
7497                crypto::Level::OneRTT => packet::Epoch::Application,
7498            };
7499
7500            if !self.handshake_confirmed {
7501                match epoch {
7502                    // Downgrade the epoch to Handshake as the handshake is not
7503                    // completed yet.
7504                    packet::Epoch::Application => return Ok(Type::Handshake),
7505
7506                    // Downgrade the epoch to Initial as the remote peer might
7507                    // not be able to decrypt handshake packets yet.
7508                    packet::Epoch::Handshake
7509                        if self.crypto_ctx[packet::Epoch::Initial].has_keys() =>
7510                        return Ok(Type::Initial),
7511
7512                    _ => (),
7513                };
7514            }
7515
7516            return Ok(Type::from_epoch(epoch));
7517        }
7518
7519        for &epoch in packet::Epoch::epochs(
7520            packet::Epoch::Initial..=packet::Epoch::Application,
7521        ) {
7522            let crypto_ctx = &self.crypto_ctx[epoch];
7523            let pkt_space = &self.pkt_num_spaces[epoch];
7524
7525            // Only send packets in a space when we have the send keys for it.
7526            if crypto_ctx.crypto_seal.is_none() {
7527                continue;
7528            }
7529
7530            // We are ready to send data for this packet number space.
7531            if crypto_ctx.data_available() || pkt_space.ready() {
7532                return Ok(Type::from_epoch(epoch));
7533            }
7534
7535            // There are lost frames in this packet number space.
7536            for (_, p) in self.paths.iter() {
7537                if p.recovery.has_lost_frames(epoch) {
7538                    return Ok(Type::from_epoch(epoch));
7539                }
7540
7541                // We need to send PTO probe packets.
7542                if p.recovery.loss_probes(epoch) > 0 {
7543                    return Ok(Type::from_epoch(epoch));
7544                }
7545            }
7546        }
7547
7548        // If there are flushable, almost full or blocked streams, use the
7549        // Application epoch.
7550        let send_path = self.paths.get(send_pid)?;
7551        if (self.is_established() || self.is_in_early_data()) &&
7552            (self.should_send_handshake_done() ||
7553                self.almost_full ||
7554                self.blocked_limit.is_some() ||
7555                self.dgram_send_queue.has_pending() ||
7556                self.local_error
7557                    .as_ref()
7558                    .is_some_and(|conn_err| conn_err.is_app) ||
7559                self.streams.should_update_max_streams_bidi() ||
7560                self.streams.should_update_max_streams_uni() ||
7561                self.streams.has_flushable() ||
7562                self.streams.has_almost_full() ||
7563                self.streams.has_blocked() ||
7564                self.streams.has_reset() ||
7565                self.streams.has_stopped() ||
7566                self.ids.has_new_scids() ||
7567                self.ids.has_retire_dcids() ||
7568                send_path
7569                    .pmtud
7570                    .as_ref()
7571                    .is_some_and(|pmtud| pmtud.should_probe()) ||
7572                send_path.needs_ack_eliciting ||
7573                send_path.probing_required())
7574        {
7575            // Only clients can send 0-RTT packets.
7576            if !self.is_server && self.is_in_early_data() {
7577                return Ok(Type::ZeroRTT);
7578            }
7579
7580            return Ok(Type::Short);
7581        }
7582
7583        Err(Error::Done)
7584    }
7585
7586    /// Returns the mutable stream with the given ID if it exists, or creates
7587    /// a new one otherwise.
7588    fn get_or_create_stream(
7589        &mut self, id: u64, local: bool,
7590    ) -> Result<&mut stream::Stream<F>> {
7591        self.streams.get_or_create(
7592            id,
7593            &self.local_transport_params,
7594            &self.peer_transport_params,
7595            local,
7596            self.is_server,
7597        )
7598    }
7599
7600    /// Processes an incoming frame.
7601    fn process_frame(
7602        &mut self, frame: frame::Frame, hdr: &Header, recv_path_id: usize,
7603        epoch: packet::Epoch, now: Instant,
7604    ) -> Result<()> {
7605        trace!("{} rx frm {:?}", self.trace_id, frame);
7606
7607        match frame {
7608            frame::Frame::Padding { .. } => (),
7609
7610            frame::Frame::Ping { .. } => (),
7611
7612            frame::Frame::ACK {
7613                ranges, ack_delay, ..
7614            } => {
7615                let ack_delay = ack_delay
7616                    .checked_mul(2_u64.pow(
7617                        self.peer_transport_params.ack_delay_exponent as u32,
7618                    ))
7619                    .ok_or(Error::InvalidFrame)?;
7620
7621                if epoch == packet::Epoch::Handshake ||
7622                    (epoch == packet::Epoch::Application &&
7623                        self.is_established())
7624                {
7625                    self.peer_verified_initial_address = true;
7626                }
7627
7628                let handshake_status = self.handshake_status();
7629
7630                let is_app_limited = self.delivery_rate_check_if_app_limited();
7631
7632                let largest_acked = ranges.last().expect(
7633                    "ACK frames should always have at least one ack range",
7634                );
7635
7636                for (_, p) in self.paths.iter_mut() {
7637                    if self.pkt_num_spaces[epoch]
7638                        .largest_tx_pkt_num
7639                        .is_some_and(|largest_sent| largest_sent < largest_acked)
7640                    {
7641                        // https://www.rfc-editor.org/rfc/rfc9000#section-13.1
7642                        // An endpoint SHOULD treat receipt of an acknowledgment
7643                        // for a packet it did not send as
7644                        // a connection error of type PROTOCOL_VIOLATION
7645                        return Err(Error::InvalidAckRange);
7646                    }
7647
7648                    if is_app_limited {
7649                        p.recovery.delivery_rate_update_app_limited(true);
7650                    }
7651
7652                    let OnAckReceivedOutcome {
7653                        lost_packets,
7654                        lost_bytes,
7655                        acked_bytes,
7656                        spurious_losses,
7657                    } = p.recovery.on_ack_received(
7658                        &ranges,
7659                        ack_delay,
7660                        epoch,
7661                        handshake_status,
7662                        now,
7663                        self.pkt_num_manager.skip_pn(),
7664                        &self.trace_id,
7665                    )?;
7666
7667                    let skip_pn = self.pkt_num_manager.skip_pn();
7668                    let largest_acked =
7669                        p.recovery.get_largest_acked_on_epoch(epoch);
7670
7671                    // Consider the skip_pn validated if the peer has sent an ack
7672                    // for a larger pkt number.
7673                    if let Some((largest_acked, skip_pn)) =
7674                        largest_acked.zip(skip_pn)
7675                    {
7676                        if largest_acked > skip_pn {
7677                            self.pkt_num_manager.set_skip_pn(None);
7678                        }
7679                    }
7680
7681                    self.lost_count += lost_packets;
7682                    self.lost_bytes += lost_bytes as u64;
7683                    self.acked_bytes += acked_bytes as u64;
7684                    self.spurious_lost_count += spurious_losses;
7685                }
7686            },
7687
7688            frame::Frame::ResetStream {
7689                stream_id,
7690                error_code,
7691                final_size,
7692            } => {
7693                // Peer can't send on our unidirectional streams.
7694                if !stream::is_bidi(stream_id) &&
7695                    stream::is_local(stream_id, self.is_server)
7696                {
7697                    return Err(Error::InvalidStreamState(stream_id));
7698                }
7699
7700                let max_rx_data_left = self.max_rx_data() - self.rx_data;
7701
7702                // Get existing stream or create a new one, but if the stream
7703                // has already been closed and collected, ignore the frame.
7704                //
7705                // This can happen if e.g. an ACK frame is lost, and the peer
7706                // retransmits another frame before it realizes that the stream
7707                // is gone.
7708                //
7709                // Note that it makes it impossible to check if the frame is
7710                // illegal, since we have no state, but since we ignore the
7711                // frame, it should be fine.
7712                let stream = match self.get_or_create_stream(stream_id, false) {
7713                    Ok(v) => v,
7714
7715                    Err(Error::Done) => return Ok(()),
7716
7717                    Err(e) => return Err(e),
7718                };
7719
7720                let was_readable = stream.is_readable();
7721                let priority_key = Arc::clone(&stream.priority_key);
7722
7723                let stream::RecvBufResetReturn {
7724                    max_data_delta,
7725                    consumed_flowcontrol,
7726                } = stream.recv.reset(error_code, final_size)?;
7727
7728                if max_data_delta > max_rx_data_left {
7729                    return Err(Error::FlowControl);
7730                }
7731
7732                if !was_readable && stream.is_readable() {
7733                    self.streams.insert_readable(&priority_key);
7734                }
7735
7736                self.rx_data += max_data_delta;
7737                // We dropped the receive buffer, return connection level
7738                // flow-control
7739                self.flow_control.add_consumed(consumed_flowcontrol);
7740
7741                // ... and check if need to send an updated MAX_DATA frame
7742                if self.should_update_max_data() {
7743                    self.almost_full = true;
7744                }
7745
7746                self.reset_stream_remote_count =
7747                    self.reset_stream_remote_count.saturating_add(1);
7748            },
7749
7750            frame::Frame::StopSending {
7751                stream_id,
7752                error_code,
7753            } => {
7754                // STOP_SENDING on a receive-only stream is a fatal error.
7755                if !stream::is_local(stream_id, self.is_server) &&
7756                    !stream::is_bidi(stream_id)
7757                {
7758                    return Err(Error::InvalidStreamState(stream_id));
7759                }
7760
7761                // Get existing stream or create a new one, but if the stream
7762                // has already been closed and collected, ignore the frame.
7763                //
7764                // This can happen if e.g. an ACK frame is lost, and the peer
7765                // retransmits another frame before it realizes that the stream
7766                // is gone.
7767                //
7768                // Note that it makes it impossible to check if the frame is
7769                // illegal, since we have no state, but since we ignore the
7770                // frame, it should be fine.
7771                let stream = match self.get_or_create_stream(stream_id, false) {
7772                    Ok(v) => v,
7773
7774                    Err(Error::Done) => return Ok(()),
7775
7776                    Err(e) => return Err(e),
7777                };
7778
7779                let was_writable = stream.is_writable();
7780
7781                let priority_key = Arc::clone(&stream.priority_key);
7782
7783                // Try stopping the stream.
7784                if let Ok((final_size, unsent)) = stream.send.stop(error_code) {
7785                    // Claw back some flow control allowance from data that was
7786                    // buffered but not actually sent before the stream was
7787                    // reset.
7788                    //
7789                    // Note that `tx_cap` will be updated later on, so no need
7790                    // to touch it here.
7791                    self.tx_data = self.tx_data.saturating_sub(unsent);
7792
7793                    self.tx_buffered =
7794                        self.tx_buffered.saturating_sub(unsent as usize);
7795
7796                    // These drops in qlog are a bit weird, but the only way to
7797                    // ensure that all bytes that are moved from App to Transport
7798                    // in stream_do_send are eventually moved from Transport to
7799                    // Dropped.  Ideally we would add a Transport to Network
7800                    // transition also as a way to indicate when bytes were
7801                    // transmitted vs dropped without ever being sent.
7802                    qlog_with_type!(QLOG_DATA_MV, self.qlog, q, {
7803                        let ev_data =
7804                            EventData::DataMoved(qlog::events::quic::DataMoved {
7805                                stream_id: Some(stream_id),
7806                                offset: Some(final_size),
7807                                length: Some(unsent),
7808                                from: Some(DataRecipient::Transport),
7809                                to: Some(DataRecipient::Dropped),
7810                                ..Default::default()
7811                            });
7812
7813                        q.add_event_data_with_instant(ev_data, now).ok();
7814                    });
7815
7816                    self.streams.insert_reset(stream_id, error_code, final_size);
7817
7818                    if !was_writable {
7819                        self.streams.insert_writable(&priority_key);
7820                    }
7821
7822                    self.stopped_stream_remote_count =
7823                        self.stopped_stream_remote_count.saturating_add(1);
7824                    self.reset_stream_local_count =
7825                        self.reset_stream_local_count.saturating_add(1);
7826                }
7827            },
7828
7829            frame::Frame::Crypto { data } => {
7830                if data.max_off() >= MAX_CRYPTO_STREAM_OFFSET {
7831                    return Err(Error::CryptoBufferExceeded);
7832                }
7833
7834                // Push the data to the stream so it can be re-ordered.
7835                self.crypto_ctx[epoch].crypto_stream.recv.write(data)?;
7836
7837                // Feed crypto data to the TLS state, if there's data
7838                // available at the expected offset.
7839                let mut crypto_buf = [0; 512];
7840
7841                let level = crypto::Level::from_epoch(epoch);
7842
7843                let stream = &mut self.crypto_ctx[epoch].crypto_stream;
7844
7845                while let Ok((read, _)) = stream.recv.emit(&mut crypto_buf) {
7846                    let recv_buf = &crypto_buf[..read];
7847                    self.handshake.provide_data(level, recv_buf)?;
7848                }
7849
7850                self.do_handshake(now)?;
7851            },
7852
7853            frame::Frame::CryptoHeader { .. } => unreachable!(),
7854
7855            // TODO: implement stateless retry
7856            frame::Frame::NewToken { .. } =>
7857                if self.is_server {
7858                    return Err(Error::InvalidPacket);
7859                },
7860
7861            frame::Frame::Stream { stream_id, data } => {
7862                // Peer can't send on our unidirectional streams.
7863                if !stream::is_bidi(stream_id) &&
7864                    stream::is_local(stream_id, self.is_server)
7865                {
7866                    return Err(Error::InvalidStreamState(stream_id));
7867                }
7868
7869                let max_rx_data_left = self.max_rx_data() - self.rx_data;
7870
7871                // Get existing stream or create a new one, but if the stream
7872                // has already been closed and collected, ignore the frame.
7873                //
7874                // This can happen if e.g. an ACK frame is lost, and the peer
7875                // retransmits another frame before it realizes that the stream
7876                // is gone.
7877                //
7878                // Note that it makes it impossible to check if the frame is
7879                // illegal, since we have no state, but since we ignore the
7880                // frame, it should be fine.
7881                let stream = match self.get_or_create_stream(stream_id, false) {
7882                    Ok(v) => v,
7883
7884                    Err(Error::Done) => return Ok(()),
7885
7886                    Err(e) => return Err(e),
7887                };
7888
7889                // Check for the connection-level flow control limit.
7890                let max_off_delta =
7891                    data.max_off().saturating_sub(stream.recv.max_off());
7892
7893                if max_off_delta > max_rx_data_left {
7894                    return Err(Error::FlowControl);
7895                }
7896
7897                let was_readable = stream.is_readable();
7898                let priority_key = Arc::clone(&stream.priority_key);
7899
7900                let was_draining = stream.recv.is_draining();
7901
7902                stream.recv.write(data)?;
7903
7904                if !was_readable && stream.is_readable() {
7905                    self.streams.insert_readable(&priority_key);
7906                }
7907
7908                self.rx_data += max_off_delta;
7909
7910                if was_draining {
7911                    // When a stream is in draining state it will not queue
7912                    // incoming data for the application to read, so consider
7913                    // the received data as consumed, which might trigger a flow
7914                    // control update.
7915                    self.flow_control.add_consumed(max_off_delta);
7916
7917                    if self.should_update_max_data() {
7918                        self.almost_full = true;
7919                    }
7920                }
7921            },
7922
7923            frame::Frame::StreamHeader { .. } => unreachable!(),
7924
7925            frame::Frame::MaxData { max } => {
7926                self.max_tx_data = cmp::max(self.max_tx_data, max);
7927            },
7928
7929            frame::Frame::MaxStreamData { stream_id, max } => {
7930                // Peer can't receive on its own unidirectional streams.
7931                if !stream::is_bidi(stream_id) &&
7932                    !stream::is_local(stream_id, self.is_server)
7933                {
7934                    return Err(Error::InvalidStreamState(stream_id));
7935                }
7936
7937                // Get existing stream or create a new one, but if the stream
7938                // has already been closed and collected, ignore the frame.
7939                //
7940                // This can happen if e.g. an ACK frame is lost, and the peer
7941                // retransmits another frame before it realizes that the stream
7942                // is gone.
7943                //
7944                // Note that it makes it impossible to check if the frame is
7945                // illegal, since we have no state, but since we ignore the
7946                // frame, it should be fine.
7947                let stream = match self.get_or_create_stream(stream_id, false) {
7948                    Ok(v) => v,
7949
7950                    Err(Error::Done) => return Ok(()),
7951
7952                    Err(e) => return Err(e),
7953                };
7954
7955                let was_flushable = stream.is_flushable();
7956
7957                stream.send.update_max_data(max);
7958
7959                let writable = stream.is_writable();
7960
7961                let priority_key = Arc::clone(&stream.priority_key);
7962
7963                // If the stream is now flushable push it to the flushable queue,
7964                // but only if it wasn't already queued.
7965                if stream.is_flushable() && !was_flushable {
7966                    let priority_key = Arc::clone(&stream.priority_key);
7967                    self.streams.insert_flushable(&priority_key);
7968                }
7969
7970                if writable {
7971                    self.streams.insert_writable(&priority_key);
7972                }
7973            },
7974
7975            frame::Frame::MaxStreamsBidi { max } => {
7976                if max > MAX_STREAM_ID {
7977                    return Err(Error::InvalidFrame);
7978                }
7979
7980                self.streams.update_peer_max_streams_bidi(max);
7981            },
7982
7983            frame::Frame::MaxStreamsUni { max } => {
7984                if max > MAX_STREAM_ID {
7985                    return Err(Error::InvalidFrame);
7986                }
7987
7988                self.streams.update_peer_max_streams_uni(max);
7989            },
7990
7991            frame::Frame::DataBlocked { .. } => {
7992                self.data_blocked_recv_count =
7993                    self.data_blocked_recv_count.saturating_add(1);
7994            },
7995
7996            frame::Frame::StreamDataBlocked { .. } => {
7997                self.stream_data_blocked_recv_count =
7998                    self.stream_data_blocked_recv_count.saturating_add(1);
7999            },
8000
8001            frame::Frame::StreamsBlockedBidi { limit } => {
8002                if limit > MAX_STREAM_ID {
8003                    return Err(Error::InvalidFrame);
8004                }
8005            },
8006
8007            frame::Frame::StreamsBlockedUni { limit } => {
8008                if limit > MAX_STREAM_ID {
8009                    return Err(Error::InvalidFrame);
8010                }
8011            },
8012
8013            frame::Frame::NewConnectionId {
8014                seq_num,
8015                retire_prior_to,
8016                conn_id,
8017                reset_token,
8018            } => {
8019                if self.ids.zero_length_dcid() {
8020                    return Err(Error::InvalidState);
8021                }
8022
8023                let mut retired_path_ids = SmallVec::new();
8024
8025                // Retire pending path IDs before propagating the error code to
8026                // make sure retired connection IDs are not in use anymore.
8027                let new_dcid_res = self.ids.new_dcid(
8028                    conn_id.into(),
8029                    seq_num,
8030                    u128::from_be_bytes(reset_token),
8031                    retire_prior_to,
8032                    &mut retired_path_ids,
8033                );
8034
8035                for (dcid_seq, pid) in retired_path_ids {
8036                    let path = self.paths.get_mut(pid)?;
8037
8038                    // Maybe the path already switched to another DCID.
8039                    if path.active_dcid_seq != Some(dcid_seq) {
8040                        continue;
8041                    }
8042
8043                    if let Some(new_dcid_seq) =
8044                        self.ids.lowest_available_dcid_seq()
8045                    {
8046                        path.active_dcid_seq = Some(new_dcid_seq);
8047
8048                        self.ids.link_dcid_to_path_id(new_dcid_seq, pid)?;
8049
8050                        trace!(
8051                            "{} path ID {} changed DCID: old seq num {} new seq num {}",
8052                            self.trace_id, pid, dcid_seq, new_dcid_seq,
8053                        );
8054                    } else {
8055                        // We cannot use this path anymore for now.
8056                        path.active_dcid_seq = None;
8057
8058                        trace!(
8059                            "{} path ID {} cannot be used; DCID seq num {} has been retired",
8060                            self.trace_id, pid, dcid_seq,
8061                        );
8062                    }
8063                }
8064
8065                // Propagate error (if any) now...
8066                new_dcid_res?;
8067            },
8068
8069            frame::Frame::RetireConnectionId { seq_num } => {
8070                if self.ids.zero_length_scid() {
8071                    return Err(Error::InvalidState);
8072                }
8073
8074                if let Some(pid) = self.ids.retire_scid(seq_num, &hdr.dcid)? {
8075                    let path = self.paths.get_mut(pid)?;
8076
8077                    // Maybe we already linked a new SCID to that path.
8078                    if path.active_scid_seq == Some(seq_num) {
8079                        // XXX: We do not remove unused paths now, we instead
8080                        // wait until we need to maintain more paths than the
8081                        // host is willing to.
8082                        path.active_scid_seq = None;
8083                    }
8084                }
8085            },
8086
8087            frame::Frame::PathChallenge { data } => {
8088                self.path_challenge_rx_count += 1;
8089
8090                self.paths
8091                    .get_mut(recv_path_id)?
8092                    .on_challenge_received(data);
8093            },
8094
8095            frame::Frame::PathResponse { data } => {
8096                self.paths.on_response_received(data)?;
8097            },
8098
8099            frame::Frame::ConnectionClose {
8100                error_code, reason, ..
8101            } => {
8102                self.peer_error = Some(ConnectionError {
8103                    is_app: false,
8104                    error_code,
8105                    reason,
8106                });
8107
8108                let path = self.paths.get_active()?;
8109                self.draining_timer = Some(now + (path.recovery.pto() * 3));
8110            },
8111
8112            frame::Frame::ApplicationClose { error_code, reason } => {
8113                self.peer_error = Some(ConnectionError {
8114                    is_app: true,
8115                    error_code,
8116                    reason,
8117                });
8118
8119                let path = self.paths.get_active()?;
8120                self.draining_timer = Some(now + (path.recovery.pto() * 3));
8121            },
8122
8123            frame::Frame::HandshakeDone => {
8124                if self.is_server {
8125                    return Err(Error::InvalidPacket);
8126                }
8127
8128                self.peer_verified_initial_address = true;
8129
8130                self.handshake_confirmed = true;
8131
8132                // Once the handshake is confirmed, we can drop Handshake keys.
8133                self.drop_epoch_state(packet::Epoch::Handshake, now);
8134            },
8135
8136            frame::Frame::Datagram { data } => {
8137                // Close the connection if DATAGRAMs are not enabled.
8138                // quiche always advertises support for 64K sized DATAGRAM
8139                // frames, as recommended by the standard, so we don't need a
8140                // size check.
8141                if !self.dgram_enabled() {
8142                    return Err(Error::InvalidState);
8143                }
8144
8145                // If recv queue is full, discard oldest
8146                if self.dgram_recv_queue.is_full() {
8147                    self.dgram_recv_queue.pop();
8148                }
8149
8150                self.dgram_recv_queue.push(data)?;
8151
8152                self.dgram_recv_count = self.dgram_recv_count.saturating_add(1);
8153
8154                let path = self.paths.get_mut(recv_path_id)?;
8155                path.dgram_recv_count = path.dgram_recv_count.saturating_add(1);
8156            },
8157
8158            frame::Frame::DatagramHeader { .. } => unreachable!(),
8159        }
8160
8161        Ok(())
8162    }
8163
8164    /// Drops the keys and recovery state for the given epoch.
8165    fn drop_epoch_state(&mut self, epoch: packet::Epoch, now: Instant) {
8166        let crypto_ctx = &mut self.crypto_ctx[epoch];
8167        if crypto_ctx.crypto_open.is_none() {
8168            return;
8169        }
8170        crypto_ctx.clear();
8171        self.pkt_num_spaces[epoch].clear();
8172
8173        let handshake_status = self.handshake_status();
8174        for (_, p) in self.paths.iter_mut() {
8175            p.recovery
8176                .on_pkt_num_space_discarded(epoch, handshake_status, now);
8177        }
8178
8179        trace!("{} dropped epoch {} state", self.trace_id, epoch);
8180    }
8181
8182    /// Returns true if the connection-level flow control needs to be updated.
8183    ///
8184    /// This happens when the new max data limit is at least double the amount
8185    /// of data that can be received before blocking.
8186    fn should_update_max_data(&self) -> bool {
8187        self.flow_control.should_update_max_data()
8188    }
8189
8190    /// Returns the connection level flow control limit.
8191    fn max_rx_data(&self) -> u64 {
8192        self.flow_control.max_data()
8193    }
8194
8195    /// Returns true if the HANDSHAKE_DONE frame needs to be sent.
8196    fn should_send_handshake_done(&self) -> bool {
8197        self.is_established() && !self.handshake_done_sent && self.is_server
8198    }
8199
8200    /// Returns the idle timeout value.
8201    ///
8202    /// `None` is returned if both end-points disabled the idle timeout.
8203    fn idle_timeout(&self) -> Option<Duration> {
8204        // If the transport parameter is set to 0, then the respective endpoint
8205        // decided to disable the idle timeout. If both are disabled we should
8206        // not set any timeout.
8207        if self.local_transport_params.max_idle_timeout == 0 &&
8208            self.peer_transport_params.max_idle_timeout == 0
8209        {
8210            return None;
8211        }
8212
8213        // If the local endpoint or the peer disabled the idle timeout, use the
8214        // other peer's value, otherwise use the minimum of the two values.
8215        let idle_timeout = if self.local_transport_params.max_idle_timeout == 0 {
8216            self.peer_transport_params.max_idle_timeout
8217        } else if self.peer_transport_params.max_idle_timeout == 0 {
8218            self.local_transport_params.max_idle_timeout
8219        } else {
8220            cmp::min(
8221                self.local_transport_params.max_idle_timeout,
8222                self.peer_transport_params.max_idle_timeout,
8223            )
8224        };
8225
8226        let path_pto = match self.paths.get_active() {
8227            Ok(p) => p.recovery.pto(),
8228            Err(_) => Duration::ZERO,
8229        };
8230
8231        let idle_timeout = Duration::from_millis(idle_timeout);
8232        let idle_timeout = cmp::max(idle_timeout, 3 * path_pto);
8233
8234        Some(idle_timeout)
8235    }
8236
8237    /// Returns the connection's handshake status for use in loss recovery.
8238    fn handshake_status(&self) -> recovery::HandshakeStatus {
8239        recovery::HandshakeStatus {
8240            has_handshake_keys: self.crypto_ctx[packet::Epoch::Handshake]
8241                .has_keys(),
8242
8243            peer_verified_address: self.peer_verified_initial_address,
8244
8245            completed: self.is_established(),
8246        }
8247    }
8248
8249    /// Updates send capacity.
8250    fn update_tx_cap(&mut self) {
8251        let cwin_available = match self.paths.get_active() {
8252            Ok(p) => p.recovery.cwnd_available() as u64,
8253            Err(_) => 0,
8254        };
8255
8256        let cap =
8257            cmp::min(cwin_available, self.max_tx_data - self.tx_data) as usize;
8258        self.tx_cap = (cap as f64 * self.tx_cap_factor).ceil() as usize;
8259    }
8260
8261    fn delivery_rate_check_if_app_limited(&self) -> bool {
8262        // Enter the app-limited phase of delivery rate when these conditions
8263        // are met:
8264        //
8265        // - The remaining capacity is higher than available bytes in cwnd (there
8266        //   is more room to send).
8267        // - New data since the last send() is smaller than available bytes in
8268        //   cwnd (we queued less than what we can send).
8269        // - There is room to send more data in cwnd.
8270        //
8271        // In application-limited phases the transmission rate is limited by the
8272        // application rather than the congestion control algorithm.
8273        //
8274        // Note that this is equivalent to CheckIfApplicationLimited() from the
8275        // delivery rate draft. This is also separate from `recovery.app_limited`
8276        // and only applies to delivery rate calculation.
8277        let cwin_available = self
8278            .paths
8279            .iter()
8280            .filter(|&(_, p)| p.active())
8281            .map(|(_, p)| p.recovery.cwnd_available())
8282            .sum();
8283
8284        ((self.tx_buffered + self.dgram_send_queue_byte_size()) < cwin_available) &&
8285            (self.tx_data.saturating_sub(self.last_tx_data)) <
8286                cwin_available as u64 &&
8287            cwin_available > 0
8288    }
8289
8290    fn check_tx_buffered_invariant(&mut self) {
8291        // tx_buffered should track bytes queued in the stream buffers
8292        // and unacked retransmitable bytes in the network.
8293        // If tx_buffered > 0 mark the tx_buffered_state if there are no
8294        // flushable streams and there no inflight bytes.
8295        //
8296        // It is normal to have tx_buffered == 0 while there are inflight bytes
8297        // since not QUIC frames are retransmittable; inflight tracks all bytes
8298        // on the network which are subject to congestion control.
8299        if self.tx_buffered > 0 &&
8300            !self.streams.has_flushable() &&
8301            !self
8302                .paths
8303                .iter()
8304                .any(|(_, p)| p.recovery.bytes_in_flight() > 0)
8305        {
8306            self.tx_buffered_state = TxBufferTrackingState::Inconsistent;
8307        }
8308    }
8309
8310    fn set_initial_dcid(
8311        &mut self, cid: ConnectionId<'static>, reset_token: Option<u128>,
8312        path_id: usize,
8313    ) -> Result<()> {
8314        self.ids.set_initial_dcid(cid, reset_token, Some(path_id));
8315        self.paths.get_mut(path_id)?.active_dcid_seq = Some(0);
8316
8317        Ok(())
8318    }
8319
8320    /// Selects the path that the incoming packet belongs to, or creates a new
8321    /// one if no existing path matches.
8322    fn get_or_create_recv_path_id(
8323        &mut self, recv_pid: Option<usize>, dcid: &ConnectionId, buf_len: usize,
8324        info: &RecvInfo,
8325    ) -> Result<usize> {
8326        let ids = &mut self.ids;
8327
8328        let (in_scid_seq, mut in_scid_pid) =
8329            ids.find_scid_seq(dcid).ok_or(Error::InvalidState)?;
8330
8331        if let Some(recv_pid) = recv_pid {
8332            // If the path observes a change of SCID used, note it.
8333            let recv_path = self.paths.get_mut(recv_pid)?;
8334
8335            let cid_entry =
8336                recv_path.active_scid_seq.and_then(|v| ids.get_scid(v).ok());
8337
8338            if cid_entry.map(|e| &e.cid) != Some(dcid) {
8339                let incoming_cid_entry = ids.get_scid(in_scid_seq)?;
8340
8341                let prev_recv_pid =
8342                    incoming_cid_entry.path_id.unwrap_or(recv_pid);
8343
8344                if prev_recv_pid != recv_pid {
8345                    trace!(
8346                        "{} peer reused CID {:?} from path {} on path {}",
8347                        self.trace_id,
8348                        dcid,
8349                        prev_recv_pid,
8350                        recv_pid
8351                    );
8352
8353                    // TODO: reset congestion control.
8354                }
8355
8356                trace!(
8357                    "{} path ID {} now see SCID with seq num {}",
8358                    self.trace_id,
8359                    recv_pid,
8360                    in_scid_seq
8361                );
8362
8363                recv_path.active_scid_seq = Some(in_scid_seq);
8364                ids.link_scid_to_path_id(in_scid_seq, recv_pid)?;
8365            }
8366
8367            return Ok(recv_pid);
8368        }
8369
8370        // This is a new 4-tuple. See if the CID has not been assigned on
8371        // another path.
8372
8373        // Ignore this step if are using zero-length SCID.
8374        if ids.zero_length_scid() {
8375            in_scid_pid = None;
8376        }
8377
8378        if let Some(in_scid_pid) = in_scid_pid {
8379            // This CID has been used by another path. If we have the
8380            // room to do so, create a new `Path` structure holding this
8381            // new 4-tuple. Otherwise, drop the packet.
8382            let old_path = self.paths.get_mut(in_scid_pid)?;
8383            let old_local_addr = old_path.local_addr();
8384            let old_peer_addr = old_path.peer_addr();
8385
8386            trace!(
8387                "{} reused CID seq {} of ({},{}) (path {}) on ({},{})",
8388                self.trace_id,
8389                in_scid_seq,
8390                old_local_addr,
8391                old_peer_addr,
8392                in_scid_pid,
8393                info.to,
8394                info.from
8395            );
8396
8397            // Notify the application.
8398            self.paths.notify_event(PathEvent::ReusedSourceConnectionId(
8399                in_scid_seq,
8400                (old_local_addr, old_peer_addr),
8401                (info.to, info.from),
8402            ));
8403        }
8404
8405        // This is a new path using an unassigned CID; create it!
8406        let mut path = path::Path::new(
8407            info.to,
8408            info.from,
8409            &self.recovery_config,
8410            self.path_challenge_recv_max_queue_len,
8411            false,
8412            None,
8413        );
8414
8415        path.max_send_bytes = buf_len * self.max_amplification_factor;
8416        path.active_scid_seq = Some(in_scid_seq);
8417
8418        // Automatically probes the new path.
8419        path.request_validation();
8420
8421        let pid = self.paths.insert_path(path, self.is_server)?;
8422
8423        // Do not record path reuse.
8424        if in_scid_pid.is_none() {
8425            ids.link_scid_to_path_id(in_scid_seq, pid)?;
8426        }
8427
8428        Ok(pid)
8429    }
8430
8431    /// Selects the path on which the next packet must be sent.
8432    fn get_send_path_id(
8433        &self, from: Option<SocketAddr>, to: Option<SocketAddr>,
8434    ) -> Result<usize> {
8435        // A probing packet must be sent, but only if the connection is fully
8436        // established.
8437        if self.is_established() {
8438            let mut probing = self
8439                .paths
8440                .iter()
8441                .filter(|(_, p)| from.is_none() || Some(p.local_addr()) == from)
8442                .filter(|(_, p)| to.is_none() || Some(p.peer_addr()) == to)
8443                .filter(|(_, p)| p.active_dcid_seq.is_some())
8444                .filter(|(_, p)| p.probing_required())
8445                .map(|(pid, _)| pid);
8446
8447            if let Some(pid) = probing.next() {
8448                return Ok(pid);
8449            }
8450        }
8451
8452        if let Some((pid, p)) = self.paths.get_active_with_pid() {
8453            if from.is_some() && Some(p.local_addr()) != from {
8454                return Err(Error::Done);
8455            }
8456
8457            if to.is_some() && Some(p.peer_addr()) != to {
8458                return Err(Error::Done);
8459            }
8460
8461            return Ok(pid);
8462        };
8463
8464        Err(Error::InvalidState)
8465    }
8466
8467    /// Sets the path with identifier 'path_id' to be active.
8468    fn set_active_path(&mut self, path_id: usize, now: Instant) -> Result<()> {
8469        if let Ok(old_active_path) = self.paths.get_active_mut() {
8470            for &e in packet::Epoch::epochs(
8471                packet::Epoch::Initial..=packet::Epoch::Application,
8472            ) {
8473                let (lost_packets, lost_bytes) = old_active_path
8474                    .recovery
8475                    .on_path_change(e, now, &self.trace_id);
8476
8477                self.lost_count += lost_packets;
8478                self.lost_bytes += lost_bytes as u64;
8479            }
8480        }
8481
8482        self.paths.set_active_path(path_id)
8483    }
8484
8485    /// Handles potential connection migration.
8486    fn on_peer_migrated(
8487        &mut self, new_pid: usize, disable_dcid_reuse: bool, now: Instant,
8488    ) -> Result<()> {
8489        let active_path_id = self.paths.get_active_path_id()?;
8490
8491        if active_path_id == new_pid {
8492            return Ok(());
8493        }
8494
8495        self.set_active_path(new_pid, now)?;
8496
8497        let no_spare_dcid =
8498            self.paths.get_mut(new_pid)?.active_dcid_seq.is_none();
8499
8500        if no_spare_dcid && !disable_dcid_reuse {
8501            self.paths.get_mut(new_pid)?.active_dcid_seq =
8502                self.paths.get_mut(active_path_id)?.active_dcid_seq;
8503        }
8504
8505        Ok(())
8506    }
8507
8508    /// Creates a new client-side path.
8509    fn create_path_on_client(
8510        &mut self, local_addr: SocketAddr, peer_addr: SocketAddr,
8511    ) -> Result<usize> {
8512        if self.is_server {
8513            return Err(Error::InvalidState);
8514        }
8515
8516        // If we use zero-length SCID and go over our local active CID limit,
8517        // the `insert_path()` call will raise an error.
8518        if !self.ids.zero_length_scid() && self.ids.available_scids() == 0 {
8519            return Err(Error::OutOfIdentifiers);
8520        }
8521
8522        // Do we have a spare DCID? If we are using zero-length DCID, just use
8523        // the default having sequence 0 (note that if we exceed our local CID
8524        // limit, the `insert_path()` call will raise an error.
8525        let dcid_seq = if self.ids.zero_length_dcid() {
8526            0
8527        } else {
8528            self.ids
8529                .lowest_available_dcid_seq()
8530                .ok_or(Error::OutOfIdentifiers)?
8531        };
8532
8533        let mut path = path::Path::new(
8534            local_addr,
8535            peer_addr,
8536            &self.recovery_config,
8537            self.path_challenge_recv_max_queue_len,
8538            false,
8539            None,
8540        );
8541        path.active_dcid_seq = Some(dcid_seq);
8542
8543        let pid = self
8544            .paths
8545            .insert_path(path, false)
8546            .map_err(|_| Error::OutOfIdentifiers)?;
8547        self.ids.link_dcid_to_path_id(dcid_seq, pid)?;
8548
8549        Ok(pid)
8550    }
8551
8552    // Marks the connection as closed and does any related tidyup.
8553    fn mark_closed(&mut self) {
8554        #[cfg(feature = "qlog")]
8555        {
8556            let cc = match (self.is_established(), self.timed_out, &self.peer_error, &self.local_error) {
8557                (false, _, _, _) => qlog::events::connectivity::ConnectionClosed {
8558                    owner: Some(TransportOwner::Local),
8559                    connection_code: None,
8560                    application_code: None,
8561                    internal_code: None,
8562                    reason: Some("Failed to establish connection".to_string()),
8563                    trigger: Some(qlog::events::connectivity::ConnectionClosedTrigger::HandshakeTimeout)
8564                },
8565
8566                (true, true, _, _) => qlog::events::connectivity::ConnectionClosed {
8567                    owner: Some(TransportOwner::Local),
8568                    connection_code: None,
8569                    application_code: None,
8570                    internal_code: None,
8571                    reason: Some("Idle timeout".to_string()),
8572                    trigger: Some(qlog::events::connectivity::ConnectionClosedTrigger::IdleTimeout)
8573                },
8574
8575                (true, false, Some(peer_error), None) => {
8576                    let (connection_code, application_code, trigger) = if peer_error.is_app {
8577                        (None, Some(qlog::events::ApplicationErrorCode::Value(peer_error.error_code)), None)
8578                    } else {
8579                        let trigger = if peer_error.error_code == WireErrorCode::NoError as u64 {
8580                            Some(qlog::events::connectivity::ConnectionClosedTrigger::Clean)
8581                        } else {
8582                            Some(qlog::events::connectivity::ConnectionClosedTrigger::Error)
8583                        };
8584
8585                        (Some(qlog::events::ConnectionErrorCode::Value(peer_error.error_code)), None, trigger)
8586                    };
8587
8588                    qlog::events::connectivity::ConnectionClosed {
8589                        owner: Some(TransportOwner::Remote),
8590                        connection_code,
8591                        application_code,
8592                        internal_code: None,
8593                        reason: Some(String::from_utf8_lossy(&peer_error.reason).to_string()),
8594                        trigger,
8595                    }
8596                },
8597
8598                (true, false, None, Some(local_error)) => {
8599                    let (connection_code, application_code, trigger) = if local_error.is_app {
8600                        (None, Some(qlog::events::ApplicationErrorCode::Value(local_error.error_code)), None)
8601                    } else {
8602                        let trigger = if local_error.error_code == WireErrorCode::NoError as u64 {
8603                            Some(qlog::events::connectivity::ConnectionClosedTrigger::Clean)
8604                        } else {
8605                            Some(qlog::events::connectivity::ConnectionClosedTrigger::Error)
8606                        };
8607
8608                        (Some(qlog::events::ConnectionErrorCode::Value(local_error.error_code)), None, trigger)
8609                    };
8610
8611                    qlog::events::connectivity::ConnectionClosed {
8612                        owner: Some(TransportOwner::Local),
8613                        connection_code,
8614                        application_code,
8615                        internal_code: None,
8616                        reason: Some(String::from_utf8_lossy(&local_error.reason).to_string()),
8617                        trigger,
8618                    }
8619                },
8620
8621                _ => qlog::events::connectivity::ConnectionClosed {
8622                    owner: None,
8623                    connection_code: None,
8624                    application_code: None,
8625                    internal_code: None,
8626                    reason: None,
8627                    trigger: None,
8628                },
8629            };
8630
8631            qlog_with_type!(QLOG_CONNECTION_CLOSED, self.qlog, q, {
8632                let ev_data = EventData::ConnectionClosed(cc);
8633
8634                q.add_event_data_now(ev_data).ok();
8635            });
8636            self.qlog.streamer = None;
8637        }
8638        self.closed = true;
8639    }
8640}
8641
8642#[cfg(feature = "boringssl-boring-crate")]
8643impl<F: BufFactory> AsMut<boring::ssl::SslRef> for Connection<F> {
8644    fn as_mut(&mut self) -> &mut boring::ssl::SslRef {
8645        self.handshake.ssl_mut()
8646    }
8647}
8648
8649/// Maps an `Error` to `Error::Done`, or itself.
8650///
8651/// When a received packet that hasn't yet been authenticated triggers a failure
8652/// it should, in most cases, be ignored, instead of raising a connection error,
8653/// to avoid potential man-in-the-middle and man-on-the-side attacks.
8654///
8655/// However, if no other packet was previously received, the connection should
8656/// indeed be closed as the received packet might just be network background
8657/// noise, and it shouldn't keep resources occupied indefinitely.
8658///
8659/// This function maps an error to `Error::Done` to ignore a packet failure
8660/// without aborting the connection, except when no other packet was previously
8661/// received, in which case the error itself is returned, but only on the
8662/// server-side as the client will already have armed the idle timer.
8663///
8664/// This must only be used for errors preceding packet authentication. Failures
8665/// happening after a packet has been authenticated should still cause the
8666/// connection to be aborted.
8667fn drop_pkt_on_err(
8668    e: Error, recv_count: usize, is_server: bool, trace_id: &str,
8669) -> Error {
8670    // On the server, if no other packet has been successfully processed, abort
8671    // the connection to avoid keeping the connection open when only junk is
8672    // received.
8673    if is_server && recv_count == 0 {
8674        return e;
8675    }
8676
8677    trace!("{trace_id} dropped invalid packet");
8678
8679    // Ignore other invalid packets that haven't been authenticated to prevent
8680    // man-in-the-middle and man-on-the-side attacks.
8681    Error::Done
8682}
8683
8684struct AddrTupleFmt(SocketAddr, SocketAddr);
8685
8686impl std::fmt::Display for AddrTupleFmt {
8687    fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
8688        let AddrTupleFmt(src, dst) = &self;
8689
8690        if src.ip().is_unspecified() || dst.ip().is_unspecified() {
8691            return Ok(());
8692        }
8693
8694        f.write_fmt(format_args!("src:{src} dst:{dst}"))
8695    }
8696}
8697
8698/// Statistics about the connection.
8699///
8700/// A connection's statistics can be collected using the [`stats()`] method.
8701///
8702/// [`stats()`]: struct.Connection.html#method.stats
8703#[derive(Clone, Default)]
8704pub struct Stats {
8705    /// The number of QUIC packets received.
8706    pub recv: usize,
8707
8708    /// The number of QUIC packets sent.
8709    pub sent: usize,
8710
8711    /// The number of QUIC packets that were lost.
8712    pub lost: usize,
8713
8714    /// The number of QUIC packets that were marked as lost but later acked.
8715    pub spurious_lost: usize,
8716
8717    /// The number of sent QUIC packets with retransmitted data.
8718    pub retrans: usize,
8719
8720    /// The number of sent bytes.
8721    pub sent_bytes: u64,
8722
8723    /// The number of received bytes.
8724    pub recv_bytes: u64,
8725
8726    /// The number of bytes sent acked.
8727    pub acked_bytes: u64,
8728
8729    /// The number of bytes sent lost.
8730    pub lost_bytes: u64,
8731
8732    /// The number of stream bytes retransmitted.
8733    pub stream_retrans_bytes: u64,
8734
8735    /// The number of DATAGRAM frames received.
8736    pub dgram_recv: usize,
8737
8738    /// The number of DATAGRAM frames sent.
8739    pub dgram_sent: usize,
8740
8741    /// The number of known paths for the connection.
8742    pub paths_count: usize,
8743
8744    /// The number of streams reset by local.
8745    pub reset_stream_count_local: u64,
8746
8747    /// The number of streams stopped by local.
8748    pub stopped_stream_count_local: u64,
8749
8750    /// The number of streams reset by remote.
8751    pub reset_stream_count_remote: u64,
8752
8753    /// The number of streams stopped by remote.
8754    pub stopped_stream_count_remote: u64,
8755
8756    /// The number of DATA_BLOCKED frames sent due to hitting the connection
8757    /// flow control limit.
8758    pub data_blocked_sent_count: u64,
8759
8760    /// The number of STREAM_DATA_BLOCKED frames sent due to a stream hitting
8761    /// the stream flow control limit.
8762    pub stream_data_blocked_sent_count: u64,
8763
8764    /// The number of DATA_BLOCKED frames received from the remote.
8765    pub data_blocked_recv_count: u64,
8766
8767    /// The number of STREAM_DATA_BLOCKED frames received from the remote.
8768    pub stream_data_blocked_recv_count: u64,
8769
8770    /// The total number of PATH_CHALLENGE frames that were received.
8771    pub path_challenge_rx_count: u64,
8772
8773    /// Total duration during which this side of the connection was
8774    /// actively sending bytes or waiting for those bytes to be acked.
8775    pub bytes_in_flight_duration: Duration,
8776
8777    /// Health state of the connection's tx_buffered.
8778    pub tx_buffered_state: TxBufferTrackingState,
8779}
8780
8781impl std::fmt::Debug for Stats {
8782    #[inline]
8783    fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
8784        write!(
8785            f,
8786            "recv={} sent={} lost={} retrans={}",
8787            self.recv, self.sent, self.lost, self.retrans,
8788        )?;
8789
8790        write!(
8791            f,
8792            " sent_bytes={} recv_bytes={} lost_bytes={}",
8793            self.sent_bytes, self.recv_bytes, self.lost_bytes,
8794        )?;
8795
8796        Ok(())
8797    }
8798}
8799
8800/// QUIC Unknown Transport Parameter.
8801///
8802/// A QUIC transport parameter that is not specifically recognized
8803/// by this implementation.
8804#[derive(Clone, Debug, PartialEq)]
8805pub struct UnknownTransportParameter<T> {
8806    /// The ID of the unknown transport parameter.
8807    pub id: u64,
8808
8809    /// Original data representing the value of the unknown transport parameter.
8810    pub value: T,
8811}
8812
8813impl<T> UnknownTransportParameter<T> {
8814    /// Checks whether an unknown Transport Parameter's ID is in the reserved
8815    /// space.
8816    ///
8817    /// See Section 18.1 in [RFC9000](https://datatracker.ietf.org/doc/html/rfc9000#name-reserved-transport-paramete).
8818    pub fn is_reserved(&self) -> bool {
8819        let n = (self.id - 27) / 31;
8820        self.id == 31 * n + 27
8821    }
8822}
8823
8824#[cfg(feature = "qlog")]
8825impl From<UnknownTransportParameter<Vec<u8>>>
8826    for qlog::events::quic::UnknownTransportParameter
8827{
8828    fn from(value: UnknownTransportParameter<Vec<u8>>) -> Self {
8829        Self {
8830            id: value.id,
8831            value: qlog::HexSlice::maybe_string(Some(value.value.as_slice()))
8832                .unwrap_or_default(),
8833        }
8834    }
8835}
8836
8837impl From<UnknownTransportParameter<&[u8]>>
8838    for UnknownTransportParameter<Vec<u8>>
8839{
8840    // When an instance of an UnknownTransportParameter is actually
8841    // stored in UnknownTransportParameters, then we make a copy
8842    // of the bytes if the source is an instance of an UnknownTransportParameter
8843    // whose value is not owned.
8844    fn from(value: UnknownTransportParameter<&[u8]>) -> Self {
8845        Self {
8846            id: value.id,
8847            value: value.value.to_vec(),
8848        }
8849    }
8850}
8851
8852/// Track unknown transport parameters, up to a limit.
8853#[derive(Clone, Debug, PartialEq, Default)]
8854pub struct UnknownTransportParameters {
8855    /// The space remaining for storing unknown transport parameters.
8856    pub capacity: usize,
8857    /// The unknown transport parameters.
8858    pub parameters: Vec<UnknownTransportParameter<Vec<u8>>>,
8859}
8860
8861impl UnknownTransportParameters {
8862    /// Pushes an unknown transport parameter into storage if there is space
8863    /// remaining.
8864    pub fn push(&mut self, new: UnknownTransportParameter<&[u8]>) -> Result<()> {
8865        let new_unknown_tp_size = new.value.len() + size_of::<u64>();
8866        if new_unknown_tp_size < self.capacity {
8867            self.capacity -= new_unknown_tp_size;
8868            self.parameters.push(new.into());
8869            Ok(())
8870        } else {
8871            Err(octets::BufferTooShortError.into())
8872        }
8873    }
8874}
8875
8876/// An Iterator over unknown transport parameters.
8877pub struct UnknownTransportParameterIterator<'a> {
8878    index: usize,
8879    parameters: &'a Vec<UnknownTransportParameter<Vec<u8>>>,
8880}
8881
8882impl<'a> IntoIterator for &'a UnknownTransportParameters {
8883    type IntoIter = UnknownTransportParameterIterator<'a>;
8884    type Item = &'a UnknownTransportParameter<Vec<u8>>;
8885
8886    fn into_iter(self) -> Self::IntoIter {
8887        UnknownTransportParameterIterator {
8888            index: 0,
8889            parameters: &self.parameters,
8890        }
8891    }
8892}
8893
8894impl<'a> Iterator for UnknownTransportParameterIterator<'a> {
8895    type Item = &'a UnknownTransportParameter<Vec<u8>>;
8896
8897    fn next(&mut self) -> Option<Self::Item> {
8898        let result = self.parameters.get(self.index);
8899        self.index += 1;
8900        result
8901    }
8902}
8903
8904/// QUIC Transport Parameters
8905#[derive(Clone, Debug, PartialEq)]
8906pub struct TransportParams {
8907    /// Value of Destination CID field from first Initial packet sent by client
8908    pub original_destination_connection_id: Option<ConnectionId<'static>>,
8909    /// The maximum idle timeout.
8910    pub max_idle_timeout: u64,
8911    /// Token used for verifying stateless resets
8912    pub stateless_reset_token: Option<u128>,
8913    /// The maximum UDP payload size.
8914    pub max_udp_payload_size: u64,
8915    /// The initial flow control maximum data for the connection.
8916    pub initial_max_data: u64,
8917    /// The initial flow control maximum data for local bidirectional streams.
8918    pub initial_max_stream_data_bidi_local: u64,
8919    /// The initial flow control maximum data for remote bidirectional streams.
8920    pub initial_max_stream_data_bidi_remote: u64,
8921    /// The initial flow control maximum data for unidirectional streams.
8922    pub initial_max_stream_data_uni: u64,
8923    /// The initial maximum bidirectional streams.
8924    pub initial_max_streams_bidi: u64,
8925    /// The initial maximum unidirectional streams.
8926    pub initial_max_streams_uni: u64,
8927    /// The ACK delay exponent.
8928    pub ack_delay_exponent: u64,
8929    /// The max ACK delay.
8930    pub max_ack_delay: u64,
8931    /// Whether active migration is disabled.
8932    pub disable_active_migration: bool,
8933    /// The active connection ID limit.
8934    pub active_conn_id_limit: u64,
8935    /// The value that the endpoint included in the Source CID field of a Retry
8936    /// Packet.
8937    pub initial_source_connection_id: Option<ConnectionId<'static>>,
8938    /// The value that the server included in the Source CID field of a Retry
8939    /// Packet.
8940    pub retry_source_connection_id: Option<ConnectionId<'static>>,
8941    /// DATAGRAM frame extension parameter, if any.
8942    pub max_datagram_frame_size: Option<u64>,
8943    /// Unknown peer transport parameters and values, if any.
8944    pub unknown_params: Option<UnknownTransportParameters>,
8945    // pub preferred_address: ...,
8946}
8947
8948impl Default for TransportParams {
8949    fn default() -> TransportParams {
8950        TransportParams {
8951            original_destination_connection_id: None,
8952            max_idle_timeout: 0,
8953            stateless_reset_token: None,
8954            max_udp_payload_size: 65527,
8955            initial_max_data: 0,
8956            initial_max_stream_data_bidi_local: 0,
8957            initial_max_stream_data_bidi_remote: 0,
8958            initial_max_stream_data_uni: 0,
8959            initial_max_streams_bidi: 0,
8960            initial_max_streams_uni: 0,
8961            ack_delay_exponent: 3,
8962            max_ack_delay: 25,
8963            disable_active_migration: false,
8964            active_conn_id_limit: 2,
8965            initial_source_connection_id: None,
8966            retry_source_connection_id: None,
8967            max_datagram_frame_size: None,
8968            unknown_params: Default::default(),
8969        }
8970    }
8971}
8972
8973impl TransportParams {
8974    fn decode(
8975        buf: &[u8], is_server: bool, unknown_size: Option<usize>,
8976    ) -> Result<TransportParams> {
8977        let mut params = octets::Octets::with_slice(buf);
8978        let mut seen_params = HashSet::new();
8979
8980        let mut tp = TransportParams::default();
8981
8982        if let Some(unknown_transport_param_tracking_size) = unknown_size {
8983            tp.unknown_params = Some(UnknownTransportParameters {
8984                capacity: unknown_transport_param_tracking_size,
8985                parameters: vec![],
8986            });
8987        }
8988
8989        while params.cap() > 0 {
8990            let id = params.get_varint()?;
8991
8992            if seen_params.contains(&id) {
8993                return Err(Error::InvalidTransportParam);
8994            }
8995            seen_params.insert(id);
8996
8997            let mut val = params.get_bytes_with_varint_length()?;
8998
8999            match id {
9000                0x0000 => {
9001                    if is_server {
9002                        return Err(Error::InvalidTransportParam);
9003                    }
9004
9005                    tp.original_destination_connection_id =
9006                        Some(val.to_vec().into());
9007                },
9008
9009                0x0001 => {
9010                    tp.max_idle_timeout = val.get_varint()?;
9011                },
9012
9013                0x0002 => {
9014                    if is_server {
9015                        return Err(Error::InvalidTransportParam);
9016                    }
9017
9018                    tp.stateless_reset_token = Some(u128::from_be_bytes(
9019                        val.get_bytes(16)?
9020                            .to_vec()
9021                            .try_into()
9022                            .map_err(|_| Error::BufferTooShort)?,
9023                    ));
9024                },
9025
9026                0x0003 => {
9027                    tp.max_udp_payload_size = val.get_varint()?;
9028
9029                    if tp.max_udp_payload_size < 1200 {
9030                        return Err(Error::InvalidTransportParam);
9031                    }
9032                },
9033
9034                0x0004 => {
9035                    tp.initial_max_data = val.get_varint()?;
9036                },
9037
9038                0x0005 => {
9039                    tp.initial_max_stream_data_bidi_local = val.get_varint()?;
9040                },
9041
9042                0x0006 => {
9043                    tp.initial_max_stream_data_bidi_remote = val.get_varint()?;
9044                },
9045
9046                0x0007 => {
9047                    tp.initial_max_stream_data_uni = val.get_varint()?;
9048                },
9049
9050                0x0008 => {
9051                    let max = val.get_varint()?;
9052
9053                    if max > MAX_STREAM_ID {
9054                        return Err(Error::InvalidTransportParam);
9055                    }
9056
9057                    tp.initial_max_streams_bidi = max;
9058                },
9059
9060                0x0009 => {
9061                    let max = val.get_varint()?;
9062
9063                    if max > MAX_STREAM_ID {
9064                        return Err(Error::InvalidTransportParam);
9065                    }
9066
9067                    tp.initial_max_streams_uni = max;
9068                },
9069
9070                0x000a => {
9071                    let ack_delay_exponent = val.get_varint()?;
9072
9073                    if ack_delay_exponent > 20 {
9074                        return Err(Error::InvalidTransportParam);
9075                    }
9076
9077                    tp.ack_delay_exponent = ack_delay_exponent;
9078                },
9079
9080                0x000b => {
9081                    let max_ack_delay = val.get_varint()?;
9082
9083                    if max_ack_delay >= 2_u64.pow(14) {
9084                        return Err(Error::InvalidTransportParam);
9085                    }
9086
9087                    tp.max_ack_delay = max_ack_delay;
9088                },
9089
9090                0x000c => {
9091                    tp.disable_active_migration = true;
9092                },
9093
9094                0x000d => {
9095                    if is_server {
9096                        return Err(Error::InvalidTransportParam);
9097                    }
9098
9099                    // TODO: decode preferred_address
9100                },
9101
9102                0x000e => {
9103                    let limit = val.get_varint()?;
9104
9105                    if limit < 2 {
9106                        return Err(Error::InvalidTransportParam);
9107                    }
9108
9109                    tp.active_conn_id_limit = limit;
9110                },
9111
9112                0x000f => {
9113                    tp.initial_source_connection_id = Some(val.to_vec().into());
9114                },
9115
9116                0x00010 => {
9117                    if is_server {
9118                        return Err(Error::InvalidTransportParam);
9119                    }
9120
9121                    tp.retry_source_connection_id = Some(val.to_vec().into());
9122                },
9123
9124                0x0020 => {
9125                    tp.max_datagram_frame_size = Some(val.get_varint()?);
9126                },
9127
9128                // Track unknown transport parameters specially.
9129                unknown_tp_id => {
9130                    if let Some(unknown_params) = &mut tp.unknown_params {
9131                        // It is _not_ an error not to have space enough to track
9132                        // an unknown parameter.
9133                        let _ = unknown_params.push(UnknownTransportParameter {
9134                            id: unknown_tp_id,
9135                            value: val.buf(),
9136                        });
9137                    }
9138                },
9139            }
9140        }
9141
9142        Ok(tp)
9143    }
9144
9145    fn encode_param(
9146        b: &mut octets::OctetsMut, ty: u64, len: usize,
9147    ) -> Result<()> {
9148        b.put_varint(ty)?;
9149        b.put_varint(len as u64)?;
9150
9151        Ok(())
9152    }
9153
9154    fn encode<'a>(
9155        tp: &TransportParams, is_server: bool, out: &'a mut [u8],
9156    ) -> Result<&'a mut [u8]> {
9157        let mut b = octets::OctetsMut::with_slice(out);
9158
9159        if is_server {
9160            if let Some(ref odcid) = tp.original_destination_connection_id {
9161                TransportParams::encode_param(&mut b, 0x0000, odcid.len())?;
9162                b.put_bytes(odcid)?;
9163            }
9164        };
9165
9166        if tp.max_idle_timeout != 0 {
9167            assert!(tp.max_idle_timeout <= octets::MAX_VAR_INT);
9168            TransportParams::encode_param(
9169                &mut b,
9170                0x0001,
9171                octets::varint_len(tp.max_idle_timeout),
9172            )?;
9173            b.put_varint(tp.max_idle_timeout)?;
9174        }
9175
9176        if is_server {
9177            if let Some(ref token) = tp.stateless_reset_token {
9178                TransportParams::encode_param(&mut b, 0x0002, 16)?;
9179                b.put_bytes(&token.to_be_bytes())?;
9180            }
9181        }
9182
9183        if tp.max_udp_payload_size != 0 {
9184            assert!(tp.max_udp_payload_size <= octets::MAX_VAR_INT);
9185            TransportParams::encode_param(
9186                &mut b,
9187                0x0003,
9188                octets::varint_len(tp.max_udp_payload_size),
9189            )?;
9190            b.put_varint(tp.max_udp_payload_size)?;
9191        }
9192
9193        if tp.initial_max_data != 0 {
9194            assert!(tp.initial_max_data <= octets::MAX_VAR_INT);
9195            TransportParams::encode_param(
9196                &mut b,
9197                0x0004,
9198                octets::varint_len(tp.initial_max_data),
9199            )?;
9200            b.put_varint(tp.initial_max_data)?;
9201        }
9202
9203        if tp.initial_max_stream_data_bidi_local != 0 {
9204            assert!(tp.initial_max_stream_data_bidi_local <= octets::MAX_VAR_INT);
9205            TransportParams::encode_param(
9206                &mut b,
9207                0x0005,
9208                octets::varint_len(tp.initial_max_stream_data_bidi_local),
9209            )?;
9210            b.put_varint(tp.initial_max_stream_data_bidi_local)?;
9211        }
9212
9213        if tp.initial_max_stream_data_bidi_remote != 0 {
9214            assert!(
9215                tp.initial_max_stream_data_bidi_remote <= octets::MAX_VAR_INT
9216            );
9217            TransportParams::encode_param(
9218                &mut b,
9219                0x0006,
9220                octets::varint_len(tp.initial_max_stream_data_bidi_remote),
9221            )?;
9222            b.put_varint(tp.initial_max_stream_data_bidi_remote)?;
9223        }
9224
9225        if tp.initial_max_stream_data_uni != 0 {
9226            assert!(tp.initial_max_stream_data_uni <= octets::MAX_VAR_INT);
9227            TransportParams::encode_param(
9228                &mut b,
9229                0x0007,
9230                octets::varint_len(tp.initial_max_stream_data_uni),
9231            )?;
9232            b.put_varint(tp.initial_max_stream_data_uni)?;
9233        }
9234
9235        if tp.initial_max_streams_bidi != 0 {
9236            assert!(tp.initial_max_streams_bidi <= octets::MAX_VAR_INT);
9237            TransportParams::encode_param(
9238                &mut b,
9239                0x0008,
9240                octets::varint_len(tp.initial_max_streams_bidi),
9241            )?;
9242            b.put_varint(tp.initial_max_streams_bidi)?;
9243        }
9244
9245        if tp.initial_max_streams_uni != 0 {
9246            assert!(tp.initial_max_streams_uni <= octets::MAX_VAR_INT);
9247            TransportParams::encode_param(
9248                &mut b,
9249                0x0009,
9250                octets::varint_len(tp.initial_max_streams_uni),
9251            )?;
9252            b.put_varint(tp.initial_max_streams_uni)?;
9253        }
9254
9255        if tp.ack_delay_exponent != 0 {
9256            assert!(tp.ack_delay_exponent <= octets::MAX_VAR_INT);
9257            TransportParams::encode_param(
9258                &mut b,
9259                0x000a,
9260                octets::varint_len(tp.ack_delay_exponent),
9261            )?;
9262            b.put_varint(tp.ack_delay_exponent)?;
9263        }
9264
9265        if tp.max_ack_delay != 0 {
9266            assert!(tp.max_ack_delay <= octets::MAX_VAR_INT);
9267            TransportParams::encode_param(
9268                &mut b,
9269                0x000b,
9270                octets::varint_len(tp.max_ack_delay),
9271            )?;
9272            b.put_varint(tp.max_ack_delay)?;
9273        }
9274
9275        if tp.disable_active_migration {
9276            TransportParams::encode_param(&mut b, 0x000c, 0)?;
9277        }
9278
9279        // TODO: encode preferred_address
9280
9281        if tp.active_conn_id_limit != 2 {
9282            assert!(tp.active_conn_id_limit <= octets::MAX_VAR_INT);
9283            TransportParams::encode_param(
9284                &mut b,
9285                0x000e,
9286                octets::varint_len(tp.active_conn_id_limit),
9287            )?;
9288            b.put_varint(tp.active_conn_id_limit)?;
9289        }
9290
9291        if let Some(scid) = &tp.initial_source_connection_id {
9292            TransportParams::encode_param(&mut b, 0x000f, scid.len())?;
9293            b.put_bytes(scid)?;
9294        }
9295
9296        if is_server {
9297            if let Some(scid) = &tp.retry_source_connection_id {
9298                TransportParams::encode_param(&mut b, 0x0010, scid.len())?;
9299                b.put_bytes(scid)?;
9300            }
9301        }
9302
9303        if let Some(max_datagram_frame_size) = tp.max_datagram_frame_size {
9304            assert!(max_datagram_frame_size <= octets::MAX_VAR_INT);
9305            TransportParams::encode_param(
9306                &mut b,
9307                0x0020,
9308                octets::varint_len(max_datagram_frame_size),
9309            )?;
9310            b.put_varint(max_datagram_frame_size)?;
9311        }
9312
9313        let out_len = b.off();
9314
9315        Ok(&mut out[..out_len])
9316    }
9317
9318    /// Creates a qlog event for connection transport parameters and TLS fields
9319    #[cfg(feature = "qlog")]
9320    pub fn to_qlog(
9321        &self, owner: TransportOwner, cipher: Option<crypto::Algorithm>,
9322    ) -> EventData {
9323        let original_destination_connection_id = qlog::HexSlice::maybe_string(
9324            self.original_destination_connection_id.as_ref(),
9325        );
9326
9327        let stateless_reset_token = qlog::HexSlice::maybe_string(
9328            self.stateless_reset_token.map(|s| s.to_be_bytes()).as_ref(),
9329        );
9330
9331        let tls_cipher: Option<String> = cipher.map(|f| format!("{f:?}"));
9332
9333        EventData::TransportParametersSet(
9334            qlog::events::quic::TransportParametersSet {
9335                owner: Some(owner),
9336                tls_cipher,
9337                original_destination_connection_id,
9338                stateless_reset_token,
9339                disable_active_migration: Some(self.disable_active_migration),
9340                max_idle_timeout: Some(self.max_idle_timeout),
9341                max_udp_payload_size: Some(self.max_udp_payload_size as u32),
9342                ack_delay_exponent: Some(self.ack_delay_exponent as u16),
9343                max_ack_delay: Some(self.max_ack_delay as u16),
9344                active_connection_id_limit: Some(
9345                    self.active_conn_id_limit as u32,
9346                ),
9347
9348                initial_max_data: Some(self.initial_max_data),
9349                initial_max_stream_data_bidi_local: Some(
9350                    self.initial_max_stream_data_bidi_local,
9351                ),
9352                initial_max_stream_data_bidi_remote: Some(
9353                    self.initial_max_stream_data_bidi_remote,
9354                ),
9355                initial_max_stream_data_uni: Some(
9356                    self.initial_max_stream_data_uni,
9357                ),
9358                initial_max_streams_bidi: Some(self.initial_max_streams_bidi),
9359                initial_max_streams_uni: Some(self.initial_max_streams_uni),
9360
9361                unknown_parameters: self
9362                    .unknown_params
9363                    .as_ref()
9364                    .map(|unknown_params| {
9365                        unknown_params
9366                            .into_iter()
9367                            .cloned()
9368                            .map(
9369                                Into::<
9370                                    qlog::events::quic::UnknownTransportParameter,
9371                                >::into,
9372                            )
9373                            .collect()
9374                    })
9375                    .unwrap_or_default(),
9376
9377                ..Default::default()
9378            },
9379        )
9380    }
9381}
9382
9383#[doc(hidden)]
9384pub mod test_utils;
9385
9386#[cfg(test)]
9387mod tests;
9388
9389pub use crate::packet::ConnectionId;
9390pub use crate::packet::Header;
9391pub use crate::packet::Type;
9392
9393pub use crate::path::PathEvent;
9394pub use crate::path::PathStats;
9395pub use crate::path::SocketAddrIter;
9396
9397pub use crate::recovery::BbrBwLoReductionStrategy;
9398pub use crate::recovery::BbrParams;
9399pub use crate::recovery::CongestionControlAlgorithm;
9400pub use crate::recovery::StartupExit;
9401pub use crate::recovery::StartupExitReason;
9402
9403pub use crate::stream::StreamIter;
9404
9405pub use crate::range_buf::BufFactory;
9406pub use crate::range_buf::BufSplit;
9407
9408pub use crate::error::ConnectionError;
9409pub use crate::error::Error;
9410pub use crate::error::Result;
9411pub use crate::error::WireErrorCode;
9412
9413mod cid;
9414mod crypto;
9415mod dgram;
9416mod error;
9417#[cfg(feature = "ffi")]
9418mod ffi;
9419mod flowcontrol;
9420mod frame;
9421pub mod h3;
9422mod minmax;
9423mod packet;
9424mod path;
9425mod pmtud;
9426mod rand;
9427mod range_buf;
9428mod ranges;
9429mod recovery;
9430mod stream;
9431mod tls;