mirror of
https://github.com/n0-computer/noq.git
synced 2026-09-23 19:48:19 +00:00
H3: settings and errors documentation
This commit is contained in:
+43
-4
@@ -34,46 +34,60 @@ use std::io::ErrorKind;
|
||||
|
||||
use proto::ErrorCode;
|
||||
|
||||
/// A future that resolves when the handshake ends durinng a 0-RTT exchange
|
||||
pub type ZeroRttAccepted = quinn::ZeroRttAccepted;
|
||||
|
||||
/// General error enum for this crate
|
||||
#[derive(Debug, Error)]
|
||||
pub enum Error {
|
||||
/// Cannot make a new request, bescause the connection is closing
|
||||
#[error(display = "Connection is closing, resquest aborted")]
|
||||
Aborted,
|
||||
/// Protocol violation detected by the internal HTTP/3 protocol state machine
|
||||
#[error(display = "H3 protocol error: {:?}", _0)]
|
||||
Proto(proto::connection::Error),
|
||||
/// Error occurred at the `QUIC` level
|
||||
#[error(display = "QUIC protocol error: {}", _0)]
|
||||
Quic(quinn::ConnectionError),
|
||||
/// A `QUIC`-specific read error occurred
|
||||
#[error(display = "QUIC read error: {}", _0)]
|
||||
Read(ReadError),
|
||||
/// A `QUIC`-specific write error occurred
|
||||
#[error(display = "QUIC write error: {}", _0)]
|
||||
Write(WriteError),
|
||||
/// Programming error within the crate's code
|
||||
#[error(display = "Internal error: {}", _0)]
|
||||
Internal(String),
|
||||
/// The peer's behavior was detected as incorrect or malicious
|
||||
#[error(display = "Incorrect peer behavior: {}", _0)]
|
||||
Peer(String),
|
||||
/// The peer tried to open an unidirectional stream with an unknown type code
|
||||
#[error(display = "unknown stream type {}", _0)]
|
||||
UnknownStream(u64),
|
||||
/// An IO error occurred
|
||||
#[error(display = "IO error: {}", _0)]
|
||||
Io(std::io::Error),
|
||||
/// An overflow occurred into the `QPACK` decoder
|
||||
#[error(display = "Overflow max data size")]
|
||||
Overflow,
|
||||
/// A future has been polled after it was already finished
|
||||
#[error(display = "Polled after finished")]
|
||||
Poll,
|
||||
/// The peer issued an HTTP/3 error code and an optional text description
|
||||
#[error(display = "Http error: {:?}", _0)]
|
||||
Http(HttpError, Option<String>),
|
||||
}
|
||||
|
||||
impl Error {
|
||||
pub fn peer<T: Into<String>>(msg: T) -> Self {
|
||||
pub(crate) fn peer<T: Into<String>>(msg: T) -> Self {
|
||||
Error::Peer(msg.into())
|
||||
}
|
||||
|
||||
pub fn internal<T: Into<String>>(msg: T) -> Self {
|
||||
pub(crate) fn internal<T: Into<String>>(msg: T) -> Self {
|
||||
Error::Internal(msg.into())
|
||||
}
|
||||
|
||||
pub fn try_into_quic(&self) -> Option<&quinn_proto::ConnectionError> {
|
||||
pub(crate) fn try_into_quic(&self) -> Option<&quinn_proto::ConnectionError> {
|
||||
match self {
|
||||
Error::Quic(e) => Some(e),
|
||||
Error::Write(quinn::WriteError::ConnectionClosed(e)) => Some(e),
|
||||
@@ -159,27 +173,52 @@ impl From<proto::headers::Error> for Error {
|
||||
}
|
||||
}
|
||||
|
||||
/// Errors defined by the HTTP/3 protocol
|
||||
///
|
||||
/// Read the [`HTTP/3 specification`] for more details.
|
||||
///
|
||||
/// [`HTTP/3 specification`]: https://quicwg.org/base-drafts/draft-ietf-quic-http.html#name-http-3-error-codes
|
||||
#[derive(Debug)]
|
||||
pub enum HttpError {
|
||||
/// This is used when the connection or stream needs to be closed, but there is no error to signal
|
||||
NoError,
|
||||
/// Peer violated protocol requirements in a way which doesn't match a more specific error code, or endpoint declines to use the more specific error code
|
||||
GeneralProtocolError,
|
||||
/// An internal error has occurred in the HTTP stack
|
||||
InternalError,
|
||||
/// The endpoint detected that its peer created a stream that it will not accept
|
||||
StreamCreationError,
|
||||
/// A stream required by the connection was closed or reset
|
||||
ClosedCriticalStream,
|
||||
/// A frame was received which was not permitted in the current state or on the current stream
|
||||
FrameUnexpected,
|
||||
/// A frame that fails to satisfy layout requirements or with an invalid size was received
|
||||
FrameError,
|
||||
/// The endpoint detected that its peer is exhibiting a behavior that might be generating excessive load
|
||||
ExcessiveLoad,
|
||||
/// A Stream ID or Push ID was used incorrectly, such as exceeding a limit, reducing a limit, or being reused
|
||||
IdError,
|
||||
/// An endpoint detected an error in the payload of a SETTINGS frame
|
||||
SettingsError,
|
||||
/// No SETTINGS frame was received at the beginning of the control stream
|
||||
MissingSettings,
|
||||
/// A server rejected a request without performing any application processing
|
||||
RequestRejected,
|
||||
/// The request or its response (including pushed response) is cancelled
|
||||
RequestCancelled,
|
||||
/// The client's stream terminated without containing a fully-formed request
|
||||
RequestIncomplete,
|
||||
/// The connection established in response to a CONNECT request was reset or abnormally closed
|
||||
ConnectError,
|
||||
/// The requested operation cannot be served over HTTP/3. The peer should retry over HTTP/1.1
|
||||
VersionFallback,
|
||||
/// Decompression of a header block failed
|
||||
QpackDecompressionFailed,
|
||||
/// Error on the encoder stream
|
||||
QpackEncoderStreamError,
|
||||
/// Error on the decoder stream
|
||||
QpackDecoderStreamError,
|
||||
/// Unknown error code
|
||||
Unknown(u32),
|
||||
}
|
||||
|
||||
@@ -210,7 +249,7 @@ impl From<ErrorCode> for HttpError {
|
||||
}
|
||||
}
|
||||
|
||||
/// TLS ALPN value for H3
|
||||
/// TLS ALPN value for the HTTP/3 protocol
|
||||
pub const ALPN: &[u8] = b"h3-27";
|
||||
|
||||
impl From<frame::Error> for (ErrorCode, String, Error) {
|
||||
|
||||
@@ -36,6 +36,14 @@ impl Codec for SettingId {
|
||||
}
|
||||
}
|
||||
|
||||
/// Settings for a HTTP/3 connection
|
||||
///
|
||||
/// The HTTP/3 protocol offers a few settings to configure limits and header encoding
|
||||
/// parameters of a connection.
|
||||
///
|
||||
/// See the [QPACK] specification for more details.
|
||||
///
|
||||
/// [QPACK]: https://quicwg.org/base-drafts/draft-ietf-quic-qpack.html
|
||||
#[derive(Clone, Debug)]
|
||||
pub struct Settings {
|
||||
max_header_list_size: u64,
|
||||
@@ -56,6 +64,8 @@ impl Default for Settings {
|
||||
|
||||
impl Settings {
|
||||
/// Create settings with quinn-h3's recomended values
|
||||
///
|
||||
/// Enables `QPACK`.
|
||||
pub fn new() -> Self {
|
||||
Self {
|
||||
max_header_list_size: 0,
|
||||
@@ -64,6 +74,9 @@ impl Settings {
|
||||
}
|
||||
}
|
||||
|
||||
/// The maximum number of entries in headers and trailers
|
||||
///
|
||||
/// `0` means infinity.
|
||||
pub fn max_header_list_size(&self) -> u64 {
|
||||
if self.max_header_list_size == 0 {
|
||||
return std::u64::MAX;
|
||||
@@ -71,14 +84,23 @@ impl Settings {
|
||||
self.max_header_list_size
|
||||
}
|
||||
|
||||
/// The maximum size for `QPACK` encoding dynamic table
|
||||
///
|
||||
/// `0` means `QPACK` is disabled.
|
||||
pub fn qpack_max_table_capacity(&self) -> u64 {
|
||||
self.qpack_max_table_capacity
|
||||
}
|
||||
|
||||
/// The maximum number of request waiting to be decoded with arriving encoder data
|
||||
///
|
||||
/// If `0`, the peer won't send any dynamically encoded headers.
|
||||
pub fn qpack_max_blocked_streams(&self) -> u64 {
|
||||
self.qpack_max_blocked_streams
|
||||
}
|
||||
|
||||
/// Set the maximum number of entries in headers and trailers
|
||||
///
|
||||
/// `0` means infinity.
|
||||
pub fn set_max_header_list_size(&mut self, value: u64) -> Result<&mut Self, InvalidValue> {
|
||||
if value > VarInt::MAX.into_inner() as u64 {
|
||||
return Err(InvalidValue(SettingId::QPACK_MAX_TABLE_CAPACITY, value));
|
||||
@@ -87,6 +109,9 @@ impl Settings {
|
||||
Ok(self)
|
||||
}
|
||||
|
||||
/// Set the maximum size for `QPACK` encoding dynamic table
|
||||
///
|
||||
/// If `0`, the peer won't send any dynamically encoded headers.
|
||||
pub fn set_qpack_max_blocked_streams(&mut self, value: u64) -> Result<&mut Self, InvalidValue> {
|
||||
if value > MAX_BLOCKED_STREAMS_MAX {
|
||||
return Err(InvalidValue(SettingId::QPACK_MAX_BLOCKED_STREAMS, value));
|
||||
@@ -95,6 +120,9 @@ impl Settings {
|
||||
Ok(self)
|
||||
}
|
||||
|
||||
/// Set the maximum number of request waiting to be decoded with arriving encoder data
|
||||
///
|
||||
/// Set this to `0` to disable `QPACK`.
|
||||
pub fn set_qpack_max_table_capacity(&mut self, value: u64) -> Result<&mut Self, InvalidValue> {
|
||||
if value > MAX_TABLE_CAPACITY_MAX {
|
||||
return Err(InvalidValue(SettingId::QPACK_MAX_TABLE_CAPACITY, value));
|
||||
|
||||
Reference in New Issue
Block a user