Skip to main content

rustls/
conn.rs

1use alloc::boxed::Box;
2use core::fmt::Debug;
3use core::mem;
4use core::ops::{Deref, DerefMut, Range};
5#[cfg(feature = "std")]
6use std::io;
7
8use kernel::KernelConnection;
9
10use crate::common_state::{CommonState, Context, DEFAULT_BUFFER_LIMIT, IoState, State};
11use crate::enums::{AlertDescription, ContentType, ProtocolVersion};
12use crate::error::{Error, PeerMisbehaved};
13use crate::log::trace;
14use crate::msgs::deframer::DeframerIter;
15use crate::msgs::deframer::buffers::{BufferProgress, DeframerVecBuffer, Delocator, Locator};
16use crate::msgs::deframer::handshake::HandshakeDeframer;
17use crate::msgs::handshake::Random;
18use crate::msgs::message::{InboundPlainMessage, Message, MessagePayload};
19use crate::record_layer::Decrypted;
20use crate::suites::ExtractedSecrets;
21use crate::vecbuf::ChunkVecBuffer;
22
23// pub so that it can be re-exported from the crate root
24pub mod kernel;
25pub(crate) mod unbuffered;
26
27#[cfg(feature = "std")]
28mod connection {
29    use alloc::vec::Vec;
30    use core::fmt::Debug;
31    use core::ops::{Deref, DerefMut};
32    use std::io::{self, BufRead, Read};
33
34    use crate::ConnectionCommon;
35    use crate::common_state::{CommonState, IoState};
36    use crate::error::Error;
37    use crate::msgs::message::OutboundChunks;
38    use crate::suites::ExtractedSecrets;
39    use crate::vecbuf::ChunkVecBuffer;
40
41    /// A client or server connection.
42    #[derive(Debug)]
43    pub enum Connection {
44        /// A client connection
45        Client(crate::client::ClientConnection),
46        /// A server connection
47        Server(crate::server::ServerConnection),
48    }
49
50    impl Connection {
51        /// Read TLS content from `rd`.
52        ///
53        /// See [`ConnectionCommon::read_tls()`] for more information.
54        pub fn read_tls(&mut self, rd: &mut dyn Read) -> Result<usize, io::Error> {
55            match self {
56                Self::Client(conn) => conn.read_tls(rd),
57                Self::Server(conn) => conn.read_tls(rd),
58            }
59        }
60
61        /// Writes TLS messages to `wr`.
62        ///
63        /// See [`ConnectionCommon::write_tls()`] for more information.
64        pub fn write_tls(&mut self, wr: &mut dyn io::Write) -> Result<usize, io::Error> {
65            self.sendable_tls.write_to(wr)
66        }
67
68        /// Returns an object that allows reading plaintext.
69        pub fn reader(&mut self) -> Reader<'_> {
70            match self {
71                Self::Client(conn) => conn.reader(),
72                Self::Server(conn) => conn.reader(),
73            }
74        }
75
76        /// Returns an object that allows writing plaintext.
77        pub fn writer(&mut self) -> Writer<'_> {
78            match self {
79                Self::Client(conn) => Writer::new(&mut **conn),
80                Self::Server(conn) => Writer::new(&mut **conn),
81            }
82        }
83
84        /// Processes any new packets read by a previous call to [`Connection::read_tls`].
85        ///
86        /// See [`ConnectionCommon::process_new_packets()`] for more information.
87        pub fn process_new_packets(&mut self) -> Result<IoState, Error> {
88            match self {
89                Self::Client(conn) => conn.process_new_packets(),
90                Self::Server(conn) => conn.process_new_packets(),
91            }
92        }
93
94        /// Derives key material from the agreed connection secrets.
95        ///
96        /// See [`ConnectionCommon::export_keying_material()`] for more information.
97        pub fn export_keying_material<T: AsMut<[u8]>>(
98            &self,
99            output: T,
100            label: &[u8],
101            context: Option<&[u8]>,
102        ) -> Result<T, Error> {
103            match self {
104                Self::Client(conn) => conn.export_keying_material(output, label, context),
105                Self::Server(conn) => conn.export_keying_material(output, label, context),
106            }
107        }
108
109        /// This function uses `io` to complete any outstanding IO for this connection.
110        ///
111        /// See [`ConnectionCommon::complete_io()`] for more information.
112        pub fn complete_io<T>(&mut self, io: &mut T) -> Result<(usize, usize), io::Error>
113        where
114            Self: Sized,
115            T: Read + io::Write,
116        {
117            match self {
118                Self::Client(conn) => conn.complete_io(io),
119                Self::Server(conn) => conn.complete_io(io),
120            }
121        }
122
123        /// Extract secrets, so they can be used when configuring kTLS, for example.
124        /// Should be used with care as it exposes secret key material.
125        pub fn dangerous_extract_secrets(self) -> Result<ExtractedSecrets, Error> {
126            match self {
127                Self::Client(client) => client.dangerous_extract_secrets(),
128                Self::Server(server) => server.dangerous_extract_secrets(),
129            }
130        }
131
132        /// Sets a limit on the internal buffers
133        ///
134        /// See [`ConnectionCommon::set_buffer_limit()`] for more information.
135        pub fn set_buffer_limit(&mut self, limit: Option<usize>) {
136            match self {
137                Self::Client(client) => client.set_buffer_limit(limit),
138                Self::Server(server) => server.set_buffer_limit(limit),
139            }
140        }
141
142        /// Sends a TLS1.3 `key_update` message to refresh a connection's keys
143        ///
144        /// See [`ConnectionCommon::refresh_traffic_keys()`] for more information.
145        pub fn refresh_traffic_keys(&mut self) -> Result<(), Error> {
146            match self {
147                Self::Client(client) => client.refresh_traffic_keys(),
148                Self::Server(server) => server.refresh_traffic_keys(),
149            }
150        }
151    }
152
153    impl Deref for Connection {
154        type Target = CommonState;
155
156        fn deref(&self) -> &Self::Target {
157            match self {
158                Self::Client(conn) => &conn.core.common_state,
159                Self::Server(conn) => &conn.core.common_state,
160            }
161        }
162    }
163
164    impl DerefMut for Connection {
165        fn deref_mut(&mut self) -> &mut Self::Target {
166            match self {
167                Self::Client(conn) => &mut conn.core.common_state,
168                Self::Server(conn) => &mut conn.core.common_state,
169            }
170        }
171    }
172
173    /// A structure that implements [`std::io::Read`] for reading plaintext.
174    pub struct Reader<'a> {
175        pub(super) received_plaintext: &'a mut ChunkVecBuffer,
176        pub(super) has_received_close_notify: bool,
177        pub(super) has_seen_eof: bool,
178    }
179
180    impl<'a> Reader<'a> {
181        /// Check the connection's state if no bytes are available for reading.
182        fn check_no_bytes_state(&self) -> io::Result<()> {
183            match (self.has_received_close_notify, self.has_seen_eof) {
184                // cleanly closed; don't care about TCP EOF: express this as Ok(0)
185                (true, _) => Ok(()),
186                // unclean closure
187                (false, true) => Err(io::Error::new(
188                    io::ErrorKind::UnexpectedEof,
189                    UNEXPECTED_EOF_MESSAGE,
190                )),
191                // connection still going, but needs more data: signal `WouldBlock` so that
192                // the caller knows this
193                (false, false) => Err(io::ErrorKind::WouldBlock.into()),
194            }
195        }
196
197        /// Obtain a chunk of plaintext data received from the peer over this TLS connection.
198        ///
199        /// This method consumes `self` so that it can return a slice whose lifetime is bounded by
200        /// the [`ConnectionCommon`] that created this `Reader`.
201        pub fn into_first_chunk(self) -> io::Result<&'a [u8]> {
202            match self.received_plaintext.chunk() {
203                Some(chunk) => Ok(chunk),
204                None => {
205                    self.check_no_bytes_state()?;
206                    Ok(&[])
207                }
208            }
209        }
210    }
211
212    impl Read for Reader<'_> {
213        /// Obtain plaintext data received from the peer over this TLS connection.
214        ///
215        /// If the peer closes the TLS session cleanly, this returns `Ok(0)`  once all
216        /// the pending data has been read. No further data can be received on that
217        /// connection, so the underlying TCP connection should be half-closed too.
218        ///
219        /// If the peer closes the TLS session uncleanly (a TCP EOF without sending a
220        /// `close_notify` alert) this function returns a `std::io::Error` of type
221        /// `ErrorKind::UnexpectedEof` once any pending data has been read.
222        ///
223        /// Note that support for `close_notify` varies in peer TLS libraries: many do not
224        /// support it and uncleanly close the TCP connection (this might be
225        /// vulnerable to truncation attacks depending on the application protocol).
226        /// This means applications using rustls must both handle EOF
227        /// from this function, *and* unexpected EOF of the underlying TCP connection.
228        ///
229        /// If there are no bytes to read, this returns `Err(ErrorKind::WouldBlock.into())`.
230        ///
231        /// You may learn the number of bytes available at any time by inspecting
232        /// the return of [`Connection::process_new_packets`].
233        fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
234            let len = self.received_plaintext.read(buf)?;
235            if len > 0 || buf.is_empty() {
236                return Ok(len);
237            }
238
239            self.check_no_bytes_state()
240                .map(|()| len)
241        }
242
243        /// Obtain plaintext data received from the peer over this TLS connection.
244        ///
245        /// If the peer closes the TLS session, this returns `Ok(())` without filling
246        /// any more of the buffer once all the pending data has been read. No further
247        /// data can be received on that connection, so the underlying TCP connection
248        /// should be half-closed too.
249        ///
250        /// If the peer closes the TLS session uncleanly (a TCP EOF without sending a
251        /// `close_notify` alert) this function returns a `std::io::Error` of type
252        /// `ErrorKind::UnexpectedEof` once any pending data has been read.
253        ///
254        /// Note that support for `close_notify` varies in peer TLS libraries: many do not
255        /// support it and uncleanly close the TCP connection (this might be
256        /// vulnerable to truncation attacks depending on the application protocol).
257        /// This means applications using rustls must both handle EOF
258        /// from this function, *and* unexpected EOF of the underlying TCP connection.
259        ///
260        /// If there are no bytes to read, this returns `Err(ErrorKind::WouldBlock.into())`.
261        ///
262        /// You may learn the number of bytes available at any time by inspecting
263        /// the return of [`Connection::process_new_packets`].
264        #[cfg(read_buf)]
265        fn read_buf(&mut self, mut cursor: core::io::BorrowedCursor<'_, u8>) -> io::Result<()> {
266            let before = cursor.written();
267            self.received_plaintext
268                .read_buf(cursor.reborrow())?;
269            let len = cursor.written() - before;
270            if len > 0 || cursor.capacity() == 0 {
271                return Ok(());
272            }
273
274            self.check_no_bytes_state()
275        }
276    }
277
278    impl BufRead for Reader<'_> {
279        /// Obtain a chunk of plaintext data received from the peer over this TLS connection.
280        /// This reads the same data as [`Reader::read()`], but returns a reference instead of
281        /// copying the data.
282        ///
283        /// The caller should call [`Reader::consume()`] afterward to advance the buffer.
284        ///
285        /// See [`Reader::into_first_chunk()`] for a version of this function that returns a
286        /// buffer with a longer lifetime.
287        fn fill_buf(&mut self) -> io::Result<&[u8]> {
288            Reader {
289                // reborrow
290                received_plaintext: self.received_plaintext,
291                ..*self
292            }
293            .into_first_chunk()
294        }
295
296        fn consume(&mut self, amt: usize) {
297            self.received_plaintext
298                .consume_first_chunk(amt)
299        }
300    }
301
302    const UNEXPECTED_EOF_MESSAGE: &str = "peer closed connection without sending TLS close_notify: \
303https://docs.rs/rustls/latest/rustls/manual/_03_howto/index.html#unexpected-eof";
304
305    /// A structure that implements [`std::io::Write`] for writing plaintext.
306    pub struct Writer<'a> {
307        sink: &'a mut dyn PlaintextSink,
308    }
309
310    impl<'a> Writer<'a> {
311        /// Create a new Writer.
312        ///
313        /// This is not an external interface.  Get one of these objects
314        /// from [`Connection::writer`].
315        pub(crate) fn new(sink: &'a mut dyn PlaintextSink) -> Self {
316            Writer { sink }
317        }
318    }
319
320    impl io::Write for Writer<'_> {
321        /// Send the plaintext `buf` to the peer, encrypting
322        /// and authenticating it.  Once this function succeeds
323        /// you should call [`Connection::write_tls`] which will output the
324        /// corresponding TLS records.
325        ///
326        /// This function buffers plaintext sent before the
327        /// TLS handshake completes, and sends it as soon
328        /// as it can.  See [`ConnectionCommon::set_buffer_limit`] to control
329        /// the size of this buffer.
330        ///
331        /// If the connection previously encountered a fatal error (for example, while
332        /// processing received data in [`Connection::process_new_packets`]), this returns
333        /// that error, even if `buf` is empty.
334        fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
335            self.sink.write(buf)
336        }
337
338        fn write_vectored(&mut self, bufs: &[io::IoSlice<'_>]) -> io::Result<usize> {
339            self.sink.write_vectored(bufs)
340        }
341
342        /// This does not do any I/O, but returns the fatal error the connection previously
343        /// encountered, if any.
344        fn flush(&mut self) -> io::Result<()> {
345            self.sink.flush()
346        }
347    }
348
349    /// Internal trait implemented by the [`ServerConnection`]/[`ClientConnection`]
350    /// allowing them to be the subject of a [`Writer`].
351    ///
352    /// [`ServerConnection`]: crate::ServerConnection
353    /// [`ClientConnection`]: crate::ClientConnection
354    pub(crate) trait PlaintextSink {
355        fn write(&mut self, buf: &[u8]) -> io::Result<usize>;
356        fn write_vectored(&mut self, bufs: &[io::IoSlice<'_>]) -> io::Result<usize>;
357        fn flush(&mut self) -> io::Result<()>;
358    }
359
360    impl<T> ConnectionCommon<T> {
361        /// Return the fatal error this connection previously encountered, if any.
362        fn check_error(&self) -> io::Result<()> {
363            match &self.core.state {
364                Ok(_) => Ok(()),
365                Err(err) => Err(io::Error::new(io::ErrorKind::InvalidData, err.clone())),
366            }
367        }
368
369        /// Send or buffer as much of `payload` as possible.
370        ///
371        /// This updates the TLS 1.3 traffic keys as needed between records.
372        fn send_plaintext(&mut self, payload: OutboundChunks<'_>) -> usize {
373            let mut len = 0;
374            loop {
375                len += self
376                    .core
377                    .common_state
378                    .buffer_plaintext(payload.split_at(len).1, &mut self.sendable_plaintext);
379                if !self.core.maybe_refresh_traffic_keys() || len == payload.len() {
380                    return len;
381                }
382            }
383        }
384    }
385
386    impl<T> PlaintextSink for ConnectionCommon<T> {
387        fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
388            self.check_error()?;
389            Ok(self.send_plaintext(buf.into()))
390        }
391
392        fn write_vectored(&mut self, bufs: &[io::IoSlice<'_>]) -> io::Result<usize> {
393            self.check_error()?;
394            let payload_owner: Vec<&[u8]>;
395            let payload = match bufs.len() {
396                0 => return Ok(0),
397                1 => OutboundChunks::Single(bufs[0].deref()),
398                _ => {
399                    payload_owner = bufs
400                        .iter()
401                        .map(|io_slice| io_slice.deref())
402                        .collect();
403
404                    OutboundChunks::new(&payload_owner)
405                }
406            };
407            Ok(self.send_plaintext(payload))
408        }
409
410        fn flush(&mut self) -> io::Result<()> {
411            self.check_error()
412        }
413    }
414}
415
416#[cfg(feature = "std")]
417pub use connection::{Connection, Reader, Writer};
418
419#[derive(Debug)]
420pub(crate) struct ConnectionRandoms {
421    pub(crate) client: [u8; 32],
422    pub(crate) server: [u8; 32],
423}
424
425impl ConnectionRandoms {
426    pub(crate) fn new(client: Random, server: Random) -> Self {
427        Self {
428            client: client.0,
429            server: server.0,
430        }
431    }
432}
433
434/// Interface shared by client and server connections.
435pub struct ConnectionCommon<Data> {
436    pub(crate) core: ConnectionCore<Data>,
437    deframer_buffer: DeframerVecBuffer,
438    sendable_plaintext: ChunkVecBuffer,
439}
440
441impl<Data> ConnectionCommon<Data> {
442    /// Processes any new packets read by a previous call to
443    /// [`Connection::read_tls`].
444    ///
445    /// Errors from this function relate to TLS protocol errors, and
446    /// are fatal to the connection.  Future calls after an error will do
447    /// no new work and will return the same error. After an error is
448    /// received from [`process_new_packets`], you should not call [`read_tls`]
449    /// any more (it will fill up buffers to no purpose). However, you
450    /// may call the other methods on the connection, including `write`,
451    /// `send_close_notify`, and `write_tls`. Most likely you will want to
452    /// call `write_tls` to send any alerts queued by the error and then
453    /// close the underlying connection.
454    ///
455    /// Success from this function comes with some sundry state data
456    /// about the connection.
457    ///
458    /// [`read_tls`]: Connection::read_tls
459    /// [`process_new_packets`]: Connection::process_new_packets
460    #[inline]
461    pub fn process_new_packets(&mut self) -> Result<IoState, Error> {
462        self.core
463            .process_new_packets(&mut self.deframer_buffer, &mut self.sendable_plaintext)
464    }
465
466    /// Derives key material from the agreed connection secrets.
467    ///
468    /// This function fills in `output` with `output.len()` bytes of key
469    /// material derived from the master session secret using `label`
470    /// and `context` for diversification. Ownership of the buffer is taken
471    /// by the function and returned via the Ok result to ensure no key
472    /// material leaks if the function fails.
473    ///
474    /// See RFC5705 for more details on what this does and is for.
475    ///
476    /// For TLS1.3 connections, this function does not use the
477    /// "early" exporter at any point.
478    ///
479    /// This function fails if called prior to the handshake completing;
480    /// check with [`CommonState::is_handshaking`] first.
481    ///
482    /// This function fails if `output.len()` is zero.
483    #[inline]
484    pub fn export_keying_material<T: AsMut<[u8]>>(
485        &self,
486        output: T,
487        label: &[u8],
488        context: Option<&[u8]>,
489    ) -> Result<T, Error> {
490        self.core
491            .export_keying_material(output, label, context)
492    }
493
494    /// Extract secrets, so they can be used when configuring kTLS, for example.
495    /// Should be used with care as it exposes secret key material.
496    pub fn dangerous_extract_secrets(self) -> Result<ExtractedSecrets, Error> {
497        self.core.dangerous_extract_secrets()
498    }
499
500    /// Sets a limit on the internal buffers used to buffer
501    /// unsent plaintext (prior to completing the TLS handshake)
502    /// and unsent TLS records.  This limit acts only on application
503    /// data written through [`Connection::writer`].
504    ///
505    /// By default the limit is 64KB.  The limit can be set
506    /// at any time, even if the current buffer use is higher.
507    ///
508    /// [`None`] means no limit applies, and will mean that written
509    /// data is buffered without bound -- it is up to the application
510    /// to appropriately schedule its plaintext and TLS writes to bound
511    /// memory usage.
512    ///
513    /// For illustration: `Some(1)` means a limit of one byte applies:
514    /// [`Connection::writer`] will accept only one byte, encrypt it and
515    /// add a TLS header.  Once this is sent via [`Connection::write_tls`],
516    /// another byte may be sent.
517    ///
518    /// # Internal write-direction buffering
519    /// rustls has two buffers whose size are bounded by this setting:
520    ///
521    /// ## Buffering of unsent plaintext data prior to handshake completion
522    ///
523    /// Calls to [`Connection::writer`] before or during the handshake
524    /// are buffered (up to the limit specified here).  Once the
525    /// handshake completes this data is encrypted and the resulting
526    /// TLS records are added to the outgoing buffer.
527    ///
528    /// ## Buffering of outgoing TLS records
529    ///
530    /// This buffer is used to store TLS records that rustls needs to
531    /// send to the peer.  It is used in these two circumstances:
532    ///
533    /// - by [`Connection::process_new_packets`] when a handshake or alert
534    ///   TLS record needs to be sent.
535    /// - by [`Connection::writer`] post-handshake: the plaintext is
536    ///   encrypted and the resulting TLS record is buffered.
537    ///
538    /// This buffer is emptied by [`Connection::write_tls`].
539    ///
540    /// [`Connection::writer`]: crate::Connection::writer
541    /// [`Connection::write_tls`]: crate::Connection::write_tls
542    /// [`Connection::process_new_packets`]: crate::Connection::process_new_packets
543    pub fn set_buffer_limit(&mut self, limit: Option<usize>) {
544        self.sendable_plaintext.set_limit(limit);
545        self.sendable_tls.set_limit(limit);
546    }
547
548    /// Sends a TLS1.3 `key_update` message to refresh a connection's keys.
549    ///
550    /// This call refreshes our encryption keys. Once the peer receives the message,
551    /// it refreshes _its_ encryption and decryption keys and sends a response.
552    /// Once we receive that response, we refresh our decryption keys to match.
553    /// At the end of this process, keys in both directions have been refreshed.
554    ///
555    /// Note that this process does not happen synchronously: this call just
556    /// arranges that the `key_update` message will be included in the next
557    /// `write_tls` output.
558    ///
559    /// This fails with `Error::HandshakeNotComplete` if called before the initial
560    /// handshake is complete, or if a version prior to TLS1.3 is negotiated.
561    ///
562    /// # Usage advice
563    /// Note that other implementations (including rustls) may enforce limits on
564    /// the number of `key_update` messages allowed on a given connection to prevent
565    /// denial of service.  Therefore, this should be called sparingly.
566    ///
567    /// rustls implicitly and automatically refreshes traffic keys when needed
568    /// according to the selected cipher suite's cryptographic constraints.  There
569    /// is therefore no need to call this manually to avoid cryptographic keys
570    /// "wearing out".
571    ///
572    /// The main reason to call this manually is to roll keys when it is known
573    /// a connection will be idle for a long period.
574    pub fn refresh_traffic_keys(&mut self) -> Result<(), Error> {
575        self.core.refresh_traffic_keys()
576    }
577}
578
579#[cfg(feature = "std")]
580impl<Data> ConnectionCommon<Data> {
581    /// Returns an object that allows reading plaintext.
582    pub fn reader(&mut self) -> Reader<'_> {
583        let common = &mut self.core.common_state;
584        Reader {
585            received_plaintext: &mut common.received_plaintext,
586            // Are we done? i.e., have we processed all received messages, and received a
587            // close_notify to indicate that no new messages will arrive?
588            has_received_close_notify: common.has_received_close_notify,
589            has_seen_eof: common.has_seen_eof,
590        }
591    }
592
593    /// Returns an object that allows writing plaintext.
594    pub fn writer(&mut self) -> Writer<'_> {
595        Writer::new(self)
596    }
597
598    /// This function uses `io` to complete any outstanding IO for
599    /// this connection.
600    ///
601    /// This is a convenience function which solely uses other parts
602    /// of the public API.
603    ///
604    /// What this means depends on the connection  state:
605    ///
606    /// - If the connection [`is_handshaking`], then IO is performed until
607    ///   the handshake is complete.
608    /// - Otherwise, if [`wants_write`] is true, [`write_tls`] is invoked
609    ///   until it is all written.
610    /// - Otherwise, if [`wants_read`] is true, [`read_tls`] is invoked
611    ///   once.
612    ///
613    /// The return value is the number of bytes read from and written
614    /// to `io`, respectively. Once both `read()` and `write()` yield `WouldBlock`,
615    /// this function will propagate the error.
616    ///
617    /// Errors from TLS record handling (i.e., from [`process_new_packets`])
618    /// are wrapped in an `io::ErrorKind::InvalidData`-kind error.
619    ///
620    /// [`is_handshaking`]: CommonState::is_handshaking
621    /// [`wants_read`]: CommonState::wants_read
622    /// [`wants_write`]: CommonState::wants_write
623    /// [`write_tls`]: ConnectionCommon::write_tls
624    /// [`read_tls`]: ConnectionCommon::read_tls
625    /// [`process_new_packets`]: ConnectionCommon::process_new_packets
626    pub fn complete_io<T>(&mut self, io: &mut T) -> Result<(usize, usize), io::Error>
627    where
628        Self: Sized,
629        T: io::Read + io::Write,
630    {
631        let mut eof = false;
632        let mut wrlen = 0;
633        let mut rdlen = 0;
634        loop {
635            let (mut blocked_write, mut blocked_read) = (None, None);
636            let until_handshaked = self.is_handshaking();
637
638            if !self.wants_write() && !self.wants_read() {
639                // We will make no further progress.
640                return Ok((rdlen, wrlen));
641            }
642
643            while self.wants_write() {
644                match self.write_tls(io) {
645                    Ok(0) => {
646                        io.flush()?;
647                        return Ok((rdlen, wrlen)); // EOF.
648                    }
649                    Ok(n) => wrlen += n,
650                    Err(err) if err.kind() == io::ErrorKind::WouldBlock => {
651                        blocked_write = Some(err);
652                        break;
653                    }
654                    Err(err) => return Err(err),
655                }
656            }
657            if wrlen > 0 {
658                io.flush()?;
659            }
660
661            if !until_handshaked && wrlen > 0 {
662                return Ok((rdlen, wrlen));
663            }
664
665            // If we want to write, but are WouldBlocked by the underlying IO, *and*
666            // have no desire to read; that is everything.
667            if let (Some(_), false) = (&blocked_write, self.wants_read()) {
668                return match wrlen {
669                    0 => Err(blocked_write.unwrap()),
670                    _ => Ok((rdlen, wrlen)),
671                };
672            }
673
674            while !eof && self.wants_read() {
675                let read_size = match self.read_tls(io) {
676                    Ok(0) => {
677                        eof = true;
678                        Some(0)
679                    }
680                    Ok(n) => {
681                        rdlen += n;
682                        Some(n)
683                    }
684                    Err(err) if err.kind() == io::ErrorKind::WouldBlock => {
685                        blocked_read = Some(err);
686                        break;
687                    }
688                    Err(err) if err.kind() == io::ErrorKind::Interrupted => None, // nothing to do
689                    Err(err) => return Err(err),
690                };
691                if read_size.is_some() {
692                    break;
693                }
694            }
695
696            if let Err(e) = self.process_new_packets() {
697                // In case we have an alert to send describing this error, try a last-gasp
698                // write -- but don't predate the primary error.
699                let _ignored = self.write_tls(io);
700                let _ignored = io.flush();
701                return Err(io::Error::new(io::ErrorKind::InvalidData, e));
702            };
703
704            // If we want to read, but are WouldBlocked by the underlying IO, *and*
705            // have no desire to write; that is everything.
706            if let (Some(_), false) = (&blocked_read, self.wants_write()) {
707                return match rdlen {
708                    0 => Err(blocked_read.unwrap()),
709                    _ => Ok((rdlen, wrlen)),
710                };
711            }
712
713            // if we're doing IO until handshaked, and we believe we've finished handshaking,
714            // but process_new_packets() has queued TLS data to send, loop around again to write
715            // the queued messages.
716            if until_handshaked && !self.is_handshaking() && self.wants_write() {
717                continue;
718            }
719
720            let blocked = blocked_write.zip(blocked_read);
721            match (eof, until_handshaked, self.is_handshaking(), blocked) {
722                (_, true, false, _) => return Ok((rdlen, wrlen)),
723                (_, _, _, Some((e, _))) if rdlen == 0 && wrlen == 0 => return Err(e),
724                (_, false, _, _) => return Ok((rdlen, wrlen)),
725                (true, true, true, _) => return Err(io::Error::from(io::ErrorKind::UnexpectedEof)),
726                _ => {}
727            }
728        }
729    }
730
731    /// Extract the first handshake message.
732    ///
733    /// This is a shortcut to the `process_new_packets()` -> `process_msg()` ->
734    /// `process_handshake_messages()` path, specialized for the first handshake message.
735    pub(crate) fn first_handshake_message(&mut self) -> Result<Option<Message<'static>>, Error> {
736        let mut buffer_progress = self.core.hs_deframer.progress();
737
738        let res = self
739            .core
740            .deframe(
741                None,
742                self.deframer_buffer.filled_mut(),
743                &mut buffer_progress,
744            )
745            .map(|opt| opt.map(|pm| Message::try_from(pm).map(|m| m.into_owned())));
746
747        match res? {
748            Some(Ok(msg)) => {
749                self.deframer_buffer
750                    .discard(buffer_progress.take_discard());
751                Ok(Some(msg))
752            }
753            Some(Err(err)) => Err(self.send_fatal_alert(AlertDescription::DecodeError, err)),
754            None => Ok(None),
755        }
756    }
757
758    pub(crate) fn replace_state(&mut self, new: Box<dyn State<Data>>) {
759        self.core.state = Ok(new);
760    }
761
762    /// Read TLS content from `rd` into the internal buffer.
763    ///
764    /// Due to the internal buffering, `rd` can supply TLS messages in arbitrary-sized chunks (like
765    /// a socket or pipe might).
766    ///
767    /// You should call [`process_new_packets()`] each time a call to this function succeeds in order
768    /// to empty the incoming TLS data buffer.
769    ///
770    /// This function returns `Ok(0)` when the underlying `rd` does so. This typically happens when
771    /// a socket is cleanly closed, or a file is at EOF. Errors may result from the IO done through
772    /// `rd`; additionally, errors of `ErrorKind::Other` are emitted to signal backpressure:
773    ///
774    /// * In order to empty the incoming TLS data buffer, you should call [`process_new_packets()`]
775    ///   each time a call to this function succeeds.
776    /// * In order to empty the incoming plaintext data buffer, you should empty it through
777    ///   the [`reader()`] after the call to [`process_new_packets()`].
778    ///
779    /// This function also returns `Ok(0)` once a `close_notify` alert has been successfully
780    /// received.  No additional data is ever read in this state.
781    ///
782    /// [`process_new_packets()`]: ConnectionCommon::process_new_packets
783    /// [`reader()`]: ConnectionCommon::reader
784    pub fn read_tls(&mut self, rd: &mut dyn io::Read) -> Result<usize, io::Error> {
785        if self.received_plaintext.is_full() {
786            return Err(io::Error::new(
787                io::ErrorKind::Other,
788                "received plaintext buffer full",
789            ));
790        }
791
792        if self.has_received_close_notify {
793            return Ok(0);
794        }
795
796        let res = self
797            .deframer_buffer
798            .read(rd, self.core.hs_deframer.is_active());
799        if let Ok(0) = res {
800            self.has_seen_eof = true;
801        }
802        res
803    }
804
805    /// Writes TLS messages to `wr`.
806    ///
807    /// On success, this function returns `Ok(n)` where `n` is a number of bytes written to `wr`
808    /// (after encoding and encryption).
809    ///
810    /// After this function returns, the connection buffer may not yet be fully flushed. The
811    /// [`CommonState::wants_write`] function can be used to check if the output buffer is empty.
812    pub fn write_tls(&mut self, wr: &mut dyn io::Write) -> Result<usize, io::Error> {
813        self.sendable_tls.write_to(wr)
814    }
815}
816
817impl<'a, Data> From<&'a mut ConnectionCommon<Data>> for Context<'a, Data> {
818    fn from(conn: &'a mut ConnectionCommon<Data>) -> Self {
819        Self {
820            common: &mut conn.core.common_state,
821            data: &mut conn.core.data,
822            sendable_plaintext: Some(&mut conn.sendable_plaintext),
823        }
824    }
825}
826
827impl<T> Deref for ConnectionCommon<T> {
828    type Target = CommonState;
829
830    fn deref(&self) -> &Self::Target {
831        &self.core.common_state
832    }
833}
834
835impl<T> DerefMut for ConnectionCommon<T> {
836    fn deref_mut(&mut self) -> &mut Self::Target {
837        &mut self.core.common_state
838    }
839}
840
841impl<Data> From<ConnectionCore<Data>> for ConnectionCommon<Data> {
842    fn from(core: ConnectionCore<Data>) -> Self {
843        Self {
844            core,
845            deframer_buffer: DeframerVecBuffer::default(),
846            sendable_plaintext: ChunkVecBuffer::new(Some(DEFAULT_BUFFER_LIMIT)),
847        }
848    }
849}
850
851/// Interface shared by unbuffered client and server connections.
852pub struct UnbufferedConnectionCommon<Data> {
853    pub(crate) core: ConnectionCore<Data>,
854    wants_write: bool,
855    emitted_peer_closed_state: bool,
856}
857
858impl<Data> From<ConnectionCore<Data>> for UnbufferedConnectionCommon<Data> {
859    fn from(core: ConnectionCore<Data>) -> Self {
860        Self {
861            core,
862            wants_write: false,
863            emitted_peer_closed_state: false,
864        }
865    }
866}
867
868impl<Data> UnbufferedConnectionCommon<Data> {
869    /// Extract secrets, so they can be used when configuring kTLS, for example.
870    /// Should be used with care as it exposes secret key material.
871    pub fn dangerous_extract_secrets(self) -> Result<ExtractedSecrets, Error> {
872        self.core.dangerous_extract_secrets()
873    }
874}
875
876impl<T> Deref for UnbufferedConnectionCommon<T> {
877    type Target = CommonState;
878
879    fn deref(&self) -> &Self::Target {
880        &self.core.common_state
881    }
882}
883
884pub(crate) struct ConnectionCore<Data> {
885    pub(crate) state: Result<Box<dyn State<Data>>, Error>,
886    pub(crate) data: Data,
887    pub(crate) common_state: CommonState,
888    pub(crate) hs_deframer: HandshakeDeframer,
889
890    /// We limit consecutive empty fragments to avoid a route for the peer to send
891    /// us significant but fruitless traffic.
892    seen_consecutive_empty_fragments: u8,
893}
894
895impl<Data> ConnectionCore<Data> {
896    pub(crate) fn new(state: Box<dyn State<Data>>, data: Data, common_state: CommonState) -> Self {
897        Self {
898            state: Ok(state),
899            data,
900            common_state,
901            hs_deframer: HandshakeDeframer::default(),
902            seen_consecutive_empty_fragments: 0,
903        }
904    }
905
906    pub(crate) fn process_new_packets(
907        &mut self,
908        deframer_buffer: &mut DeframerVecBuffer,
909        sendable_plaintext: &mut ChunkVecBuffer,
910    ) -> Result<IoState, Error> {
911        let mut state = match mem::replace(&mut self.state, Err(Error::HandshakeNotComplete)) {
912            Ok(state) => state,
913            Err(e) => {
914                self.state = Err(e.clone());
915                return Err(e);
916            }
917        };
918
919        let mut buffer_progress = self.hs_deframer.progress();
920
921        loop {
922            let res = self.deframe(
923                Some(&*state),
924                deframer_buffer.filled_mut(),
925                &mut buffer_progress,
926            );
927
928            let opt_msg = match res {
929                Ok(opt_msg) => opt_msg,
930                Err(e) => {
931                    self.state = Err(e.clone());
932                    deframer_buffer.discard(buffer_progress.take_discard());
933                    return Err(e);
934                }
935            };
936
937            let Some(msg) = opt_msg else {
938                break;
939            };
940
941            match self.process_msg(msg, state, Some(sendable_plaintext)) {
942                Ok(new) => state = new,
943                Err(e) => {
944                    self.state = Err(e.clone());
945                    deframer_buffer.discard(buffer_progress.take_discard());
946                    return Err(e);
947                }
948            }
949
950            if self
951                .common_state
952                .has_received_close_notify
953            {
954                // "Any data received after a closure alert has been received MUST be ignored."
955                // -- <https://datatracker.ietf.org/doc/html/rfc8446#section-6.1>
956                // This is data that has already been accepted in `read_tls`.
957                buffer_progress.add_discard(deframer_buffer.filled().len());
958                break;
959            }
960
961            deframer_buffer.discard(buffer_progress.take_discard());
962        }
963
964        deframer_buffer.discard(buffer_progress.take_discard());
965        self.state = Ok(state);
966        Ok(self.common_state.current_io_state())
967    }
968
969    /// Pull a message out of the deframer and send any messages that need to be sent as a result.
970    fn deframe<'b>(
971        &mut self,
972        state: Option<&dyn State<Data>>,
973        buffer: &'b mut [u8],
974        buffer_progress: &mut BufferProgress,
975    ) -> Result<Option<InboundPlainMessage<'b>>, Error> {
976        // before processing any more of `buffer`, return any extant messages from `hs_deframer`
977        if self.hs_deframer.has_message_ready() {
978            Ok(self.take_handshake_message(buffer, buffer_progress))
979        } else {
980            self.process_more_input(state, buffer, buffer_progress)
981        }
982    }
983
984    fn take_handshake_message<'b>(
985        &mut self,
986        buffer: &'b mut [u8],
987        buffer_progress: &mut BufferProgress,
988    ) -> Option<InboundPlainMessage<'b>> {
989        let message = self
990            .hs_deframer
991            .iter(buffer)
992            .next()
993            .map(|(message, discard)| {
994                buffer_progress.add_discard(discard);
995                message
996            });
997        self.common_state.aligned_handshake = self.hs_deframer.is_aligned();
998        message
999    }
1000
1001    fn process_more_input<'b>(
1002        &mut self,
1003        state: Option<&dyn State<Data>>,
1004        buffer: &'b mut [u8],
1005        buffer_progress: &mut BufferProgress,
1006    ) -> Result<Option<InboundPlainMessage<'b>>, Error> {
1007        let version_is_tls13 = matches!(
1008            self.common_state.negotiated_version,
1009            Some(ProtocolVersion::TLSv1_3)
1010        );
1011
1012        let locator = Locator::new(buffer);
1013
1014        loop {
1015            let mut iter = DeframerIter::new(&mut buffer[buffer_progress.processed()..]);
1016
1017            let (message, processed) = loop {
1018                let message = match iter.next().transpose() {
1019                    Ok(Some(message)) => message,
1020                    Ok(None) => return Ok(None),
1021                    Err(err) => return Err(self.handle_deframe_error(err, state)),
1022                };
1023
1024                let allowed_plaintext = match message.typ {
1025                    // CCS messages are always plaintext.
1026                    ContentType::ChangeCipherSpec => true,
1027                    // Alerts are allowed to be plaintext if-and-only-if:
1028                    // * The negotiated protocol version is TLS 1.3. - In TLS 1.2 it is unambiguous when
1029                    //   keying changes based on the CCS message. Only TLS 1.3 requires these heuristics.
1030                    // * We have not yet decrypted any messages from the peer - if we have we don't
1031                    //   expect any plaintext.
1032                    // * The payload size is indicative of a plaintext alert message.
1033                    ContentType::Alert
1034                        if version_is_tls13
1035                            && !self
1036                                .common_state
1037                                .record_layer
1038                                .has_decrypted()
1039                            && message.payload.len() <= 2 =>
1040                    {
1041                        true
1042                    }
1043                    // In other circumstances, we expect all messages to be encrypted.
1044                    _ => false,
1045                };
1046
1047                if allowed_plaintext && !self.hs_deframer.is_active() {
1048                    break (message.into_plain_message(), iter.bytes_consumed());
1049                }
1050
1051                let message = match self
1052                    .common_state
1053                    .record_layer
1054                    .decrypt_incoming(message)
1055                {
1056                    // failed decryption during trial decryption is not allowed to be
1057                    // interleaved with partial handshake data.
1058                    Ok(None) if !self.hs_deframer.is_aligned() => {
1059                        return Err(
1060                            PeerMisbehaved::RejectedEarlyDataInterleavedWithHandshakeMessage.into(),
1061                        );
1062                    }
1063
1064                    // failed decryption during trial decryption.
1065                    Ok(None) => continue,
1066
1067                    Ok(Some(message)) => message,
1068
1069                    Err(err) => return Err(self.handle_deframe_error(err, state)),
1070                };
1071
1072                let Decrypted {
1073                    want_close_before_decrypt,
1074                    plaintext,
1075                } = message;
1076
1077                if want_close_before_decrypt {
1078                    self.common_state.send_close_notify();
1079                }
1080
1081                break (plaintext, iter.bytes_consumed());
1082            };
1083
1084            if !self.hs_deframer.is_aligned() && message.typ != ContentType::Handshake {
1085                // "Handshake messages MUST NOT be interleaved with other record
1086                // types.  That is, if a handshake message is split over two or more
1087                // records, there MUST NOT be any other records between them."
1088                // https://www.rfc-editor.org/rfc/rfc8446#section-5.1
1089                return Err(PeerMisbehaved::MessageInterleavedWithHandshakeMessage.into());
1090            }
1091
1092            match message.payload.len() {
1093                0 => {
1094                    if self.seen_consecutive_empty_fragments
1095                        == ALLOWED_CONSECUTIVE_EMPTY_FRAGMENTS_MAX
1096                    {
1097                        return Err(PeerMisbehaved::TooManyEmptyFragments.into());
1098                    }
1099                    self.seen_consecutive_empty_fragments += 1;
1100                }
1101                _ => {
1102                    self.seen_consecutive_empty_fragments = 0;
1103                }
1104            };
1105
1106            buffer_progress.add_processed(processed);
1107
1108            // do an end-run around the borrow checker, converting `message` (containing
1109            // a borrowed slice) to an unborrowed one (containing a `Range` into the
1110            // same buffer).  the reborrow happens inside the branch that returns the
1111            // message.
1112            //
1113            // is fixed by -Zpolonius
1114            // https://github.com/rust-lang/rfcs/blob/master/text/2094-nll.md#problem-case-3-conditional-control-flow-across-functions
1115            let unborrowed = InboundUnborrowedMessage::unborrow(&locator, message);
1116
1117            if unborrowed.typ != ContentType::Handshake {
1118                let message = unborrowed.reborrow(&Delocator::new(buffer));
1119                buffer_progress.add_discard(processed);
1120                return Ok(Some(message));
1121            }
1122
1123            let message = unborrowed.reborrow(&Delocator::new(buffer));
1124            self.hs_deframer
1125                .input_message(message, &locator, buffer_progress.processed());
1126            self.hs_deframer.coalesce(buffer)?;
1127
1128            self.common_state.aligned_handshake = self.hs_deframer.is_aligned();
1129
1130            if self.hs_deframer.has_message_ready() {
1131                // trial decryption finishes with the first handshake message after it started.
1132                self.common_state
1133                    .record_layer
1134                    .finish_trial_decryption();
1135
1136                return Ok(self.take_handshake_message(buffer, buffer_progress));
1137            }
1138        }
1139    }
1140
1141    fn handle_deframe_error(&mut self, error: Error, state: Option<&dyn State<Data>>) -> Error {
1142        match error {
1143            error @ Error::InvalidMessage(_) => {
1144                if self.common_state.is_quic() {
1145                    self.common_state.quic.alert = Some(AlertDescription::DecodeError);
1146                    error
1147                } else {
1148                    self.common_state
1149                        .send_fatal_alert(AlertDescription::DecodeError, error)
1150                }
1151            }
1152            Error::PeerSentOversizedRecord => self
1153                .common_state
1154                .send_fatal_alert(AlertDescription::RecordOverflow, error),
1155            Error::DecryptError => {
1156                if let Some(state) = state {
1157                    state.handle_decrypt_error();
1158                }
1159                self.common_state
1160                    .send_fatal_alert(AlertDescription::BadRecordMac, error)
1161            }
1162            Error::PeerMisbehaved(PeerMisbehaved::IllegalMiddleboxChangeCipherSpec) => self
1163                .common_state
1164                .send_fatal_alert(AlertDescription::UnexpectedMessage, error),
1165
1166            error => error,
1167        }
1168    }
1169
1170    fn process_msg(
1171        &mut self,
1172        msg: InboundPlainMessage<'_>,
1173        state: Box<dyn State<Data>>,
1174        sendable_plaintext: Option<&mut ChunkVecBuffer>,
1175    ) -> Result<Box<dyn State<Data>>, Error> {
1176        // Drop CCS messages during handshake in TLS1.3
1177        if msg.typ == ContentType::ChangeCipherSpec
1178            && !self
1179                .common_state
1180                .may_receive_application_data
1181            && self.common_state.is_tls13()
1182        {
1183            if !msg.is_valid_ccs() {
1184                // "An implementation which receives any other change_cipher_spec value or
1185                //  which receives a protected change_cipher_spec record MUST abort the
1186                //  handshake with an "unexpected_message" alert."
1187                return Err(self.common_state.send_fatal_alert(
1188                    AlertDescription::UnexpectedMessage,
1189                    PeerMisbehaved::IllegalMiddleboxChangeCipherSpec,
1190                ));
1191            }
1192
1193            self.common_state
1194                .received_tls13_change_cipher_spec()?;
1195            trace!("Dropping CCS");
1196            return Ok(state);
1197        }
1198
1199        // Now we can fully parse the message payload.
1200        let msg = match Message::try_from(msg) {
1201            Ok(msg) => msg,
1202            Err(err) => {
1203                return Err(self
1204                    .common_state
1205                    .send_fatal_alert(AlertDescription::from(err), err));
1206            }
1207        };
1208
1209        // For alerts, we have separate logic.
1210        if let MessagePayload::Alert(alert) = &msg.payload {
1211            self.common_state.process_alert(alert)?;
1212            return Ok(state);
1213        }
1214
1215        self.common_state
1216            .process_main_protocol(msg, state, &mut self.data, sendable_plaintext)
1217    }
1218
1219    pub(crate) fn dangerous_extract_secrets(self) -> Result<ExtractedSecrets, Error> {
1220        Ok(self
1221            .dangerous_into_kernel_connection()?
1222            .0)
1223    }
1224
1225    pub(crate) fn dangerous_into_kernel_connection(
1226        self,
1227    ) -> Result<(ExtractedSecrets, KernelConnection<Data>), Error> {
1228        if !self
1229            .common_state
1230            .enable_secret_extraction
1231        {
1232            return Err(Error::General("Secret extraction is disabled".into()));
1233        }
1234
1235        if self.common_state.is_handshaking() {
1236            return Err(Error::HandshakeNotComplete);
1237        }
1238
1239        if !self
1240            .common_state
1241            .sendable_tls
1242            .is_empty()
1243        {
1244            return Err(Error::General(
1245                "cannot convert into an KernelConnection while there are still buffered TLS records to send"
1246                    .into()
1247            ));
1248        }
1249
1250        let state = self.state?;
1251
1252        let record_layer = &self.common_state.record_layer;
1253        let secrets = state.extract_secrets()?;
1254        let secrets = ExtractedSecrets {
1255            tx: (record_layer.write_seq(), secrets.tx),
1256            rx: (record_layer.read_seq(), secrets.rx),
1257        };
1258
1259        let state = state.into_external_state()?;
1260        let external = KernelConnection::new(state, self.common_state)?;
1261
1262        Ok((secrets, external))
1263    }
1264
1265    pub(crate) fn export_keying_material<T: AsMut<[u8]>>(
1266        &self,
1267        mut output: T,
1268        label: &[u8],
1269        context: Option<&[u8]>,
1270    ) -> Result<T, Error> {
1271        if output.as_mut().is_empty() {
1272            return Err(Error::General(
1273                "export_keying_material with zero-length output".into(),
1274            ));
1275        }
1276
1277        match self.state.as_ref() {
1278            Ok(st) => st
1279                .export_keying_material(output.as_mut(), label, context)
1280                .map(|_| output),
1281            Err(e) => Err(e.clone()),
1282        }
1283    }
1284
1285    /// Trigger a `refresh_traffic_keys` if required by `CommonState`.
1286    ///
1287    /// Returns whether the traffic keys were updated.
1288    fn maybe_refresh_traffic_keys(&mut self) -> bool {
1289        mem::take(
1290            &mut self
1291                .common_state
1292                .refresh_traffic_keys_pending,
1293        ) && self.refresh_traffic_keys().is_ok()
1294    }
1295
1296    fn refresh_traffic_keys(&mut self) -> Result<(), Error> {
1297        match &mut self.state {
1298            Ok(st) => st.send_key_update_request(&mut self.common_state),
1299            Err(e) => Err(e.clone()),
1300        }
1301    }
1302}
1303
1304/// Data specific to the peer's side (client or server).
1305pub trait SideData: Debug {}
1306
1307/// An InboundPlainMessage which does not borrow its payload, but
1308/// references a range that can later be borrowed.
1309struct InboundUnborrowedMessage {
1310    typ: ContentType,
1311    version: ProtocolVersion,
1312    bounds: Range<usize>,
1313}
1314
1315impl InboundUnborrowedMessage {
1316    fn unborrow(locator: &Locator, msg: InboundPlainMessage<'_>) -> Self {
1317        Self {
1318            typ: msg.typ,
1319            version: msg.version,
1320            bounds: locator.locate(msg.payload),
1321        }
1322    }
1323
1324    fn reborrow<'b>(self, delocator: &Delocator<'b>) -> InboundPlainMessage<'b> {
1325        InboundPlainMessage {
1326            typ: self.typ,
1327            version: self.version,
1328            payload: delocator.slice_from_range(&self.bounds),
1329        }
1330    }
1331}
1332
1333/// cf. BoringSSL's `kMaxEmptyRecords`
1334/// <https://github.com/google/boringssl/blob/dec5989b793c56ad4dd32173bd2d8595ca78b398/ssl/tls_record.cc#L124-L128>
1335const ALLOWED_CONSECUTIVE_EMPTY_FRAGMENTS_MAX: u8 = 32;