1use std::{fmt, net::SocketAddr};
2
3use bytes::{Buf, BufMut, BytesMut};
4
5use crate::FourTuple;
6use crate::PathId;
7use crate::{Duration, Instant, MAX_CID_SIZE, ResetToken, coding::BufExt, packet::PartialDecode};
8
9#[derive(Debug)]
11pub struct ConnectionEvent(pub(crate) ConnectionEventInner);
12
13#[derive(Debug)]
14pub(crate) enum ConnectionEventInner {
15 Datagram(DatagramConnectionEvent),
17 NewIdentifiers(Vec<IssuedCid>, Instant, usize, Option<Duration>),
19}
20
21#[derive(Debug)]
23pub(crate) struct DatagramConnectionEvent {
24 pub(crate) now: Instant,
25 pub(crate) network_path: FourTuple,
26 pub(crate) path_id: PathId,
27 pub(crate) ecn: Option<EcnCodepoint>,
28 pub(crate) first_decode: PartialDecode,
29 pub(crate) remaining: Option<BytesMut>,
30}
31
32#[derive(Debug)]
34pub struct EndpointEvent(pub(crate) EndpointEventInner);
35
36impl EndpointEvent {
37 pub fn drained() -> Self {
42 Self(EndpointEventInner::Drained)
43 }
44
45 pub fn is_drained(&self) -> bool {
49 self.0 == EndpointEventInner::Drained
50 }
51
52 pub fn is_draining(&self) -> bool {
54 self.0 == EndpointEventInner::Draining
55 }
56}
57
58#[derive(Clone, Debug, Eq, PartialEq)]
59pub(crate) enum EndpointEventInner {
60 Draining,
62 Drained,
64 ResetToken(PathId, SocketAddr, ResetToken),
70 RetireResetToken(PathId),
75 NeedIdentifiers(PathId, Instant, u64),
84 RetireConnectionId(Instant, PathId, u64, bool),
89}
90
91#[derive(Clone, Copy, Eq, PartialEq, Ord, PartialOrd, Hash)]
95#[cfg_attr(test, derive(test_strategy::Arbitrary))]
96pub struct ConnectionId {
97 #[cfg_attr(test, strategy(1u8..=MAX_CID_SIZE as u8))]
99 len: u8,
100 bytes: [u8; MAX_CID_SIZE],
102}
103
104impl ConnectionId {
105 pub fn new(bytes: &[u8]) -> Self {
107 debug_assert!(bytes.len() <= MAX_CID_SIZE);
108 let mut res = Self {
109 len: bytes.len() as u8,
110 bytes: [0; MAX_CID_SIZE],
111 };
112 res.bytes[..bytes.len()].copy_from_slice(bytes);
113 res
114 }
115
116 pub fn from_buf(buf: &mut (impl Buf + ?Sized), len: usize) -> Self {
120 debug_assert!(len <= MAX_CID_SIZE);
121 let mut res = Self {
122 len: len as u8,
123 bytes: [0; MAX_CID_SIZE],
124 };
125 buf.copy_to_slice(&mut res[..len]);
126 res
127 }
128
129 pub(crate) fn len(&self) -> usize {
130 self.len as usize
131 }
132
133 pub(crate) fn decode_long(buf: &mut impl Buf) -> Option<Self> {
135 let len = buf.get::<u8>().ok()? as usize;
136 match len > MAX_CID_SIZE || buf.remaining() < len {
137 false => Some(Self::from_buf(buf, len)),
138 true => None,
139 }
140 }
141
142 pub(crate) fn encode_long(&self, buf: &mut impl BufMut) {
144 buf.put_u8(self.len() as u8);
145 buf.put_slice(self);
146 }
147}
148
149impl ::std::ops::Deref for ConnectionId {
150 type Target = [u8];
151 fn deref(&self) -> &[u8] {
152 &self.bytes[0..self.len as usize]
153 }
154}
155
156impl ::std::ops::DerefMut for ConnectionId {
157 fn deref_mut(&mut self) -> &mut [u8] {
158 &mut self.bytes[0..self.len as usize]
159 }
160}
161
162impl fmt::Debug for ConnectionId {
163 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
164 self.bytes[0..self.len as usize].fmt(f)
165 }
166}
167
168impl fmt::Display for ConnectionId {
169 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
170 for byte in self.iter() {
171 write!(f, "{byte:02x}")?;
172 }
173 Ok(())
174 }
175}
176
177#[repr(u8)]
179#[derive(Debug, Copy, Clone, Eq, PartialEq)]
180pub enum EcnCodepoint {
181 Ect0 = 0b10,
183 Ect1 = 0b01,
185 Ce = 0b11,
187}
188
189impl EcnCodepoint {
190 pub fn from_bits(x: u8) -> Option<Self> {
192 use EcnCodepoint::*;
193 Some(match x & 0b11 {
194 0b10 => Ect0,
195 0b01 => Ect1,
196 0b11 => Ce,
197 _ => {
198 return None;
199 }
200 })
201 }
202
203 pub fn is_ce(self) -> bool {
205 matches!(self, Self::Ce)
206 }
207}
208
209#[derive(Debug, Copy, Clone)]
210pub(crate) struct IssuedCid {
211 pub(crate) path_id: PathId,
212 pub(crate) sequence: u64,
213 pub(crate) id: ConnectionId,
214 pub(crate) reset_token: ResetToken,
215}