Parsing refactors
This commit is contained in:
parent
1b6a7021e7
commit
9a13848f80
@ -18,8 +18,7 @@ use nom::{
|
|||||||
use nom_locate::{position, LocatedSpan};
|
use nom_locate::{position, LocatedSpan};
|
||||||
|
|
||||||
use crate::identifier::{Id, IdStore};
|
use crate::identifier::{Id, IdStore};
|
||||||
|
use crate::parsing::StoreRef;
|
||||||
type StoreRef = Rc<RefCell<IdStore<ASTItem>>>;
|
|
||||||
|
|
||||||
pub type Span<'a> = LocatedSpan<&'a str, StoreRef>;
|
pub type Span<'a> = LocatedSpan<&'a str, StoreRef>;
|
||||||
type ParseResult<'a, O> = IResult<Span<'a>, O, VerboseError<Span<'a>>>;
|
type ParseResult<'a, O> = IResult<Span<'a>, O, VerboseError<Span<'a>>>;
|
||||||
@ -66,11 +65,6 @@ fn fresh_id(span: &Span) -> Id<ASTItem> {
|
|||||||
table_handle.fresh()
|
table_handle.fresh()
|
||||||
}
|
}
|
||||||
|
|
||||||
fn fresh_id_rc(store_ref: &StoreRef) -> Id<ASTItem> {
|
|
||||||
let mut table_handle = store_ref.borrow_mut();
|
|
||||||
table_handle.fresh()
|
|
||||||
}
|
|
||||||
|
|
||||||
fn tok<'a, O>(
|
fn tok<'a, O>(
|
||||||
input_parser: impl Parser<Span<'a>, O, VerboseError<Span<'a>>>,
|
input_parser: impl Parser<Span<'a>, O, VerboseError<Span<'a>>>,
|
||||||
) -> impl FnMut(Span<'a>) -> IResult<Span<'a>, O, VerboseError<Span<'a>>> {
|
) -> impl FnMut(Span<'a>) -> IResult<Span<'a>, O, VerboseError<Span<'a>>> {
|
||||||
@ -129,17 +123,16 @@ fn statement_delimiter(input: Span) -> ParseResult<()> {
|
|||||||
|
|
||||||
pub fn program(input: Span) -> ParseResult<AST> {
|
pub fn program(input: Span) -> ParseResult<AST> {
|
||||||
let id = fresh_id(&input);
|
let id = fresh_id(&input);
|
||||||
//TODO `rest` should be empty
|
|
||||||
let (rest, statements) = context(
|
let (rest, statements) = context(
|
||||||
"AST",
|
"AST",
|
||||||
terminated(
|
terminated(
|
||||||
map(
|
map(
|
||||||
tuple((
|
delimited(
|
||||||
many0(statement_delimiter),
|
many0(statement_delimiter),
|
||||||
separated_list0(many1(statement_delimiter), statement),
|
separated_list0(many1(statement_delimiter), statement),
|
||||||
many0(statement_delimiter),
|
many0(statement_delimiter),
|
||||||
)),
|
),
|
||||||
|(_, items, _)| items.into(),
|
|items| items.into(),
|
||||||
),
|
),
|
||||||
tok(eof),
|
tok(eof),
|
||||||
),
|
),
|
||||||
@ -470,12 +463,12 @@ fn prefix_op(input: Span) -> ParseResult<PrefixOp> {
|
|||||||
|
|
||||||
fn prefix_expr(allow_struct: bool) -> impl FnMut(Span) -> ParseResult<ExpressionKind> {
|
fn prefix_expr(allow_struct: bool) -> impl FnMut(Span) -> ParseResult<ExpressionKind> {
|
||||||
move |input: Span| {
|
move |input: Span| {
|
||||||
let handle = input.extra.clone();
|
let id = fresh_id(&input);
|
||||||
context(
|
context(
|
||||||
"prefix-expr",
|
"prefix-expr",
|
||||||
map(pair(opt(prefix_op), extended_expr(allow_struct)), move |(prefix, expr)| {
|
map(pair(opt(prefix_op), extended_expr(allow_struct)), move |(prefix, expr)| {
|
||||||
if let Some(prefix) = prefix {
|
if let Some(prefix) = prefix {
|
||||||
let expr = Expression::new(fresh_id_rc(&handle), expr);
|
let expr = Expression::new(id, expr);
|
||||||
ExpressionKind::PrefixExp(prefix, Box::new(expr))
|
ExpressionKind::PrefixExp(prefix, Box::new(expr))
|
||||||
} else {
|
} else {
|
||||||
expr
|
expr
|
||||||
@ -968,6 +961,7 @@ impl BinopSequence {
|
|||||||
#[cfg(test)]
|
#[cfg(test)]
|
||||||
mod test {
|
mod test {
|
||||||
use pretty_assertions::assert_eq;
|
use pretty_assertions::assert_eq;
|
||||||
|
|
||||||
use super::*;
|
use super::*;
|
||||||
|
|
||||||
macro_rules! span {
|
macro_rules! span {
|
||||||
|
@ -15,13 +15,15 @@ use crate::{
|
|||||||
identifier::{Id, IdStore},
|
identifier::{Id, IdStore},
|
||||||
};
|
};
|
||||||
|
|
||||||
|
pub(crate) type StoreRef = Rc<RefCell<IdStore<ASTItem>>>;
|
||||||
pub struct Parser {
|
pub struct Parser {
|
||||||
id_store: IdStore<ASTItem>,
|
id_store: StoreRef,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Parser {
|
impl Parser {
|
||||||
pub(crate) fn new() -> Self {
|
pub(crate) fn new() -> Self {
|
||||||
Self { id_store: IdStore::new() }
|
let id_store: IdStore<ASTItem> = IdStore::new();
|
||||||
|
Self { id_store: Rc::new(RefCell::new(id_store)) }
|
||||||
}
|
}
|
||||||
|
|
||||||
pub(crate) fn parse(&mut self, input: &str) -> Result<AST, ParseError> {
|
pub(crate) fn parse(&mut self, input: &str) -> Result<AST, ParseError> {
|
||||||
@ -29,14 +31,13 @@ impl Parser {
|
|||||||
}
|
}
|
||||||
|
|
||||||
pub(crate) fn parse_comb(&mut self, input: &str) -> Result<AST, ParseError> {
|
pub(crate) fn parse_comb(&mut self, input: &str) -> Result<AST, ParseError> {
|
||||||
let id_store: IdStore<ASTItem> = IdStore::new();
|
let span = Span::new_extra(input, self.id_store.clone());
|
||||||
let span = Span::new_extra(input, Rc::new(RefCell::new(id_store)));
|
|
||||||
let (rest, output) = combinator::program(span).map_err(|err| convert_err(input, err))?;
|
let (rest, output) = combinator::program(span).map_err(|err| convert_err(input, err))?;
|
||||||
|
|
||||||
if rest.fragment() != &"" {
|
if rest.fragment() != &"" {
|
||||||
return Err(ParseError {
|
return Err(ParseError {
|
||||||
location: Default::default(),
|
location: Default::default(),
|
||||||
msg: format!("BAD STATE remaining string: `{}`", rest.fragment()),
|
msg: format!("Bad parse state, remaining text: `{}`", rest.fragment()),
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -50,9 +51,7 @@ impl Parser {
|
|||||||
|
|
||||||
#[cfg(test)]
|
#[cfg(test)]
|
||||||
fn expression_comb(&mut self, input: &str) -> Result<Expression, ParseError> {
|
fn expression_comb(&mut self, input: &str) -> Result<Expression, ParseError> {
|
||||||
let id_store: IdStore<ASTItem> = IdStore::new();
|
let span = Span::new_extra(input, self.id_store.clone());
|
||||||
let span = Span::new_extra(input, Rc::new(RefCell::new(id_store)));
|
|
||||||
|
|
||||||
combinator::expression(span).map_err(|err| convert_err(input, err)).map(|(rest, output)| output)
|
combinator::expression(span).map_err(|err| convert_err(input, err)).map(|(rest, output)| output)
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -63,13 +62,12 @@ impl Parser {
|
|||||||
|
|
||||||
#[cfg(test)]
|
#[cfg(test)]
|
||||||
fn block_comb(&mut self, input: &str) -> Result<Block, ParseError> {
|
fn block_comb(&mut self, input: &str) -> Result<Block, ParseError> {
|
||||||
let id_store: IdStore<ASTItem> = IdStore::new();
|
let span = Span::new_extra(input, self.id_store.clone());
|
||||||
let span = Span::new_extra(input, Rc::new(RefCell::new(id_store)));
|
|
||||||
combinator::block(span).map_err(|err| convert_err(input, err)).map(|(_, output)| output)
|
combinator::block(span).map_err(|err| convert_err(input, err)).map(|(_, output)| output)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn fresh(&mut self) -> Id<ASTItem> {
|
fn fresh(&mut self) -> Id<ASTItem> {
|
||||||
self.id_store.fresh()
|
self.id_store.borrow_mut().fresh()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user