clia_rustls_mod/
conn.rs

1use alloc::boxed::Box;
2use core::fmt::Debug;
3use core::mem;
4use core::ops::{Deref, DerefMut};
5#[cfg(feature = "std")]
6use std::io;
7
8use crate::common_state::{CommonState, Context, IoState, State, DEFAULT_BUFFER_LIMIT};
9use crate::enums::{AlertDescription, ContentType};
10use crate::error::{Error, PeerMisbehaved};
11#[cfg(feature = "logging")]
12use crate::log::trace;
13use crate::msgs::deframer::{Deframed, DeframerSliceBuffer, DeframerVecBuffer, MessageDeframer};
14use crate::msgs::handshake::Random;
15use crate::msgs::message::{InboundPlainMessage, Message, MessagePayload};
16use crate::suites::{ExtractedSecrets, PartiallyExtractedSecrets};
17use crate::vecbuf::ChunkVecBuffer;
18
19pub(crate) mod unbuffered;
20
21#[cfg(feature = "std")]
22mod connection {
23    use alloc::vec::Vec;
24    use core::fmt::Debug;
25    use core::ops::{Deref, DerefMut};
26    use std::io;
27
28    use crate::common_state::{CommonState, IoState};
29    use crate::error::Error;
30    use crate::msgs::message::OutboundChunks;
31    use crate::suites::ExtractedSecrets;
32    use crate::vecbuf::ChunkVecBuffer;
33    use crate::ConnectionCommon;
34
35    /// A client or server connection.
36    #[derive(Debug)]
37    pub enum Connection {
38        /// A client connection
39        Client(crate::client::ClientConnection),
40        /// A server connection
41        Server(crate::server::ServerConnection),
42    }
43
44    impl Connection {
45        /// Read TLS content from `rd`.
46        ///
47        /// See [`ConnectionCommon::read_tls()`] for more information.
48        pub fn read_tls(&mut self, rd: &mut dyn io::Read) -> Result<usize, io::Error> {
49            match self {
50                Self::Client(conn) => conn.read_tls(rd),
51                Self::Server(conn) => conn.read_tls(rd),
52            }
53        }
54
55        /// Writes TLS messages to `wr`.
56        ///
57        /// See [`ConnectionCommon::write_tls()`] for more information.
58        pub fn write_tls(&mut self, wr: &mut dyn io::Write) -> Result<usize, io::Error> {
59            self.sendable_tls.write_to(wr)
60        }
61
62        /// Returns an object that allows reading plaintext.
63        pub fn reader(&mut self) -> Reader {
64            match self {
65                Self::Client(conn) => conn.reader(),
66                Self::Server(conn) => conn.reader(),
67            }
68        }
69
70        /// Returns an object that allows writing plaintext.
71        pub fn writer(&mut self) -> Writer {
72            match self {
73                Self::Client(conn) => Writer::new(&mut **conn),
74                Self::Server(conn) => Writer::new(&mut **conn),
75            }
76        }
77
78        /// Processes any new packets read by a previous call to [`Connection::read_tls`].
79        ///
80        /// See [`ConnectionCommon::process_new_packets()`] for more information.
81        pub fn process_new_packets(&mut self) -> Result<IoState, Error> {
82            match self {
83                Self::Client(conn) => conn.process_new_packets(),
84                Self::Server(conn) => conn.process_new_packets(),
85            }
86        }
87
88        /// Derives key material from the agreed connection secrets.
89        ///
90        /// See [`ConnectionCommon::export_keying_material()`] for more information.
91        pub fn export_keying_material<T: AsMut<[u8]>>(
92            &self,
93            output: T,
94            label: &[u8],
95            context: Option<&[u8]>,
96        ) -> Result<T, Error> {
97            match self {
98                Self::Client(conn) => conn.export_keying_material(output, label, context),
99                Self::Server(conn) => conn.export_keying_material(output, label, context),
100            }
101        }
102
103        /// This function uses `io` to complete any outstanding IO for this connection.
104        ///
105        /// See [`ConnectionCommon::complete_io()`] for more information.
106        pub fn complete_io<T>(&mut self, io: &mut T) -> Result<(usize, usize), io::Error>
107        where
108            Self: Sized,
109            T: io::Read + io::Write,
110        {
111            match self {
112                Self::Client(conn) => conn.complete_io(io),
113                Self::Server(conn) => conn.complete_io(io),
114            }
115        }
116
117        /// Extract secrets, so they can be used when configuring kTLS, for example.
118        /// Should be used with care as it exposes secret key material.
119        pub fn dangerous_extract_secrets(self) -> Result<ExtractedSecrets, Error> {
120            match self {
121                Self::Client(client) => client.dangerous_extract_secrets(),
122                Self::Server(server) => server.dangerous_extract_secrets(),
123            }
124        }
125
126        /// Sets a limit on the internal buffers
127        ///
128        /// See [`ConnectionCommon::set_buffer_limit()`] for more information.
129        pub fn set_buffer_limit(&mut self, limit: Option<usize>) {
130            match self {
131                Self::Client(client) => client.set_buffer_limit(limit),
132                Self::Server(server) => server.set_buffer_limit(limit),
133            }
134        }
135    }
136
137    impl Deref for Connection {
138        type Target = CommonState;
139
140        fn deref(&self) -> &Self::Target {
141            match self {
142                Self::Client(conn) => &conn.core.common_state,
143                Self::Server(conn) => &conn.core.common_state,
144            }
145        }
146    }
147
148    impl DerefMut for Connection {
149        fn deref_mut(&mut self) -> &mut Self::Target {
150            match self {
151                Self::Client(conn) => &mut conn.core.common_state,
152                Self::Server(conn) => &mut conn.core.common_state,
153            }
154        }
155    }
156
157    /// A structure that implements [`std::io::Read`] for reading plaintext.
158    pub struct Reader<'a> {
159        pub(super) received_plaintext: &'a mut ChunkVecBuffer,
160        pub(super) peer_cleanly_closed: bool,
161        pub(super) has_seen_eof: bool,
162    }
163
164    impl<'a> io::Read for Reader<'a> {
165        /// Obtain plaintext data received from the peer over this TLS connection.
166        ///
167        /// If the peer closes the TLS session cleanly, this returns `Ok(0)`  once all
168        /// the pending data has been read. No further data can be received on that
169        /// connection, so the underlying TCP connection should be half-closed too.
170        ///
171        /// If the peer closes the TLS session uncleanly (a TCP EOF without sending a
172        /// `close_notify` alert) this function returns a `std::io::Error` of type
173        /// `ErrorKind::UnexpectedEof` once any pending data has been read.
174        ///
175        /// Note that support for `close_notify` varies in peer TLS libraries: many do not
176        /// support it and uncleanly close the TCP connection (this might be
177        /// vulnerable to truncation attacks depending on the application protocol).
178        /// This means applications using rustls must both handle EOF
179        /// from this function, *and* unexpected EOF of the underlying TCP connection.
180        ///
181        /// If there are no bytes to read, this returns `Err(ErrorKind::WouldBlock.into())`.
182        ///
183        /// You may learn the number of bytes available at any time by inspecting
184        /// the return of [`Connection::process_new_packets`].
185        fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
186            let len = self.received_plaintext.read(buf)?;
187
188            if len == 0 && !buf.is_empty() {
189                // No bytes available:
190                match (self.peer_cleanly_closed, self.has_seen_eof) {
191                    // cleanly closed; don't care about TCP EOF: express this as Ok(0)
192                    (true, _) => {}
193                    // unclean closure
194                    (false, true) => {
195                        return Err(io::Error::new(
196                            io::ErrorKind::UnexpectedEof,
197                            UNEXPECTED_EOF_MESSAGE,
198                        ))
199                    }
200                    // connection still going, but needs more data: signal `WouldBlock` so that
201                    // the caller knows this
202                    (false, false) => return Err(io::ErrorKind::WouldBlock.into()),
203                }
204            }
205
206            Ok(len)
207        }
208
209        /// Obtain plaintext data received from the peer over this TLS connection.
210        ///
211        /// If the peer closes the TLS session, this returns `Ok(())` without filling
212        /// any more of the buffer once all the pending data has been read. No further
213        /// data can be received on that connection, so the underlying TCP connection
214        /// should be half-closed too.
215        ///
216        /// If the peer closes the TLS session uncleanly (a TCP EOF without sending a
217        /// `close_notify` alert) this function returns a `std::io::Error` of type
218        /// `ErrorKind::UnexpectedEof` once any pending data has been read.
219        ///
220        /// Note that support for `close_notify` varies in peer TLS libraries: many do not
221        /// support it and uncleanly close the TCP connection (this might be
222        /// vulnerable to truncation attacks depending on the application protocol).
223        /// This means applications using rustls must both handle EOF
224        /// from this function, *and* unexpected EOF of the underlying TCP connection.
225        ///
226        /// If there are no bytes to read, this returns `Err(ErrorKind::WouldBlock.into())`.
227        ///
228        /// You may learn the number of bytes available at any time by inspecting
229        /// the return of [`Connection::process_new_packets`].
230        #[cfg(read_buf)]
231        fn read_buf(&mut self, mut cursor: core::io::BorrowedCursor<'_>) -> io::Result<()> {
232            let before = cursor.written();
233            self.received_plaintext
234                .read_buf(cursor.reborrow())?;
235            let len = cursor.written() - before;
236
237            if len == 0 && cursor.capacity() > 0 {
238                // No bytes available:
239                match (self.peer_cleanly_closed, self.has_seen_eof) {
240                    // cleanly closed; don't care about TCP EOF: express this as Ok(0)
241                    (true, _) => {}
242                    // unclean closure
243                    (false, true) => {
244                        return Err(io::Error::new(
245                            io::ErrorKind::UnexpectedEof,
246                            UNEXPECTED_EOF_MESSAGE,
247                        ));
248                    }
249                    // connection still going, but need more data: signal `WouldBlock` so that
250                    // the caller knows this
251                    (false, false) => return Err(io::ErrorKind::WouldBlock.into()),
252                }
253            }
254
255            Ok(())
256        }
257    }
258
259    const UNEXPECTED_EOF_MESSAGE: &str =
260        "peer closed connection without sending TLS close_notify: \
261https://docs.rs/rustls/latest/rustls/manual/_03_howto/index.html#unexpected-eof";
262
263    /// A structure that implements [`std::io::Write`] for writing plaintext.
264    pub struct Writer<'a> {
265        sink: &'a mut dyn PlaintextSink,
266    }
267
268    impl<'a> Writer<'a> {
269        /// Create a new Writer.
270        ///
271        /// This is not an external interface.  Get one of these objects
272        /// from [`Connection::writer`].
273        pub(crate) fn new(sink: &'a mut dyn PlaintextSink) -> Self {
274            Writer { sink }
275        }
276    }
277
278    impl<'a> io::Write for Writer<'a> {
279        /// Send the plaintext `buf` to the peer, encrypting
280        /// and authenticating it.  Once this function succeeds
281        /// you should call [`Connection::write_tls`] which will output the
282        /// corresponding TLS records.
283        ///
284        /// This function buffers plaintext sent before the
285        /// TLS handshake completes, and sends it as soon
286        /// as it can.  See [`ConnectionCommon::set_buffer_limit`] to control
287        /// the size of this buffer.
288        fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
289            self.sink.write(buf)
290        }
291
292        fn write_vectored(&mut self, bufs: &[io::IoSlice<'_>]) -> io::Result<usize> {
293            self.sink.write_vectored(bufs)
294        }
295
296        fn flush(&mut self) -> io::Result<()> {
297            self.sink.flush()
298        }
299    }
300
301    /// Internal trait implemented by the [`ServerConnection`]/[`ClientConnection`]
302    /// allowing them to be the subject of a [`Writer`].
303    ///
304    /// [`ServerConnection`]: crate::ServerConnection
305    /// [`ClientConnection`]: crate::ClientConnection
306    pub(crate) trait PlaintextSink {
307        fn write(&mut self, buf: &[u8]) -> io::Result<usize>;
308        fn write_vectored(&mut self, bufs: &[io::IoSlice<'_>]) -> io::Result<usize>;
309        fn flush(&mut self) -> io::Result<()>;
310    }
311
312    impl<T> PlaintextSink for ConnectionCommon<T> {
313        fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
314            Ok(self
315                .core
316                .common_state
317                .buffer_plaintext(buf.into(), &mut self.sendable_plaintext))
318        }
319
320        fn write_vectored(&mut self, bufs: &[io::IoSlice<'_>]) -> io::Result<usize> {
321            let payload_owner: Vec<&[u8]>;
322            let payload = match bufs.len() {
323                0 => return Ok(0),
324                1 => OutboundChunks::Single(bufs[0].deref()),
325                _ => {
326                    payload_owner = bufs
327                        .iter()
328                        .map(|io_slice| io_slice.deref())
329                        .collect();
330
331                    OutboundChunks::new(&payload_owner)
332                }
333            };
334            Ok(self
335                .core
336                .common_state
337                .buffer_plaintext(payload, &mut self.sendable_plaintext))
338        }
339
340        fn flush(&mut self) -> io::Result<()> {
341            Ok(())
342        }
343    }
344}
345
346#[cfg(feature = "std")]
347pub use connection::{Connection, Reader, Writer};
348
349#[derive(Debug)]
350pub(crate) struct ConnectionRandoms {
351    pub(crate) client: [u8; 32],
352    pub(crate) server: [u8; 32],
353}
354
355/// How many ChangeCipherSpec messages we accept and drop in TLS1.3 handshakes.
356/// The spec says 1, but implementations (namely the boringssl test suite) get
357/// this wrong.  BoringSSL itself accepts up to 32.
358static TLS13_MAX_DROPPED_CCS: u8 = 2u8;
359
360impl ConnectionRandoms {
361    pub(crate) fn new(client: Random, server: Random) -> Self {
362        Self {
363            client: client.0,
364            server: server.0,
365        }
366    }
367}
368
369/// Interface shared by client and server connections.
370pub struct ConnectionCommon<Data> {
371    pub(crate) core: ConnectionCore<Data>,
372    deframer_buffer: DeframerVecBuffer,
373    sendable_plaintext: ChunkVecBuffer,
374}
375
376impl<Data> ConnectionCommon<Data> {
377    /// Processes any new packets read by a previous call to
378    /// [`Connection::read_tls`].
379    ///
380    /// Errors from this function relate to TLS protocol errors, and
381    /// are fatal to the connection.  Future calls after an error will do
382    /// no new work and will return the same error. After an error is
383    /// received from [`process_new_packets`], you should not call [`read_tls`]
384    /// any more (it will fill up buffers to no purpose). However, you
385    /// may call the other methods on the connection, including `write`,
386    /// `send_close_notify`, and `write_tls`. Most likely you will want to
387    /// call `write_tls` to send any alerts queued by the error and then
388    /// close the underlying connection.
389    ///
390    /// Success from this function comes with some sundry state data
391    /// about the connection.
392    ///
393    /// [`read_tls`]: Connection::read_tls
394    /// [`process_new_packets`]: Connection::process_new_packets
395    #[inline]
396    pub fn process_new_packets(&mut self) -> Result<IoState, Error> {
397        self.core
398            .process_new_packets(&mut self.deframer_buffer, &mut self.sendable_plaintext)
399    }
400
401    /// Derives key material from the agreed connection secrets.
402    ///
403    /// This function fills in `output` with `output.len()` bytes of key
404    /// material derived from the master session secret using `label`
405    /// and `context` for diversification. Ownership of the buffer is taken
406    /// by the function and returned via the Ok result to ensure no key
407    /// material leaks if the function fails.
408    ///
409    /// See RFC5705 for more details on what this does and is for.
410    ///
411    /// For TLS1.3 connections, this function does not use the
412    /// "early" exporter at any point.
413    ///
414    /// This function fails if called prior to the handshake completing;
415    /// check with [`CommonState::is_handshaking`] first.
416    ///
417    /// This function fails if `output.len()` is zero.
418    #[inline]
419    pub fn export_keying_material<T: AsMut<[u8]>>(
420        &self,
421        output: T,
422        label: &[u8],
423        context: Option<&[u8]>,
424    ) -> Result<T, Error> {
425        self.core
426            .export_keying_material(output, label, context)
427    }
428
429    /// Extract secrets, so they can be used when configuring kTLS, for example.
430    /// Should be used with care as it exposes secret key material.
431    pub fn dangerous_extract_secrets(self) -> Result<ExtractedSecrets, Error> {
432        if !self.enable_secret_extraction {
433            return Err(Error::General("Secret extraction is disabled".into()));
434        }
435
436        let st = self.core.state?;
437
438        let record_layer = self.core.common_state.record_layer;
439        let PartiallyExtractedSecrets { tx, rx } = st.extract_secrets()?;
440        Ok(ExtractedSecrets {
441            tx: (record_layer.write_seq(), tx),
442            rx: (record_layer.read_seq(), rx),
443        })
444    }
445
446    /// Sets a limit on the internal buffers used to buffer
447    /// unsent plaintext (prior to completing the TLS handshake)
448    /// and unsent TLS records.  This limit acts only on application
449    /// data written through [`Connection::writer`].
450    ///
451    /// By default the limit is 64KB.  The limit can be set
452    /// at any time, even if the current buffer use is higher.
453    ///
454    /// [`None`] means no limit applies, and will mean that written
455    /// data is buffered without bound -- it is up to the application
456    /// to appropriately schedule its plaintext and TLS writes to bound
457    /// memory usage.
458    ///
459    /// For illustration: `Some(1)` means a limit of one byte applies:
460    /// [`Connection::writer`] will accept only one byte, encrypt it and
461    /// add a TLS header.  Once this is sent via [`Connection::write_tls`],
462    /// another byte may be sent.
463    ///
464    /// # Internal write-direction buffering
465    /// rustls has two buffers whose size are bounded by this setting:
466    ///
467    /// ## Buffering of unsent plaintext data prior to handshake completion
468    ///
469    /// Calls to [`Connection::writer`] before or during the handshake
470    /// are buffered (up to the limit specified here).  Once the
471    /// handshake completes this data is encrypted and the resulting
472    /// TLS records are added to the outgoing buffer.
473    ///
474    /// ## Buffering of outgoing TLS records
475    ///
476    /// This buffer is used to store TLS records that rustls needs to
477    /// send to the peer.  It is used in these two circumstances:
478    ///
479    /// - by [`Connection::process_new_packets`] when a handshake or alert
480    ///   TLS record needs to be sent.
481    /// - by [`Connection::writer`] post-handshake: the plaintext is
482    ///   encrypted and the resulting TLS record is buffered.
483    ///
484    /// This buffer is emptied by [`Connection::write_tls`].
485    ///
486    /// [`Connection::writer`]: crate::Connection::writer
487    /// [`Connection::write_tls`]: crate::Connection::write_tls
488    /// [`Connection::process_new_packets`]: crate::Connection::process_new_packets
489    pub fn set_buffer_limit(&mut self, limit: Option<usize>) {
490        self.sendable_plaintext.set_limit(limit);
491        self.sendable_tls.set_limit(limit);
492    }
493}
494
495#[cfg(feature = "std")]
496impl<Data> ConnectionCommon<Data> {
497    /// Returns an object that allows reading plaintext.
498    pub fn reader(&mut self) -> Reader {
499        let common = &mut self.core.common_state;
500        Reader {
501            received_plaintext: &mut common.received_plaintext,
502            // Are we done? i.e., have we processed all received messages, and received a
503            // close_notify to indicate that no new messages will arrive?
504            peer_cleanly_closed: common.has_received_close_notify
505                && !self.deframer_buffer.has_pending(),
506            has_seen_eof: common.has_seen_eof,
507        }
508    }
509
510    /// Returns an object that allows writing plaintext.
511    pub fn writer(&mut self) -> Writer {
512        Writer::new(self)
513    }
514
515    /// This function uses `io` to complete any outstanding IO for
516    /// this connection.
517    ///
518    /// This is a convenience function which solely uses other parts
519    /// of the public API.
520    ///
521    /// What this means depends on the connection  state:
522    ///
523    /// - If the connection [`is_handshaking`], then IO is performed until
524    ///   the handshake is complete.
525    /// - Otherwise, if [`wants_write`] is true, [`write_tls`] is invoked
526    ///   until it is all written.
527    /// - Otherwise, if [`wants_read`] is true, [`read_tls`] is invoked
528    ///   once.
529    ///
530    /// The return value is the number of bytes read from and written
531    /// to `io`, respectively.
532    ///
533    /// This function will block if `io` blocks.
534    ///
535    /// Errors from TLS record handling (i.e., from [`process_new_packets`])
536    /// are wrapped in an `io::ErrorKind::InvalidData`-kind error.
537    ///
538    /// [`is_handshaking`]: CommonState::is_handshaking
539    /// [`wants_read`]: CommonState::wants_read
540    /// [`wants_write`]: CommonState::wants_write
541    /// [`write_tls`]: ConnectionCommon::write_tls
542    /// [`read_tls`]: ConnectionCommon::read_tls
543    /// [`process_new_packets`]: ConnectionCommon::process_new_packets
544    pub fn complete_io<T>(&mut self, io: &mut T) -> Result<(usize, usize), io::Error>
545    where
546        Self: Sized,
547        T: io::Read + io::Write,
548    {
549        let mut eof = false;
550        let mut wrlen = 0;
551        let mut rdlen = 0;
552
553        loop {
554            let until_handshaked = self.is_handshaking();
555
556            while self.wants_write() {
557                wrlen += self.write_tls(io)?;
558            }
559            io.flush()?;
560
561            if !until_handshaked && wrlen > 0 {
562                return Ok((rdlen, wrlen));
563            }
564
565            while !eof && self.wants_read() {
566                let read_size = match self.read_tls(io) {
567                    Ok(0) => {
568                        eof = true;
569                        Some(0)
570                    }
571                    Ok(n) => {
572                        rdlen += n;
573                        Some(n)
574                    }
575                    Err(ref err) if err.kind() == io::ErrorKind::Interrupted => None, // nothing to do
576                    Err(err) => return Err(err),
577                };
578                if read_size.is_some() {
579                    break;
580                }
581            }
582
583            match self.process_new_packets() {
584                Ok(_) => {}
585                Err(e) => {
586                    // In case we have an alert to send describing this error,
587                    // try a last-gasp write -- but don't predate the primary
588                    // error.
589                    let _ignored = self.write_tls(io);
590                    let _ignored = io.flush();
591
592                    return Err(io::Error::new(io::ErrorKind::InvalidData, e));
593                }
594            };
595
596            // if we're doing IO until handshaked, and we believe we've finished handshaking,
597            // but process_new_packets() has queued TLS data to send, loop around again to write
598            // the queued messages.
599            if until_handshaked && !self.is_handshaking() && self.wants_write() {
600                continue;
601            }
602
603            match (eof, until_handshaked, self.is_handshaking()) {
604                (_, true, false) => return Ok((rdlen, wrlen)),
605                (_, false, _) => return Ok((rdlen, wrlen)),
606                (true, true, true) => return Err(io::Error::from(io::ErrorKind::UnexpectedEof)),
607                (..) => {}
608            }
609        }
610    }
611
612    /// Extract the first handshake message.
613    ///
614    /// This is a shortcut to the `process_new_packets()` -> `process_msg()` ->
615    /// `process_handshake_messages()` path, specialized for the first handshake message.
616    pub(crate) fn first_handshake_message(&mut self) -> Result<Option<Message<'static>>, Error> {
617        let mut deframer_buffer = self.deframer_buffer.borrow();
618        let res = self
619            .core
620            .deframe(None, &mut deframer_buffer)
621            .map(|opt| opt.map(|pm| Message::try_from(pm).map(|m| m.into_owned())));
622        let discard = deframer_buffer.pending_discard();
623        self.deframer_buffer.discard(discard);
624
625        match res? {
626            Some(Ok(msg)) => Ok(Some(msg)),
627            Some(Err(err)) => Err(self.send_fatal_alert(AlertDescription::DecodeError, err)),
628            None => Ok(None),
629        }
630    }
631
632    pub(crate) fn replace_state(&mut self, new: Box<dyn State<Data>>) {
633        self.core.state = Ok(new);
634    }
635
636    /// Read TLS content from `rd` into the internal buffer.
637    ///
638    /// Due to the internal buffering, `rd` can supply TLS messages in arbitrary-sized chunks (like
639    /// a socket or pipe might).
640    ///
641    /// You should call [`process_new_packets()`] each time a call to this function succeeds in order
642    /// to empty the incoming TLS data buffer.
643    ///
644    /// This function returns `Ok(0)` when the underlying `rd` does so. This typically happens when
645    /// a socket is cleanly closed, or a file is at EOF. Errors may result from the IO done through
646    /// `rd`; additionally, errors of `ErrorKind::Other` are emitted to signal backpressure:
647    ///
648    /// * In order to empty the incoming TLS data buffer, you should call [`process_new_packets()`]
649    ///   each time a call to this function succeeds.
650    /// * In order to empty the incoming plaintext data buffer, you should empty it through
651    ///   the [`reader()`] after the call to [`process_new_packets()`].
652    ///
653    /// [`process_new_packets()`]: ConnectionCommon::process_new_packets
654    /// [`reader()`]: ConnectionCommon::reader
655    pub fn read_tls(&mut self, rd: &mut dyn io::Read) -> Result<usize, io::Error> {
656        if self.received_plaintext.is_full() {
657            return Err(io::Error::new(
658                io::ErrorKind::Other,
659                "received plaintext buffer full",
660            ));
661        }
662
663        let res = self
664            .core
665            .message_deframer
666            .read(rd, &mut self.deframer_buffer);
667        if let Ok(0) = res {
668            self.has_seen_eof = true;
669        }
670        res
671    }
672
673    /// Writes TLS messages to `wr`.
674    ///
675    /// On success, this function returns `Ok(n)` where `n` is a number of bytes written to `wr`
676    /// (after encoding and encryption).
677    ///
678    /// After this function returns, the connection buffer may not yet be fully flushed. The
679    /// [`CommonState::wants_write`] function can be used to check if the output buffer is empty.
680    pub fn write_tls(&mut self, wr: &mut dyn io::Write) -> Result<usize, io::Error> {
681        self.sendable_tls.write_to(wr)
682    }
683}
684
685impl<'a, Data> From<&'a mut ConnectionCommon<Data>> for Context<'a, Data> {
686    fn from(conn: &'a mut ConnectionCommon<Data>) -> Self {
687        Self {
688            common: &mut conn.core.common_state,
689            data: &mut conn.core.data,
690            sendable_plaintext: Some(&mut conn.sendable_plaintext),
691        }
692    }
693}
694
695impl<T> Deref for ConnectionCommon<T> {
696    type Target = CommonState;
697
698    fn deref(&self) -> &Self::Target {
699        &self.core.common_state
700    }
701}
702
703impl<T> DerefMut for ConnectionCommon<T> {
704    fn deref_mut(&mut self) -> &mut Self::Target {
705        &mut self.core.common_state
706    }
707}
708
709impl<Data> From<ConnectionCore<Data>> for ConnectionCommon<Data> {
710    fn from(core: ConnectionCore<Data>) -> Self {
711        Self {
712            core,
713            deframer_buffer: DeframerVecBuffer::default(),
714            sendable_plaintext: ChunkVecBuffer::new(Some(DEFAULT_BUFFER_LIMIT)),
715        }
716    }
717}
718
719/// Interface shared by unbuffered client and server connections.
720pub struct UnbufferedConnectionCommon<Data> {
721    pub(crate) core: ConnectionCore<Data>,
722    wants_write: bool,
723}
724
725impl<Data> From<ConnectionCore<Data>> for UnbufferedConnectionCommon<Data> {
726    fn from(core: ConnectionCore<Data>) -> Self {
727        Self {
728            core,
729            wants_write: false,
730        }
731    }
732}
733
734pub(crate) struct ConnectionCore<Data> {
735    pub(crate) state: Result<Box<dyn State<Data>>, Error>,
736    pub(crate) data: Data,
737    pub(crate) common_state: CommonState,
738    pub(crate) message_deframer: MessageDeframer,
739}
740
741impl<Data> ConnectionCore<Data> {
742    pub(crate) fn new(state: Box<dyn State<Data>>, data: Data, common_state: CommonState) -> Self {
743        Self {
744            state: Ok(state),
745            data,
746            common_state,
747            message_deframer: MessageDeframer::default(),
748        }
749    }
750
751    pub(crate) fn process_new_packets(
752        &mut self,
753        deframer_buffer: &mut DeframerVecBuffer,
754        sendable_plaintext: &mut ChunkVecBuffer,
755    ) -> Result<IoState, Error> {
756        let mut state = match mem::replace(&mut self.state, Err(Error::HandshakeNotComplete)) {
757            Ok(state) => state,
758            Err(e) => {
759                self.state = Err(e.clone());
760                return Err(e);
761            }
762        };
763
764        let mut discard = 0;
765        loop {
766            let mut borrowed_buffer = deframer_buffer.borrow();
767            borrowed_buffer.queue_discard(discard);
768
769            let res = self.deframe(Some(&*state), &mut borrowed_buffer);
770            discard = borrowed_buffer.pending_discard();
771
772            let opt_msg = match res {
773                Ok(opt_msg) => opt_msg,
774                Err(e) => {
775                    self.state = Err(e.clone());
776                    deframer_buffer.discard(discard);
777                    return Err(e);
778                }
779            };
780
781            let msg = match opt_msg {
782                Some(msg) => msg,
783                None => break,
784            };
785
786            match self.process_msg(msg, state, Some(sendable_plaintext)) {
787                Ok(new) => state = new,
788                Err(e) => {
789                    self.state = Err(e.clone());
790                    deframer_buffer.discard(discard);
791                    return Err(e);
792                }
793            }
794        }
795
796        deframer_buffer.discard(discard);
797        self.state = Ok(state);
798        Ok(self.common_state.current_io_state())
799    }
800
801    /// Pull a message out of the deframer and send any messages that need to be sent as a result.
802    fn deframe<'b>(
803        &mut self,
804        state: Option<&dyn State<Data>>,
805        deframer_buffer: &mut DeframerSliceBuffer<'b>,
806    ) -> Result<Option<InboundPlainMessage<'b>>, Error> {
807        match self.message_deframer.pop(
808            &mut self.common_state.record_layer,
809            self.common_state.negotiated_version,
810            deframer_buffer,
811        ) {
812            Ok(Some(Deframed {
813                want_close_before_decrypt,
814                aligned,
815                trial_decryption_finished,
816                message,
817            })) => {
818                if want_close_before_decrypt {
819                    self.common_state.send_close_notify();
820                }
821
822                if trial_decryption_finished {
823                    self.common_state
824                        .record_layer
825                        .finish_trial_decryption();
826                }
827
828                self.common_state.aligned_handshake = aligned;
829                Ok(Some(message))
830            }
831            Ok(None) => Ok(None),
832            Err(err @ Error::InvalidMessage(_)) => {
833                if self.common_state.is_quic() {
834                    self.common_state.quic.alert = Some(AlertDescription::DecodeError);
835                }
836
837                Err(if !self.common_state.is_quic() {
838                    self.common_state
839                        .send_fatal_alert(AlertDescription::DecodeError, err)
840                } else {
841                    err
842                })
843            }
844            Err(err @ Error::PeerSentOversizedRecord) => Err(self
845                .common_state
846                .send_fatal_alert(AlertDescription::RecordOverflow, err)),
847            Err(err @ Error::DecryptError) => {
848                if let Some(state) = state {
849                    state.handle_decrypt_error();
850                }
851                Err(self
852                    .common_state
853                    .send_fatal_alert(AlertDescription::BadRecordMac, err))
854            }
855            Err(e) => Err(e),
856        }
857    }
858
859    fn process_msg(
860        &mut self,
861        msg: InboundPlainMessage,
862        state: Box<dyn State<Data>>,
863        sendable_plaintext: Option<&mut ChunkVecBuffer>,
864    ) -> Result<Box<dyn State<Data>>, Error> {
865        // Drop CCS messages during handshake in TLS1.3
866        if msg.typ == ContentType::ChangeCipherSpec
867            && !self
868                .common_state
869                .may_receive_application_data
870            && self.common_state.is_tls13()
871        {
872            if !msg.is_valid_ccs()
873                || self.common_state.received_middlebox_ccs > TLS13_MAX_DROPPED_CCS
874            {
875                // "An implementation which receives any other change_cipher_spec value or
876                //  which receives a protected change_cipher_spec record MUST abort the
877                //  handshake with an "unexpected_message" alert."
878                return Err(self.common_state.send_fatal_alert(
879                    AlertDescription::UnexpectedMessage,
880                    PeerMisbehaved::IllegalMiddleboxChangeCipherSpec,
881                ));
882            } else {
883                self.common_state.received_middlebox_ccs += 1;
884                trace!("Dropping CCS");
885                return Ok(state);
886            }
887        }
888
889        // Now we can fully parse the message payload.
890        let msg = match Message::try_from(msg) {
891            Ok(msg) => msg,
892            Err(err) => {
893                return Err(self
894                    .common_state
895                    .send_fatal_alert(AlertDescription::DecodeError, err));
896            }
897        };
898
899        // For alerts, we have separate logic.
900        if let MessagePayload::Alert(alert) = &msg.payload {
901            self.common_state.process_alert(alert)?;
902            return Ok(state);
903        }
904
905        self.common_state
906            .process_main_protocol(msg, state, &mut self.data, sendable_plaintext)
907    }
908
909    pub(crate) fn export_keying_material<T: AsMut<[u8]>>(
910        &self,
911        mut output: T,
912        label: &[u8],
913        context: Option<&[u8]>,
914    ) -> Result<T, Error> {
915        if output.as_mut().is_empty() {
916            return Err(Error::General(
917                "export_keying_material with zero-length output".into(),
918            ));
919        }
920
921        match self.state.as_ref() {
922            Ok(st) => st
923                .export_keying_material(output.as_mut(), label, context)
924                .map(|_| output),
925            Err(e) => Err(e.clone()),
926        }
927    }
928}
929
930/// Data specific to the peer's side (client or server).
931pub trait SideData: Debug {}