use std::str::FromStr; use crate::ast; grammar; pub LiteralInt: ast::LiteralInt = { r"[0-9]+" => ast::LiteralInt{value: i64::from_str(<>).unwrap()} }; pub Identifier: ast::Identifier = { r"[A-Za-z][A-Za-z0-9_]*" => ast::Identifier{name: <>.to_string()} }; pub FunctionCall: ast::FunctionCall = { "(" > ")" => ast::FunctionCall{name:i, arguments: args} } pub Expression: Box = { "+" => Box::new(ast::Expression::Op(l, ast::Operator::Plus, r)), "-" => Box::new(ast::Expression::Op(l, ast::Operator::Minus, r)), Factor, } pub Factor: Box = { "*" => Box::new(ast::Expression::Op(l, ast::Operator::Mul, r)), "/" => Box::new(ast::Expression::Op(l, ast::Operator::Div, r)), Term, } pub Term: Box = { LiteralInt => Box::new(ast::Expression::LiteralInt(<>)), Identifier => Box::new(ast::Expression::Identifier(<>)), => Box::new(ast::Expression::FunctionCall(<>)), "(" ")", } pub Block: ast::Block = { "{" "}" => ast::Block{expression: e} } pub VariableDeclaration: ast::VariableDeclaration = { Identifier => ast::VariableDeclaration{name: <>} } pub Function: ast::Function = { "fn" "(" > ")" => ast::Function{name: n, arguments: args, block: b} } pub Module: ast::Module = { => ast::Module{functions: fs} } // From https://lalrpop.github.io/lalrpop/tutorial/006_macros.html // Comma seperated list of T with optional trailing comma Comma: Vec = { ",")*> => match e { None => v, Some(e) => { let mut v = v; v.push(e); v } } };