Provided by: openssl_3.3.1-2ubuntu2_amd64 bug

NAME

       ossl-guide-quic-introduction - OpenSSL Guide: An introduction to QUIC in OpenSSL

INTRODUCTION

       This page will provide an introduction to some basic QUIC concepts and background and how
       it is used within OpenSSL. It assumes that you have a basic understanding of UDP/IP and
       sockets. It also assumes that you are familiar with some OpenSSL and TLS fundamentals (see
       ossl-guide-libraries-introduction(7) and ossl-guide-tls-introduction(7)).

WHAT IS QUIC?

       QUIC is a general purpose protocol for enabling applications to securely communicate over
       a network. It is defined in RFC9000 (see <https://datatracker.ietf.org/doc/rfc9000/>).
       QUIC integrates parts of the TLS protocol for connection establishment but independently
       protects packets.  It provides similar security guarantees to TLS such as confidentiality,
       integrity and authentication (see ossl-guide-tls-introduction(7)).

       QUIC delivers a number of advantages:

       Multiple streams
           It supports multiple streams of communication (see "QUIC STREAMS" below), allowing
           application protocols built on QUIC to create arbitrarily many bytestreams for
           communication between a client and server. This allows an application protocol to
           avoid problems where one packet of data is held up waiting on another packet being
           delivered (commonly referred to as "head-of-line blocking"). It also enables an
           application to open additional logical streams without requiring a round-trip exchange
           of packets between the client and server as is required when opening an additional
           TLS/TCP connection.

       HTTP/3
           Since QUIC is the basis of HTTP/3, support for QUIC also enables applications to use
           HTTP/3 using a suitable third-party library.

       Fast connection initiation
           Future versions of OpenSSL will offer support for 0-RTT connection initiation,
           allowing a connection to be initiated to a server and application data to be
           transmitted without any waiting time. This is similar to TLS 1.3's 0-RTT functionality
           but also avoids the round trip needed to open a TCP socket; thus, it is similar to a
           combination of TLS 1.3 0-RTT and TCP Fast Open.

       Connection migration
           Future versions of OpenSSL will offer support for connection migration, allowing
           connections to seamlessly survive IP address changes.

       Datagram based use cases
           Future versions of OpenSSL will offer support for the QUIC datagram extension,
           allowing support for both TLS and DTLS-style use cases on a single connection.

       Implemented as application library
           Because most QUIC implementations, including OpenSSL's implementation, are implemented
           as an application library rather than by an operating system, an application can gain
           the benefit of QUIC without needing to wait for an OS update to be deployed. Future
           evolutions and enhancements to the QUIC protocol can be delivered as quickly as an
           application can be updated without dependency on an OS update cadence.

       Multiplexing over a single UDP socket
           Because QUIC is UDP-based, it is possible to multiplex a QUIC connection on the same
           UDP socket as some other UDP-based protocols, such as RTP.

QUIC TIME BASED EVENTS

       A key difference between the TLS implementation and the QUIC implementation in OpenSSL is
       how time is handled. The QUIC protocol requires various actions to be performed on a
       regular basis regardless of whether application data is being transmitted or received.

       OpenSSL introduces a new function SSL_handle_events(3) that will automatically process any
       outstanding time based events that must be handled.  Alternatively calling any I/O
       function such as SSL_read_ex(3) or SSL_write_ex(3) will also process these events. There
       is also SSL_get_event_timeout(3) which tells an application the amount of time that
       remains until SSL_handle_events(3) (or any I/O function) must be called.

       Fortunately a blocking application that does not leave the QUIC connection idle, and is
       regularly calling I/O functions does not typically need to worry about this. However if
       you are developing a nonblocking application or one that may leave the QUIC connection
       idle for a period of time then you will need to arrange to call these functions.

       OpenSSL provides an optional "thread assisted mode" that will automatically create a
       background thread and will regularly call SSL_handle_events(3) in a thread safe manner.
       This provides a simple way for an application to satisfy the QUIC requirements for time
       based events without having to implement special logic to accomplish it.

QUIC AND TLS

       QUIC reuses parts of the TLS protocol in its implementation. Specifically the TLS
       handshake also exists in QUIC. The TLS handshake messages are wrapped up in QUIC protocol
       messages in order to send them to the peer. Once the TLS handshake is complete all
       application data is sent entirely using QUIC protocol messages without using TLS -
       although some TLS handshake messages may still be sent in some circumstances.

       This relationship between QUIC and TLS means that many of the API functions in OpenSSL
       that apply to TLS connections also apply to QUIC connections and applications can use them
       in exactly the same way. Some functions do not apply to QUIC at all, and others have
       altered semantics. You should refer to the documentation pages for each function for
       information on how it applies to QUIC.  Typically if QUIC is not mentioned in the manual
       pages then the functions apply to both TLS and QUIC.

QUIC STREAMS

       QUIC introduces the concept of "streams". A stream provides a reliable mechanism for
       sending and receiving application data between the endpoints. The bytes transmitted are
       guaranteed to be received in the same order they were sent without any loss of data or
       reordering of the bytes. A TLS application effectively has one bi-directional stream
       available to it per TLS connection. A QUIC application can have multiple uni-directional
       or bi-directional streams available to it for each connection.

       In OpenSSL an SSL object is used to represent both connections and streams.  A QUIC
       application creates an initial SSL object to represent the connection (known as the
       connection SSL object). Once the connection is complete additional SSL objects can be
       created to represent streams (known as stream SSL objects). Unless configured otherwise, a
       "default" stream is also associated with the connection SSL object so you can still write
       data and read data to/from it. Some OpenSSL API functions can only be used with connection
       SSL objects, and some can only be used with stream SSL objects.  Check the documentation
       for each function to confirm what type of SSL object can be used in any particular
       context. A connection SSL object that has a default stream attached to it can be used in
       contexts that require a connection SSL object or in contexts that require a stream SSL
       object.

SOCKETS AND BLOCKING

       TLS assumes "stream" type semantics for its underlying transport layer protocol (usually
       achieved by using TCP). However QUIC assumes "datagram" type semantics by using UDP. An
       OpenSSL application using QUIC is responsible for creating a BIO to represent the
       underlying transport layer. This BIO must support datagrams and is typically
       BIO_s_datagram(3), but other BIO choices are available.  See bio(7) for an introduction to
       OpenSSL's BIO concept.

       A significant difference between OpenSSL TLS applications and OpenSSL QUIC applications is
       the way that blocking is implemented. In TLS if your application expects blocking
       behaviour then you configure the underlying socket for blocking. Conversely if your
       application wants nonblocking behaviour then the underlying socket is configured to be
       nonblocking.

       With an OpenSSL QUIC application the underlying socket must always be configured to be
       nonblocking. Howevever the SSL object will, by default, still operate in blocking mode.
       So, from an application's perspective, calls to functions such as SSL_read_ex(3),
       SSL_write_ex(3) and other I/O functions will still block. OpenSSL itself provides that
       blocking capability for QUIC instead of the socket. If nonblocking behaviour is desired
       then the application must call SSL_set_blocking_mode(3).

FURTHER READING

       See ossl-guide-quic-client-block(7) to see an example of applying these concepts in order
       to write a simple blocking QUIC client.

SEE ALSO

       ossl-guide-introduction(7), ossl-guide-libraries-introduction(7),
       ossl-guide-libssl-introduction(7), ossl-guide-tls-introduction(7),
       ossl-guide-tls-client-block(7), ossl-guide-quic-client-block(7), bio(7)

COPYRIGHT

       Copyright 2023 The OpenSSL Project Authors. All Rights Reserved.

       Licensed under the Apache License 2.0 (the "License").  You may not use this file except
       in compliance with the License.  You can obtain a copy in the file LICENSE in the source
       distribution or at <https://www.openssl.org/source/license.html>.