#[cfg(feature = "std")]
use std::error::Error;
use core::convert::Infallible;
use core::fmt::{self, Display, Formatter};
use core::iter::{self, Extend};
use core::marker::PhantomData;
use core::mem::{self, MaybeUninit};
use core::ptr;
use crate::slice::Slice;
#[derive(Debug, PartialEq, Eq, Clone, Hash)]
pub enum ParseError {
Reject,
Indeterminate, }
impl Display for ParseError {
fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result {
match self {
ParseError::Reject => write!(f, "Input rejected"),
ParseError::Indeterminate => {
write!(f, "Insufficent input to conclusively determine validity")
},
}
}
}
#[cfg(feature = "std")]
impl Error for ParseError {}
#[must_use = "parsers are lazy and do not do anything until consumed"]
pub trait Parse<T> {
type Output;
type Err;
fn parse(self, input: T) -> Result<(T, Self::Output), Self::Err>;
fn map<F, O>(self, func: F) -> Map<T, Self, F, O>
where F: Fn(Self::Output) -> O, Self: Sized {
Map { parser: self, func, _t: PhantomData }
}
fn map_err<F, E>(self, func: F) -> MapErr<T, Self, F, E>
where F: Fn(Self::Err) -> E, Self: Sized {
MapErr { parser: self, func, _t: PhantomData }
}
fn maybe(self) -> Maybe<T, Self>
where T: Clone, Self: Sized {
Maybe { parser: self, _t: PhantomData }
}
fn chain<I>(self, inner: I) -> Chain<T, Self, I>
where I: Parse<Self::Output, Err = Self::Err>, Self: Sized {
Chain { parser: self, inner_parser: inner, _t: PhantomData }
}
fn or<O>(self, other: O) -> Or<T, Self, O>
where T: Clone, O: Parse<T, Output = Self::Output, Err = Self::Err>, Self: Sized {
Or { left: self, right: other, _t: PhantomData }
}
fn and<O>(self, length_err: Self::Err, other: O) -> And<T, Self, O>
where T: Clone + Eq, O: Parse<T, Err = Self::Err>, Self: Sized {
And { left: self, right: other, length_err: length_err, _t: PhantomData }
}
fn fuse<O>(self, other: O) -> Fuse<T, Self, O>
where O: Parse<T, Err = Self::Err>, Self: Sized, {
Fuse { left: self, right: other, _t: PhantomData }
}
fn fuse_extend<O>(self, other: O) -> FuseExtend<T, Self, Self::Output, O>
where O: Parse<T, Err = Self::Err>, Self::Output: Extend<O::Output>, Self: Sized {
FuseExtend { left: self, right: other, _t: PhantomData }
}
fn repeat_const<const N: usize>(self) -> RepeatConst<T, Self, N>
where Self: Clone + Sized {
RepeatConst { parser: self, _t: PhantomData }
}
fn repeat_greedy<O>(self, default: O) -> RepeatGreedy<T, Self, O>
where T: Clone, O: Extend<Self::Output>, Self: Clone + Sized {
RepeatGreedy { parser: self, output: default, _t: PhantomData }
}
}
impl<T, F, R, E> Parse<T> for F
where F: Fn(T) -> Result<(T, R), E> {
type Err = E;
type Output = R;
fn parse(self, input: T) -> Result<(T, Self::Output), Self::Err> { self(input) }
}
#[derive(Debug, PartialEq, Eq, Clone, Hash, Default)]
#[must_use = "parsers are lazy and do not do anything until consumed"]
pub struct Empty;
impl<T: Slice<Output = T>> Parse<T> for Empty {
type Err = Infallible; type Output = T;
fn parse(self, input: T) -> Result<(T, Self::Output), Self::Err> {
Ok(input.split_at(input.len()).expect("slicing from [i..i] from to [..] must never fail"))
}
}
#[derive(Debug, PartialEq, Eq, Clone, Hash, Default)]
#[must_use = "parsers are lazy and do not do anything until consumed"]
pub struct Identity;
impl<T: Slice<Output = T>> Parse<T> for Identity {
type Err = Infallible; type Output = T;
fn parse(self, input: T) -> Result<(T, Self::Output), Self::Err> {
Ok(input.split_at(0).expect("slicing from [i..i] or from [..] must never fail"))
}
}
#[derive(Debug, PartialEq, Eq, Clone, Hash)]
#[must_use = "parsers are lazy and do not do anything until consumed"]
pub struct Match<T: Slice + Eq>(pub T);
impl<T: Slice<Output = T> + Eq> Parse<T> for Match<T> {
type Err = ParseError;
type Output = T::Output;
fn parse(self, input: T) -> Result<(T, Self::Output), Self::Err> {
if self.0.len() > input.len() {
Err(ParseError::Indeterminate)
} else {
input
.split_at(self.0.len())
.filter(|(matched, _)| *matched == self.0)
.map(|(matched, rest)| (rest, matched))
.ok_or(ParseError::Reject)
}
}
}
#[derive(Debug, PartialEq, Eq, Clone, Hash)]
#[must_use = "parsers are lazy and do not do anything until consumed"]
pub struct Map<T, P, F, O>
where P: Parse<T>, F: Fn(P::Output) -> O {
parser: P,
func: F,
_t: PhantomData<T>,
}
impl<T, P, F, O> Parse<T> for Map<T, P, F, O>
where P: Parse<T>, F: Fn(P::Output) -> O {
type Err = P::Err;
type Output = O;
fn parse(self, input: T) -> Result<(T, Self::Output), Self::Err> {
self.parser.parse(input).map(|(rest, output)| {
(rest, (self.func)(output))
})
}
}
#[derive(Debug, PartialEq, Eq, Clone, Hash)]
#[must_use = "parsers are lazy and do not do anything until consumed"]
pub struct MapErr<T, P, F, E>
where P: Parse<T>, F: Fn(P::Err) -> E {
parser: P,
func: F,
_t: PhantomData<T>,
}
impl<T, P, F, E> Parse<T> for MapErr<T, P, F, E>
where P: Parse<T>, F: Fn(P::Err) -> E {
type Err = E;
type Output = P::Output;
fn parse(self, input: T) -> Result<(T, Self::Output), Self::Err> {
self.parser.parse(input).map_err(|err| { (self.func)(err) })
}
}
#[derive(Debug, PartialEq, Eq, Clone, Hash)]
#[must_use = "parsers are lazy and do not do anything until consumed"]
pub struct Maybe<T, P>
where T: Clone, P: Parse<T> {
parser: P,
_t: PhantomData<T>,
}
impl<T, P> Maybe<T, P>
where T: Clone, P: Parse<T> {
pub fn unwrap_or(self, default: P::Output) ->
Map<T, Self, impl Clone + Fn(Option<P::Output>) -> P::Output, P::Output>
where P::Output: Clone {
self.map(move |option| option.unwrap_or(default.clone()))
}
}
impl<T, P> Parse<T> for Maybe<T, P>
where T: Clone, P: Parse<T> {
type Err = P::Err;
type Output = Option<P::Output>;
fn parse(self, input: T) -> Result<(T, Self::Output), Self::Err> {
match self.parser.parse(input.clone()) {
Ok((rest, output)) => Ok((rest, Some(output))),
Err(_) => Ok((input, None)),
}
}
}
#[derive(Debug, PartialEq, Eq, Clone, Hash)]
#[must_use = "parsers are lazy and do not do anything until consumed"]
pub struct Chain<T, P, I>
where P: Parse<T>, I: Parse<P::Output, Err = P::Err> {
parser: P,
inner_parser: I,
_t: PhantomData<T>,
}
impl<T, P, I> Parse<T> for Chain<T, P, I>
where P: Parse<T>, I: Parse<P::Output, Err = P::Err> + Clone {
type Err = P::Err;
type Output = I::Output;
fn parse(self, input: T) -> Result<(T, Self::Output), Self::Err> {
let (rest, res) = self.parser
.map(|output| self.inner_parser.clone().parse(output))
.parse(input)?;
let (_, output) = res?;
Ok((rest, output))
}
}
#[derive(Debug, PartialEq, Eq, Clone, Hash)]
#[must_use = "parsers are lazy and do not do anything until consumed"]
pub struct Or<T, L, R>
where T: Clone, L: Parse<T>, R: Parse<T, Output = L::Output, Err = L::Err> {
left: L,
right: R,
_t: PhantomData<T>,
}
impl<T, L, R> Parse<T> for Or<T, L, R>
where T: Clone, L: Parse<T>, R: Parse<T, Output = L::Output, Err = L::Err> {
type Err = L::Err;
type Output = L::Output;
fn parse(self, input: T) -> Result<(T, Self::Output), Self::Err> {
match self.left.parse(input.clone()) {
Ok(res) => Ok(res),
Err(_) => self.right.parse(input), }
}
}
#[derive(Debug, PartialEq, Eq, Clone, Hash)]
#[must_use = "parsers are lazy and do not do anything until consumed"]
pub struct And<T, L, R>
where T: Clone + Eq, L: Parse<T>, R: Parse<T, Err = L::Err> {
left: L,
right: R,
length_err: L::Err,
_t: PhantomData<T>,
}
impl<T, L, R> And<T, L, R>
where T: Clone + Eq, L: Parse<T>, R: Parse<T, Err = L::Err> {
pub fn first(self) -> Map<T, Self, impl Clone + Copy + Send + Sync + Fn((L::Output, R::Output)) -> L::Output, L::Output> {
self.map(|(out, _)| out)
}
pub fn second(self) -> Map<T, Self, impl Clone + Copy + Send + Sync + Fn((L::Output, R::Output)) -> R::Output, R::Output> {
self.map(|(_, out)| out)
}
}
impl<T, L, R> Parse<T> for And<T, L, R>
where T: Clone + Eq, L: Parse<T>, R: Parse<T, Err = L::Err> {
type Err = L::Err;
type Output = (L::Output, R::Output);
fn parse(self, input: T) -> Result<(T, Self::Output), Self::Err> {
let (left_rest, left_output) = self.left.parse(input.clone())?;
let (right_rest, right_output) = self.right.parse(input)?;
if left_rest == right_rest {
Ok((left_rest, (left_output, right_output)))
} else {
Err(self.length_err)
}
}
}
#[derive(Debug, PartialEq, Eq, Clone, Hash)]
#[must_use = "parsers are lazy and do not do anything until consumed"]
pub struct Fuse<T, L, R>
where L: Parse<T>, R: Parse<T, Err = L::Err> {
left: L,
right: R,
_t: PhantomData<T>,
}
impl<T, L, R> Fuse<T, L, R>
where L: Parse<T>, R: Parse<T, Err = L::Err> {
pub fn first(self) -> Map<T, Self, impl Clone + Copy + Send + Sync + Fn((L::Output, R::Output)) -> L::Output, L::Output> {
self.map(|(out, _)| out)
}
pub fn second(self) -> Map<T, Self, impl Clone + Copy + Send + Sync + Fn((L::Output, R::Output)) -> R::Output, R::Output> {
self.map(|(_, out)| out)
}
}
impl<T, L, R> Parse<T> for Fuse<T, L, R>
where L: Parse<T>, R: Parse<T, Err = L::Err> {
type Err = L::Err;
type Output = (L::Output, R::Output);
fn parse(self, input: T) -> Result<(T, Self::Output), Self::Err> {
let (rest, left_output) = self.left.parse(input)?;
let (rest, right_output) = self.right.parse(rest)?;
Ok((rest, (left_output, right_output)))
}
}
#[derive(Debug, PartialEq, Eq, Clone, Hash)]
#[must_use = "parsers are lazy and do not do anything until consumed"]
pub struct FuseExtend<T, L, LO, R>
where L: Parse<T, Output = LO>, R: Parse<T, Err = L::Err>, LO: Extend<R::Output> {
left: L,
right: R,
_t: PhantomData<T>,
}
impl<T, L, LO, R> Parse<T> for FuseExtend<T, L, LO, R>
where L: Parse<T, Output = LO>, R: Parse<T, Err = L::Err>, LO: Extend<R::Output> {
type Err = L::Err;
type Output = L::Output;
fn parse(self, input: T) -> Result<(T, Self::Output), Self::Err> {
let (rest, (mut left, right)) = self.left.fuse(self.right).parse(input)?;
left.extend(iter::once(right));
Ok((rest, left))
}
}
#[derive(Debug, PartialEq, Eq, Clone, Hash)]
#[must_use = "parsers are lazy and do not do anything until consumed"]
pub struct RepeatConst<T, P, const N: usize>
where P: Parse<T> + Clone {
parser: P,
_t: PhantomData<T>,
}
impl<T, P, const N: usize> Parse<T> for RepeatConst<T, P, N>
where P: Parse<T> + Clone {
type Err = P::Err;
type Output = [P::Output; N];
fn parse(self, input: T) -> Result<(T, Self::Output), Self::Err> {
let mut output: [MaybeUninit<P::Output>; N] = unsafe {
MaybeUninit::uninit().assume_init()
};
let mut rest = input;
for i in 0..N {
match self.parser.clone().parse(rest) {
Ok((new_rest, new_output)) => {
rest = new_rest;
output[i].write(new_output);
},
Err(error) => {
for item in &mut output[0..i] { unsafe { ptr::drop_in_place(item.as_mut_ptr()); }
}
return Err(error);
}
}
}
let output: [P::Output; N] = unsafe { mem::transmute_copy(&output) };
Ok((rest, output))
}
}
#[derive(Debug, PartialEq, Eq, Clone, Hash)]
#[must_use = "parsers are lazy and do not do anything until consumed"]
pub struct RepeatGreedy<T, P, O>
where T: Clone, P: Parse<T> + Clone, O: Extend<P::Output> {
parser: P,
output: O,
_t: PhantomData<T>,
}
impl<T, P, O> Parse<T> for RepeatGreedy<T, P, O>
where T: Clone, P: Parse<T> + Clone, O: Extend<P::Output> {
type Err = P::Err; type Output = O;
fn parse(mut self, input: T) -> Result<(T, Self::Output), Self::Err> {
let mut rest = input;
loop {
match self.parser.clone().parse(rest.clone()) {
Ok((new_rest, output)) => {
rest = new_rest;
self.output.extend(iter::once(output));
},
Err(_) => return Ok((rest, self.output)),
}
}
}
}
#[macro_export]
macro_rules! any_of {
($parser1:expr $(, $parser:expr )* $(,)? ) => {
{
use $crate::parse::Parse;
$parser1
$(
.or($parser)
)*
}
};
}
#[macro_export]
macro_rules! any_of_match {
( $($parser:expr),* $(,)? ) => {
any_of!(
$(
Match($parser),
)*
)
};
}
#[macro_export]
macro_rules! any_of_match_arr {
( $($parser:expr),* $(,)? ) => {
any_of!(
$(
Match(&[$parser][..]),
)*
)
};
}
#[cfg(test)]
mod test {
use super::*;
#[test]
fn slice() {
let slice = "asdfghjk";
for i in 0..slice.len() + 1 {
for j in 0..slice.len() + 1 {
assert_eq!(slice.slice(i..j), slice.get(i..j));
}
}
}
#[test]
fn split_at() {
let slice = "asdfghjk";
assert_eq!(Slice::split_at(&slice, 3), Some(("asd", "fghjk")));
}
#[test]
fn match_test() {
let val = "asdfg";
assert_eq!(val.parse_with(Match("asd")), Ok(("fg", "asd")));
}
#[test]
fn any_of() {
let parser = any_of!(Match("a"), Match("b"), Match("c").map(|_| "C"));
assert_eq!(parser.clone().parse(&"abcde"), Ok(("bcde", "a")));
assert_eq!(parser.clone().parse(&"cde"), Ok(("de", "C")));
assert_eq!(parser.parse(&"def"), Err(ParseError::Reject));
}
#[test]
fn any_of_match() {
let parser = any_of_match!("a", "b", "c", "d", "e", "f");
assert_eq!(parser.clone().parse("fedcba"), Ok(("edcba", "f")));
let parser = any_of_match_arr![2i32, 4i32, 6i32, 8i32, 0i32];
assert_eq!(parser.parse(&[2i32, 3, 4][..]), Ok((&[3, 4][..], &[2][..])));
}
}