use macros
This commit is contained in:
parent
043feadd71
commit
f6b193f69e
4 changed files with 44 additions and 61 deletions
7
imap/src/proto/macros.rs
Normal file
7
imap/src/proto/macros.rs
Normal file
|
@ -0,0 +1,7 @@
|
||||||
|
macro_rules! rule {
|
||||||
|
($vis:vis $name:ident : $ret:ty => $expr:expr) => {
|
||||||
|
$vis fn $name(i: &[u8]) -> nom::IResult<&[u8], $ret> {
|
||||||
|
$expr(i)
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
|
@ -1,5 +1,8 @@
|
||||||
#![allow(non_snake_case, dead_code)]
|
#![allow(non_snake_case, dead_code)]
|
||||||
|
|
||||||
|
#[macro_use]
|
||||||
|
mod macros;
|
||||||
|
|
||||||
// data types
|
// data types
|
||||||
pub mod response;
|
pub mod response;
|
||||||
|
|
||||||
|
|
|
@ -1,69 +1,37 @@
|
||||||
//! Grammar from https://tools.ietf.org/html/rfc2234#section-6.1
|
//! Grammar from https://tools.ietf.org/html/rfc2234#section-6.1
|
||||||
|
|
||||||
use nom::{branch::alt, character::streaming::anychar, multi::many0, sequence::pair, IResult};
|
use nom::{branch::alt, character::streaming::anychar, multi::many0, sequence::pair};
|
||||||
|
|
||||||
use super::parsers::{byte, satisfy, skip};
|
use super::parsers::{byte, satisfy, skip};
|
||||||
|
|
||||||
pub fn ALPHA(i: &[u8]) -> IResult<&[u8], u8> {
|
rule!(pub ALPHA : u8 => satisfy(|c| (c >= b'a' && c <= b'z') || (c >= b'A' && c <= b'Z')));
|
||||||
satisfy(|c| (c >= b'a' && c <= b'z') || (c >= b'A' && c <= b'Z'))(i)
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn BIT(i: &[u8]) -> IResult<&[u8], u8> {
|
rule!(pub BIT : u8 => satisfy(|c| c == b'0' || c == b'1'));
|
||||||
satisfy(|c| c == b'0' || c == b'1')(i)
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn CHAR(i: &[u8]) -> IResult<&[u8], u8> {
|
rule!(pub CHAR : u8 => satisfy(|c| c != b'\0'));
|
||||||
satisfy(|c| c != b'\0')(i)
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn CR(i: &[u8]) -> IResult<&[u8], u8> {
|
rule!(pub CR : u8 => byte(b'\x0d'));
|
||||||
byte(b'\x0d')(i)
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn CRLF(i: &[u8]) -> IResult<&[u8], (u8, u8)> {
|
rule!(pub CRLF : (u8, u8) => pair(CR, LF));
|
||||||
pair(CR, LF)(i)
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn CTL(i: &[u8]) -> IResult<&[u8], u8> {
|
rule!(pub CTL : u8 => satisfy(|c| c <= b'\x1f' || c == b'\x7f'));
|
||||||
satisfy(|c| c <= b'\x1f' || c == b'\x7f')(i)
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn DIGIT(i: &[u8]) -> IResult<&[u8], u8> {
|
rule!(pub DIGIT : u8 => satisfy(|c| c >= b'\x30' && c <= b'\x39'));
|
||||||
satisfy(|c| c >= b'\x30' && c <= b'\x39')(i)
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn DQUOTE(i: &[u8]) -> IResult<&[u8], u8> {
|
rule!(pub DQUOTE : u8 => byte(b'\x22'));
|
||||||
byte(b'\x22')(i)
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn HEXDIG(i: &[u8]) -> IResult<&[u8], u8> {
|
rule!(pub HEXDIG : u8 => alt((DIGIT, satisfy(|c| c >= b'A' && c <= b'F'))));
|
||||||
alt((DIGIT, satisfy(|c| c >= b'A' && c <= b'F')))(i)
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn HTAB(i: &[u8]) -> IResult<&[u8], u8> {
|
rule!(pub HTAB : u8 => byte(b'\x09'));
|
||||||
byte(b'\x09')(i)
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn LF(i: &[u8]) -> IResult<&[u8], u8> {
|
rule!(pub LF : u8 => byte(b'\x0a'));
|
||||||
byte(b'\x0a')(i)
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn LWSP(i: &[u8]) -> IResult<&[u8], ()> {
|
rule!(pub LWSP : () => skip(many0(alt((skip(WSP), skip(pair(CRLF, WSP)))))));
|
||||||
skip(many0(alt((skip(WSP), skip(pair(CRLF, WSP))))))(i)
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn OCTET(i: &[u8]) -> IResult<&[u8], char> {
|
rule!(pub OCTET : char => anychar);
|
||||||
anychar(i)
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn SP(i: &[u8]) -> IResult<&[u8], u8> {
|
rule!(pub SP : u8 => byte(b'\x20'));
|
||||||
byte(b'\x20')(i)
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn VCHAR(i: &[u8]) -> IResult<&[u8], u8> {
|
rule!(pub VCHAR : u8 => satisfy(|c| c >= b'\x21' && c <= b'\x7e'));
|
||||||
satisfy(|c| c >= b'\x21' && c <= b'\x7e')(i)
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn WSP(i: &[u8]) -> IResult<&[u8], u8> {
|
rule!(pub WSP : u8 => alt((SP, HTAB)));
|
||||||
alt((SP, HTAB))(i)
|
|
||||||
}
|
|
||||||
|
|
|
@ -11,6 +11,17 @@ use nom::{
|
||||||
};
|
};
|
||||||
|
|
||||||
use super::rfc2234::{CRLF, DIGIT, DQUOTE};
|
use super::rfc2234::{CRLF, DIGIT, DQUOTE};
|
||||||
|
use super::parsers::byte;
|
||||||
|
|
||||||
|
rule!(pub astring : Vec<u8> => alt((many1(ASTRING_CHAR), string)));
|
||||||
|
|
||||||
|
rule!(pub ASTRING_CHAR : u8 => alt((ATOM_CHAR, resp_specials)));
|
||||||
|
|
||||||
|
rule!(pub atom : Vec<u8> => many1(ATOM_CHAR));
|
||||||
|
|
||||||
|
pub fn ATOM_CHAR(i: &[u8]) -> IResult<&[u8], u8> {
|
||||||
|
todo!()
|
||||||
|
}
|
||||||
|
|
||||||
/// literal = "{" number "}" CRLF *CHAR8
|
/// literal = "{" number "}" CRLF *CHAR8
|
||||||
/// ; Number represents the number of CHAR8s
|
/// ; Number represents the number of CHAR8s
|
||||||
|
@ -29,13 +40,9 @@ fn test_literal() {
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn nil(i: &[u8]) -> IResult<&[u8], &[u8]> {
|
rule!(pub nil : &[u8] => tag_no_case("NIL"));
|
||||||
tag_no_case("NIL")(i)
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn nstring(i: &[u8]) -> IResult<&[u8], Option<Vec<u8>>> {
|
rule!(pub nstring : Option<Vec<u8>> => alt((map(string, Some), map(nil, |_| None))));
|
||||||
alt((map(string, Some), map(nil, |_| None)))(i)
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn number(i: &[u8]) -> IResult<&[u8], u32> {
|
pub fn number(i: &[u8]) -> IResult<&[u8], u32> {
|
||||||
map_res(map_res(many1(DIGIT), String::from_utf8), |s| {
|
map_res(map_res(many1(DIGIT), String::from_utf8), |s| {
|
||||||
|
@ -43,17 +50,15 @@ pub fn number(i: &[u8]) -> IResult<&[u8], u32> {
|
||||||
})(i)
|
})(i)
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn quoted(i: &[u8]) -> IResult<&[u8], Vec<u8>> {
|
rule!(pub quoted : Vec<u8> => delimited(DQUOTE, many0(QUOTED_CHAR), DQUOTE));
|
||||||
delimited(DQUOTE, many0(QUOTED_CHAR), DQUOTE)(i)
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn QUOTED_CHAR(i: &[u8]) -> IResult<&[u8], u8> {
|
pub fn QUOTED_CHAR(i: &[u8]) -> IResult<&[u8], u8> {
|
||||||
todo!()
|
todo!()
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn string(i: &[u8]) -> IResult<&[u8], Vec<u8>> {
|
rule!(pub resp_specials : u8 => byte(b']'));
|
||||||
alt((quoted, literal))(i)
|
|
||||||
}
|
rule!(pub string : Vec<u8> => alt((quoted, literal)));
|
||||||
|
|
||||||
pub fn TEXT_CHAR(i: &[u8]) -> IResult<&[u8], u8> {
|
pub fn TEXT_CHAR(i: &[u8]) -> IResult<&[u8], u8> {
|
||||||
todo!()
|
todo!()
|
||||||
|
|
Loading…
Reference in a new issue