mirror of
https://github.com/Noratrieb/dilaria.git
synced 2026-01-14 17:35:03 +01:00
add assignments
This commit is contained in:
parent
63c9d5300c
commit
0b79d4500d
3 changed files with 78 additions and 8 deletions
|
|
@ -13,13 +13,13 @@
|
||||||
| <break-stmt>
|
| <break-stmt>
|
||||||
| <return-stmt>
|
| <return-stmt>
|
||||||
| <block>
|
| <block>
|
||||||
| <expression-statement>
|
|
||||||
|
|
||||||
|
|
||||||
<declaration> ::= "let" <IDENT> "=" <expression> ";"
|
<declaration> ::= "let" <IDENT> "=" <expression> ";"
|
||||||
|
|
||||||
|
|
||||||
<assignment> ::= { call "." } <IDENT> "=" <expression> ";"
|
<assignment> ::= { call "." } <IDENT> "=" <expression> ";"
|
||||||
|
| <expression> ";"
|
||||||
|
|
||||||
|
|
||||||
<fn-decl> ::= "fn" <IDENT> <fn-args> <block>
|
<fn-decl> ::= "fn" <IDENT> <fn-args> <block>
|
||||||
|
|
|
||||||
|
|
@ -75,9 +75,8 @@ impl<'code> Parser<'code> {
|
||||||
TokenType::Return => self.return_stmt(),
|
TokenType::Return => self.return_stmt(),
|
||||||
TokenType::BraceO => Ok(Stmt::Block(self.block()?)),
|
TokenType::BraceO => Ok(Stmt::Block(self.block()?)),
|
||||||
_ => {
|
_ => {
|
||||||
let expr = self.expression()?;
|
let stmt = self.assignment()?;
|
||||||
self.expect(TokenType::Semi)?;
|
Ok(stmt)
|
||||||
Ok(Stmt::Expr(expr))
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -95,10 +94,6 @@ impl<'code> Parser<'code> {
|
||||||
}))
|
}))
|
||||||
}
|
}
|
||||||
|
|
||||||
fn assignment(&mut self) -> ParseResult<'code, Stmt> {
|
|
||||||
todo!("oh god no")
|
|
||||||
}
|
|
||||||
|
|
||||||
fn fn_decl(&mut self) -> ParseResult<'code, Stmt> {
|
fn fn_decl(&mut self) -> ParseResult<'code, Stmt> {
|
||||||
let keyword_span = self.expect(TokenType::Fn)?.span;
|
let keyword_span = self.expect(TokenType::Fn)?.span;
|
||||||
let name = self.ident()?;
|
let name = self.ident()?;
|
||||||
|
|
@ -215,6 +210,24 @@ impl<'code> Parser<'code> {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn assignment(&mut self) -> ParseResult<'code, Stmt> {
|
||||||
|
let expr = self.expression()?;
|
||||||
|
|
||||||
|
if let Some(TokenType::Equal) = self.peek_kind() {
|
||||||
|
let _ = self.expect(TokenType::Equal)?;
|
||||||
|
let init = self.expression()?;
|
||||||
|
let semi_span = self.expect(TokenType::Semi)?.span;
|
||||||
|
Ok(Stmt::Assignment(Assignment {
|
||||||
|
span: expr.span().extend(semi_span),
|
||||||
|
lhs: expr,
|
||||||
|
rhs: init,
|
||||||
|
}))
|
||||||
|
} else {
|
||||||
|
let _ = self.expect(TokenType::Semi)?;
|
||||||
|
Ok(Stmt::Expr(expr))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
fn expression(&mut self) -> ParseResult<'code, Expr> {
|
fn expression(&mut self) -> ParseResult<'code, Expr> {
|
||||||
self.logical_or()
|
self.logical_or()
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -73,6 +73,63 @@ fn test_number_literal<F: FnOnce(Vec<Token<'_>>) -> Expr>(parser: F) {
|
||||||
assert_eq!(num_lit(10.0), unary);
|
assert_eq!(num_lit(10.0), unary);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
mod assignment {
|
||||||
|
use super::prelude::*;
|
||||||
|
|
||||||
|
fn parse_assignment(tokens: Vec<Token>) -> Stmt {
|
||||||
|
let mut parser = parser(tokens);
|
||||||
|
parser.assignment().unwrap()
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn simple() {
|
||||||
|
let tokens = [Ident("hugo"), Equal, Number(10.0), Semi].map(token).into();
|
||||||
|
let ast = parse_assignment(tokens);
|
||||||
|
assert_eq!(
|
||||||
|
Stmt::Assignment(Assignment {
|
||||||
|
span: Default::default(),
|
||||||
|
lhs: Expr::Ident(ident("hugo")),
|
||||||
|
rhs: num_lit(10.0)
|
||||||
|
}),
|
||||||
|
ast
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn call_expr() {
|
||||||
|
let tokens = [
|
||||||
|
Ident("hugo"),
|
||||||
|
Dot,
|
||||||
|
Ident("age"),
|
||||||
|
Equal,
|
||||||
|
Number(2021.0),
|
||||||
|
Minus,
|
||||||
|
Number(1986.0),
|
||||||
|
Semi,
|
||||||
|
]
|
||||||
|
.map(token)
|
||||||
|
.into();
|
||||||
|
let ast = parse_assignment(tokens);
|
||||||
|
assert_eq!(
|
||||||
|
Stmt::Assignment(Assignment {
|
||||||
|
span: Default::default(),
|
||||||
|
lhs: Expr::Call(Box::new(Call {
|
||||||
|
callee: Expr::Ident(ident("hugo")),
|
||||||
|
span: Default::default(),
|
||||||
|
kind: CallKind::Field(ident("age"))
|
||||||
|
})),
|
||||||
|
rhs: Expr::BinaryOp(Box::new(BinaryOp {
|
||||||
|
span: Default::default(),
|
||||||
|
lhs: num_lit(2021.0),
|
||||||
|
rhs: num_lit(1986.0),
|
||||||
|
kind: BinaryOpKind::Sub
|
||||||
|
}))
|
||||||
|
}),
|
||||||
|
ast
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
mod r#fn {
|
mod r#fn {
|
||||||
use super::prelude::*;
|
use super::prelude::*;
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue