Merge branch 'feat/parser'

This commit is contained in:
2026-05-09 20:23:46 +08:00
2 changed files with 68 additions and 8 deletions
+1 -1
View File
@@ -1,4 +1,4 @@
pub mod types; pub mod types;
mod lexer; pub mod lexer;
pub mod parser; pub mod parser;
pub mod err; pub mod err;
+67 -7
View File
@@ -12,7 +12,7 @@ use crate::{
pub struct Parser { pub struct Parser {
tokens: Vec<Token>, tokens: Vec<Token>,
diagnostics: Diagnositics, pub diagnostics: Diagnositics,
pos: usize, pos: usize,
} }
#[derive(Debug, Clone, PartialEq, Eq)] #[derive(Debug, Clone, PartialEq, Eq)]
@@ -31,7 +31,9 @@ impl Parser {
pos: 0, pos: 0,
} }
} }
pub fn parse(&mut self) {} pub fn parse(&mut self) -> CompileUnit {
self.parse_compile_unit()
}
fn peek(&self) -> Option<&Token> { fn peek(&self) -> Option<&Token> {
self.tokens.get(self.pos) self.tokens.get(self.pos)
} }
@@ -366,10 +368,68 @@ impl Parser {
assert!(self.peek().is_some()); assert!(self.peek().is_some());
let token = self.next().unwrap().clone(); let token = self.next().unwrap().clone();
match token.value { match token.value {
TokenValue::Ident(name) => Some(Expr { TokenValue::Ident(name) => {
value: ExprValue::Var(name), if self
span: token.span, .peek()
}), .is_some_and(|t| matches!(t.value, TokenValue::LParen))
{
self.advance(1);
let mut args = vec![];
loop {
match self.peek() {
Some(t) if matches!(t.value, TokenValue::RParen) => {
let end_span = t.span;
self.advance(1);
return Some(Expr {
value: ExprValue::FuncCall(name, args),
span: Span::from_two(token.span, end_span),
});
}
Some(_) => {}
None => {
self.diagnostics.add_from_frontend_error(
ParseError::ExpectButEof("`)`"),
token.span,
);
return None;
}
}
args.push(self.parse_expr()?);
match self.peek() {
Some(t) if matches!(t.value, TokenValue::Comma) => {
self.advance(1);
}
Some(t) if matches!(t.value, TokenValue::RParen) => {
let end_span = t.span;
self.advance(1);
return Some(Expr {
value: ExprValue::FuncCall(name, args),
span: Span::from_two(token.span, end_span),
});
}
Some(_) => {
let token = self.next().unwrap().clone();
self.diagnostics.add_from_frontend_error(
ParseError::UnexpectedToken(token.value, "`,` or `)`"),
token.span,
);
return None;
}
None => {
self.diagnostics.add_from_frontend_error(
ParseError::ExpectButEof("`)`"),
token.span,
);
return None;
}
}
}
}
Some(Expr {
value: ExprValue::Var(name),
span: token.span,
})
},
TokenValue::IntLit(value) => Some(Expr { TokenValue::IntLit(value) => Some(Expr {
value: ExprValue::IntLit(value), value: ExprValue::IntLit(value),
span: token.span, span: token.span,
@@ -709,4 +769,4 @@ mod tests {
test_case("0-3,14-25"); test_case("0-3,14-25");
// test_case("0-3,14-25"); // test_case("0-3,14-25");
} }
} }