parser: small refactor around Invocations
TODO: merge Expression and Object, their distinction makes little sense
This commit is contained in:
parent
d17524a7d2
commit
599721de7c
|
@ -36,8 +36,8 @@ pub struct Entry {
|
|||
pub enum Object {
|
||||
Code {
|
||||
cfe: bool,
|
||||
data: Box<[Statement]>,
|
||||
ret: Option<Statement>,
|
||||
data: Box<[Expression]>,
|
||||
ret: Option<Box<Expression>>,
|
||||
},
|
||||
Module(Module),
|
||||
Alias(FullIdentifier),
|
||||
|
@ -58,22 +58,15 @@ pub struct Path {
|
|||
}
|
||||
|
||||
#[derive(Clone, Debug)]
|
||||
pub enum StmtArgs {
|
||||
Single(Box<Object>),
|
||||
Multi(BTreeMap<Box<[Atom]>, (Location, Object)>),
|
||||
}
|
||||
|
||||
impl Default for StmtArgs {
|
||||
#[inline]
|
||||
fn default() -> Self {
|
||||
StmtArgs::Multi(BTreeMap::new())
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Clone, Debug)]
|
||||
pub struct Statement {
|
||||
pub sel: FullIdentifier,
|
||||
pub args: StmtArgs,
|
||||
pub enum Expression {
|
||||
InvocationSingle {
|
||||
obj: Object,
|
||||
arg: Object,
|
||||
},
|
||||
InvocationMulti {
|
||||
obj: Object,
|
||||
args: BTreeMap<Box<[Atom]>, (Location, Object)>,
|
||||
},
|
||||
}
|
||||
|
||||
pub struct Error {
|
||||
|
@ -188,11 +181,11 @@ impl FullIdentifier {
|
|||
}
|
||||
}
|
||||
|
||||
impl Statement {
|
||||
impl Expression {
|
||||
fn parse_high(ctx: &mut ParserContext<'_>) -> Result<Self, Error> {
|
||||
let sel = FullIdentifier::parse_high(ctx)?;
|
||||
let obj = Object::parse_high(ctx)?;
|
||||
|
||||
let args = if let Some(&(_, Token::Comma)) = ctx.pklx.peek() {
|
||||
Ok(if let Some(&(_, Token::Comma)) = ctx.pklx.peek() {
|
||||
let mut args = BTreeMap::new();
|
||||
while ctx.maybe_eat_token(Token::Comma).is_some() {
|
||||
let Path { loc, idents } = Path::parse_high(ctx)?;
|
||||
|
@ -205,16 +198,20 @@ impl Statement {
|
|||
});
|
||||
}
|
||||
}
|
||||
StmtArgs::Multi(args)
|
||||
Expression::InvocationMulti { obj, args }
|
||||
} else if matches!(ctx.pklx.peek(), Some(&(_, Token::SemiColon)) | None) {
|
||||
// do nothing, there won't be an argument
|
||||
// this escape hatch is a bit ugly, idk...
|
||||
StmtArgs::default()
|
||||
Expression::InvocationMulti {
|
||||
obj,
|
||||
args: BTreeMap::new(),
|
||||
}
|
||||
} else {
|
||||
StmtArgs::Single(Box::new(Object::parse_high(ctx)?))
|
||||
};
|
||||
|
||||
Ok(Statement { sel, args })
|
||||
Expression::InvocationSingle {
|
||||
obj,
|
||||
arg: Object::parse_high(ctx)?,
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -235,11 +232,11 @@ impl Object {
|
|||
let mut codata = Vec::new();
|
||||
let mut ret = None;
|
||||
while ctx.maybe_eat_token(Token::CloseBrace).is_none() {
|
||||
let stmt = Statement::parse_high(ctx)?;
|
||||
let expr = Expression::parse_high(ctx)?;
|
||||
if ctx.maybe_eat_token(Token::SemiColon).is_some() {
|
||||
codata.push(stmt);
|
||||
codata.push(expr);
|
||||
} else {
|
||||
ret = Some(stmt);
|
||||
ret = Some(Box::new(expr));
|
||||
// we don't go back to the loop header, so do it here.
|
||||
ctx.expect_token(Token::CloseBrace, /* { */ "}")?;
|
||||
break;
|
||||
|
|
Loading…
Reference in New Issue