pub(crate) use dfa::Dfa;
use httlib_huffman::EncoderError;
use std::fmt::Display;
use xbpf::libbpf;
mod dfa;
#[cfg(feature = "build")]
pub mod build;
#[cfg(feature = "h1")]
pub mod h1;
#[cfg(feature = "h2")]
pub mod h2;
#[derive(Debug, Clone, PartialEq, Eq, Hash)]
pub enum MessageBuffer {
Skb,
Msg,
DynPtr,
}
#[derive(Debug)]
pub enum Error {
MatchLimitExceeded(usize),
InvalidEncoding(EncoderError),
ParserExceedsStateLimit,
Bpf(libbpf::Error),
MalformedTableEntry(plain::Error),
}
impl std::error::Error for Error {
fn source(&self) -> Option<&(dyn std::error::Error + 'static)> {
match self {
Error::InvalidEncoding(err) => Some(err),
Error::Bpf(err) => Some(err),
Error::MatchLimitExceeded(_)
| Error::ParserExceedsStateLimit
| Error::MalformedTableEntry(_) => None,
}
}
}
impl From<EncoderError> for Error {
fn from(err: EncoderError) -> Error {
Error::InvalidEncoding(err)
}
}
impl From<libbpf::Error> for Error {
fn from(err: libbpf::Error) -> Error {
Error::Bpf(err)
}
}
impl From<plain::Error> for Error {
fn from(err: plain::Error) -> Error {
Error::MalformedTableEntry(err)
}
}
impl Display for Error {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
match self {
Error::MatchLimitExceeded(limit) => {
write!(f, "a parser captures at most {limit} ranges")
}
Error::InvalidEncoding(err) => {
write!(f, "the header name cannot be Huffman encoded: {err}")
}
Error::ParserExceedsStateLimit => {
write!(f, "the patterns do not fit into the parser program")
}
Error::Bpf(err) => write!(f, "the parser program cannot be loaded: {err}"),
Error::MalformedTableEntry(err) => {
write!(f, "the parser wrote a table entry back malformed: {err:?}")
}
}
}
}
#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)]
pub struct PseudoHeaderName(&'static str);
impl PseudoHeaderName {
pub const fn as_str(&self) -> &'static str {
self.0
}
}
impl AsRef<str> for PseudoHeaderName {
fn as_ref(&self) -> &str {
self.0
}
}
impl AsRef<[u8]> for PseudoHeaderName {
fn as_ref(&self) -> &[u8] {
self.0.as_bytes()
}
}
pub mod pseudo_header {
use super::PseudoHeaderName;
pub const METHOD: PseudoHeaderName = PseudoHeaderName(":method");
pub const PATH: PseudoHeaderName = PseudoHeaderName(":path");
pub const STATUS: PseudoHeaderName = PseudoHeaderName(":status");
pub const AUTHORITY: PseudoHeaderName = PseudoHeaderName(":authority");
pub const SCHEME: PseudoHeaderName = PseudoHeaderName(":scheme");
}
#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)]
pub(crate) struct StateId(u16);
#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)]
pub struct MatchId(u8);
impl From<MatchId> for u8 {
fn from(id: MatchId) -> u8 {
id.0
}
}