From 87b9cb9b724f51604ef5c550ba4454cf57e2c228 Mon Sep 17 00:00:00 2001 From: Vlamonster Date: Sun, 26 Nov 2023 23:54:04 +0100 Subject: [PATCH 1/2] Use more explicit types in the grammar. i.e. `ExprParsed` and `DefParsed` --- compiler/src/passes/parse/grammar.lalrpop | 99 +++++++++---------- compiler/src/passes/validate/constrain/var.rs | 2 +- 2 files changed, 50 insertions(+), 51 deletions(-) diff --git a/compiler/src/passes/parse/grammar.lalrpop b/compiler/src/passes/parse/grammar.lalrpop index 94a70ed..0761c98 100644 --- a/compiler/src/passes/parse/grammar.lalrpop +++ b/compiler/src/passes/parse/grammar.lalrpop @@ -1,9 +1,8 @@ use crate::passes::parse::{ - BinaryOp, Def, Expr, Lit, Meta, Param, PrgParsed, Span, Type, TypeDef, UnaryOp, + BinaryOp, DefParsed, ExprParsed, Lit, Meta, Param, PrgParsed, Spanned, Type, TypeDef, UnaryOp, }; use crate::passes::validate::partial_type::PartialType; use functor_derive::Functor; -use crate::passes::parse::Spanned; grammar; @@ -93,20 +92,20 @@ pub Program: PrgParsed<'input> = { } } -Def: Def, Spanned<&'input str>, Spanned, Spanned<&'input str>, Lit<'input>, Span>>> = { - "struct" "{" ":" )>> "}" => Def::TypeDef { +Def: DefParsed<'input> = { + "struct" "{" ":" )>> "}" => DefParsed::TypeDef { sym, def: TypeDef::Struct { fields }, }, - "enum" "{" ":" )>> "}" => Def::TypeDef { + "enum" "{" ":" )>> "}" => DefParsed::TypeDef { sym, def: TypeDef::Enum { variants }, }, - "fn" "(" > ")" " )?> "{" > "}" => Def::Fn { + "fn" "(" > ")" " )?> "{" > "}" => DefParsed::Fn { sym, params, typ: typ.unwrap_or(Type::Unit), - bdy: bdy.fmap(|bdy| bdy.unwrap_or(Expr::Lit { val: Lit::Unit })), + bdy: bdy.fmap(|bdy| bdy.unwrap_or(ExprParsed::Lit { val: Lit::Unit })), }, } @@ -143,76 +142,76 @@ Type: Type> = { // Num/Bool/Ident Expr = ExprStmt; -ExprStmt: Expr, Spanned<&'input str>, Lit<'input>, Span> = { - "let" )?> "=" >> ";" > => Expr::Let { +ExprStmt: ExprParsed<'input> = { + "let" )?> "=" >> ";" > => ExprParsed::Let { sym, mutable: mutable.is_some(), typ, bnd: Box::new(bnd), - bdy: Box::new(bdy.fmap(|bdy| bdy.unwrap_or(Expr::Lit { val: Lit::Unit }))), + bdy: Box::new(bdy.fmap(|bdy| bdy.unwrap_or(ExprParsed::Lit { val: Lit::Unit }))), }, - > ";" > => Expr::Seq { + > ";" > => ExprParsed::Seq { stmt: Box::new(stmt), - cnt: Box::new(cnt.fmap(|cnt| cnt.unwrap_or(Expr::Lit { val: Lit::Unit }))), + cnt: Box::new(cnt.fmap(|cnt| cnt.unwrap_or(ExprParsed::Lit { val: Lit::Unit }))), }, ExprInStmt, } -ExprInStmt: Expr, Spanned<&'input str>, Lit<'input>, Span> = { - "=" >> => Expr::Assign { +ExprInStmt: ExprParsed<'input> = { + "=" >> => ExprParsed::Assign { sym, bnd: Box::new(bnd), }, - "if" >> "{" > "}" > "}")?> => Expr::If { + "if" >> "{" > "}" > "}")?> => ExprParsed::If { cnd: Box::new(cnd), thn: Box::new(thn), - els: Box::new(els.unwrap_or(Meta { meta: (l, r - l), inner: Expr::Lit { val: Lit::Unit }})), + els: Box::new(els.unwrap_or(Meta { meta: (l, r - l), inner: ExprParsed::Lit { val: Lit::Unit }})), }, - "loop" "{" > "}" => Expr::Loop { + "loop" "{" > "}" => ExprParsed::Loop { bdy: Box::new(bdy), }, // todo: the spans in this desugaring do not make a lot sense. - "while" >> "{" > "}" => Expr::Loop { + "while" >> "{" > "}" => ExprParsed::Loop { bdy: Box::new(Meta { meta: (l, r - l), - inner: Expr::If { + inner: ExprParsed::If { cnd: Box::new(cnd), thn: Box::new(bdy), els: Box::new(Meta { meta: (l, r - l), - inner: Expr::Seq { + inner: ExprParsed::Seq { stmt: Box::new(Meta { meta: (l, r - l), - inner: Expr::Break { bdy: Box::new(Meta { + inner: ExprParsed::Break { bdy: Box::new(Meta { meta: (l, r - l), - inner: Expr::Lit { val: Lit::Unit }, + inner: ExprParsed::Lit { val: Lit::Unit }, })}, }), cnt: Box::new(Meta { meta: (l, r - l), - inner: Expr::Lit { val: Lit::Unit }, + inner: ExprParsed::Lit { val: Lit::Unit }, }), }, }), }, }), }, - "switch" >> "{" "(" ")" "=>" > )>> "}" => Expr::Switch { + "switch" >> "{" "(" ")" "=>" > )>> "}" => ExprParsed::Switch { enm: Box::new(enm), arms: arms.into_iter().map(|(s1, s2, e)| (s1, s2, Box::new(e))).collect(), }, - "break" ?>> => Expr::Break { - bdy: Box::new(bdy.fmap(|bdy| bdy.unwrap_or(Expr::Lit { val: Lit::Unit }))), + "break" ?>> => ExprParsed::Break { + bdy: Box::new(bdy.fmap(|bdy| bdy.unwrap_or(ExprParsed::Lit { val: Lit::Unit }))), }, - "return" ?>> => Expr::Return { - bdy: Box::new(bdy.fmap(|bdy| bdy.unwrap_or(Expr::Lit { val: Lit::Unit }))), + "return" ?>> => ExprParsed::Return { + bdy: Box::new(bdy.fmap(|bdy| bdy.unwrap_or(ExprParsed::Lit { val: Lit::Unit }))), }, - "continue" => Expr::Continue, + "continue" => ExprParsed::Continue, ExprLogicalOr, } -BinaryOps: Expr, Spanned<&'input str>, Lit<'input>, Span> = { - >> > => Expr::BinaryOp { +BinaryOps: ExprParsed<'input> = { + >> > => ExprParsed::BinaryOp { op, exprs: [Box::new(e1), Box::new(e2)], }, @@ -251,53 +250,53 @@ UnaryOp: UnaryOp = { "!" => UnaryOp::Not, } -ExprUnary: Expr, Spanned<&'input str>, Lit<'input>, Span> = { - >> => Expr::UnaryOp { +ExprUnary: ExprParsed<'input> = { + >> => ExprParsed::UnaryOp { op, expr: Box::new(e), }, ExprAccess, } -ExprAccess: Expr, Spanned<&'input str>, Lit<'input>, Span> = { - >> "." => Expr::AccessField { +ExprAccess: ExprParsed<'input> = { + >> "." => ExprParsed::AccessField { strct: Box::new(strct), field, }, ExprCall, } -ExprCall: Expr, Spanned<&'input str>, Lit<'input>, Span> = { - >> "(" >> ")" => Expr::Apply { +ExprCall: ExprParsed<'input> = { + >> "(" >> ")" => ExprParsed::Apply { fun: Box::new(fun), args, }, ExprAtom, } -ExprAtom: Expr, Spanned<&'input str>, Lit<'input>, Span> = { - => Expr::Lit { +ExprAtom: ExprParsed<'input> = { + => ExprParsed::Lit { val: Lit::Int { val, typ: None, }, }, - => Expr::Lit { + => ExprParsed::Lit { val: Lit::Int { val: val.trim_end_matches("i64"), typ: Some(PartialType::I64), }, }, - => Expr::Lit { + => ExprParsed::Lit { val: Lit::Int { val: val.trim_end_matches("u64"), typ: Some(PartialType::U64), }, }, - => Expr::Lit { val: Lit::Bool { val } }, - "unit" => Expr::Lit { val: Lit::Unit }, - => Expr::Var { sym }, - "::" "(" > ")" => Expr::Variant { + => ExprParsed::Lit { val: Lit::Bool { val } }, + "unit" => ExprParsed::Lit { val: Lit::Unit }, + => ExprParsed::Var { sym }, + "::" "(" > ")" => ExprParsed::Variant { enum_sym, variant_sym, bdy: Box::new(bdy), @@ -306,19 +305,19 @@ ExprAtom: Expr, Spanned<&'input str>, Lit<'input>, Span> , } -Struct: Expr, Spanned<&'input str>, Lit<'input>, Span> = { - "{" > "}" => Expr::Struct { +Struct: ExprParsed<'input> = { + "{" > "}" => ExprParsed::Struct { sym, fields, }, } -StructArg : (Spanned<&'input str>, Spanned, Spanned<&'input str>, Lit<'input>, Span>>) = { +StructArg : (Spanned<&'input str>, Spanned>) = { ":" >, - => (sym.clone(), Meta { meta: (l, r - l), inner: Expr::Var { sym } }) + => (sym.clone(), Meta { meta: (l, r - l), inner: ExprParsed::Var { sym } }) } -Never: Expr, Spanned<&'input str>, Lit<'input>, Span> = {}; +Never: ExprParsed<'input> = {}; Ident: Spanned<&'input str> = Spanned; diff --git a/compiler/src/passes/validate/constrain/var.rs b/compiler/src/passes/validate/constrain/var.rs index ec01ce1..031c7d6 100644 --- a/compiler/src/passes/validate/constrain/var.rs +++ b/compiler/src/passes/validate/constrain/var.rs @@ -5,7 +5,7 @@ use crate::passes::validate::{CMeta, ExprConstrained}; use crate::utils::gen_sym::UniqueSym; pub fn constrain_var<'p>( - env: &mut Env<'_, 'p>, + env: &Env<'_, 'p>, span: Span, sym: Spanned>, ) -> Result>, TypeError> { From bc1c5a3f5e5384fb550381f974e4e07b96eea6c2 Mon Sep 17 00:00:00 2001 From: Vlamonster Date: Mon, 27 Nov 2023 00:06:04 +0100 Subject: [PATCH 2/2] Create file after compilation succeeds. --- compiler/src/lib.rs | 8 ++------ 1 file changed, 2 insertions(+), 6 deletions(-) diff --git a/compiler/src/lib.rs b/compiler/src/lib.rs index 83c0b50..8c4e8ce 100644 --- a/compiler/src/lib.rs +++ b/compiler/src/lib.rs @@ -1,19 +1,15 @@ #![allow(clippy::module_inception)] -extern crate core; - pub mod interpreter; pub mod passes; pub mod utils; use crate::passes::parse::parse::parse_program; -use miette::{NamedSource, Report}; +use miette::{IntoDiagnostic, NamedSource, Report}; use std::fs::File; use std::path::Path; pub fn compile(program: &str, filename: &str, output: &Path) -> miette::Result<()> { - let mut file = File::create(output).unwrap(); - let add_source = |error| Report::with_source_code(error, NamedSource::new(filename, program.to_string())); @@ -32,7 +28,7 @@ pub fn compile(program: &str, filename: &str, output: &Path) -> miette::Result<( .patch() .conclude() .emit() - .write(&mut file); + .write(&mut File::create(output).into_diagnostic()?); Ok(()) }