From 9a7b62ac22257efa7feea3437f43bdd63ea491f5 Mon Sep 17 00:00:00 2001 From: Luke Boswell Date: Sat, 4 May 2024 07:40:43 +1000 Subject: [PATCH] handle dbg when unwrapping suffixed ! --- crates/compiler/can/src/suffixed.rs | 45 +++++++++++++++++++++- crates/compiler/can/tests/test_suffixed.rs | 29 ++++++++++++++ crates/compiler/parse/src/ast.rs | 2 +- 3 files changed, 73 insertions(+), 3 deletions(-) diff --git a/crates/compiler/can/src/suffixed.rs b/crates/compiler/can/src/suffixed.rs index 5bf496aa67..cb23ebe280 100644 --- a/crates/compiler/can/src/suffixed.rs +++ b/crates/compiler/can/src/suffixed.rs @@ -122,11 +122,52 @@ pub fn unwrap_suffixed_expression<'a>( Expr::SpaceBefore(..) | Expr::SpaceAfter(..) => { internal_error!( "SpaceBefore and SpaceAfter should have been removed in desugar_expr" - ) + ); } Expr::BinOps(..) => { - internal_error!("BinOps should have been desugared in desugar_expr") + internal_error!("BinOps should have been desugared in desugar_expr"); + } + + Expr::LowLevelDbg(moduel, arg, rest) => { + if is_expr_suffixed(&arg.value) { + // we cannot unwrap a suffixed expression within dbg + // e.g. dbg (foo! "bar") + return Err(EUnwrapped::Malformed); + } + + match unwrap_suffixed_expression(arena, rest, maybe_def_pat) { + Ok(unwrapped_expr) => { + let new_dbg = arena.alloc(Loc::at( + loc_expr.region, + LowLevelDbg(moduel, arg, unwrapped_expr), + )); + return Ok(new_dbg); + } + Err(EUnwrapped::UnwrappedDefExpr(unwrapped_expr)) => { + let new_dbg = arena.alloc(Loc::at( + loc_expr.region, + LowLevelDbg(moduel, arg, unwrapped_expr), + )); + Err(EUnwrapped::UnwrappedDefExpr(new_dbg)) + } + Err(EUnwrapped::UnwrappedSubExpr { + sub_arg: unwrapped_expr, + sub_pat, + sub_new, + }) => { + let new_dbg = arena.alloc(Loc::at( + loc_expr.region, + LowLevelDbg(moduel, arg, unwrapped_expr), + )); + Err(EUnwrapped::UnwrappedSubExpr { + sub_arg: new_dbg, + sub_pat, + sub_new, + }) + } + Err(EUnwrapped::Malformed) => Err(EUnwrapped::Malformed), + } } // we only need to unwrap some expressions, leave the rest as is diff --git a/crates/compiler/can/tests/test_suffixed.rs b/crates/compiler/can/tests/test_suffixed.rs index 80688ee1d4..34adc0769e 100644 --- a/crates/compiler/can/tests/test_suffixed.rs +++ b/crates/compiler/can/tests/test_suffixed.rs @@ -775,6 +775,35 @@ mod suffixed_tests { r#"Defs { tags: [Index(2147483648)], regions: [@0-226], space_before: [Slice(start = 0, length = 0)], space_after: [Slice(start = 0, length = 0)], spaces: [], type_defs: [], value_defs: [Body(@0-4 Identifier { ident: "main" }, @32-43 Apply(@32-43 Var { module_name: "Task", ident: "await" }, [@32-43 Var { module_name: "Stdin", ident: "line" }, @32-43 Closure([@23-29 Identifier { ident: "result" }], @61-226 When(@66-72 Var { module_name: "", ident: "result" }, [WhenBranch { patterns: [@96-99 Tag("End")], value: @127-137 Apply(@127-134 Var { module_name: "Task", ident: "ok" }, [@135-137 Record([])], Space), guard: None }, WhenBranch { patterns: [@159-169 Apply(@159-164 Tag("Input"), [@165-169 Identifier { ident: "name" }])], value: @197-226 Apply(@197-226 Var { module_name: "Stdout", ident: "line" }, [@210-226 Str(Line([Plaintext("Hello, "), Interpolated(@220-224 Var { module_name: "", ident: "name" })]))], Space), guard: None }]))], BangSuffix))] }"#, ); } + + /* + main = + foo = getFoo! + dbg foo + bar foo + + main = + Task.await getFoo \foo -> + dbg foo + bar! foo + + main = + Task.await getFoo \foo -> + dbg foo + bar foo + */ + #[test] + fn dbg_simple() { + run_test( + r#" + main = + foo = getFoo! + dbg foo + bar! foo + "#, + r#"Defs { tags: [Index(2147483648)], regions: [@0-85], space_before: [Slice(start = 0, length = 0)], space_after: [Slice(start = 0, length = 0)], spaces: [], type_defs: [], value_defs: [Body(@0-4 Identifier { ident: "main" }, @29-36 Apply(@29-36 Var { module_name: "Task", ident: "await" }, [@29-36 Var { module_name: "", ident: "getFoo" }, @29-36 Closure([@23-26 Identifier { ident: "foo" }], @53-85 LowLevelDbg(("test.roc:4", " "), @57-60 Apply(@57-60 Var { module_name: "Inspect", ident: "toStr" }, [@57-60 Var { module_name: "", ident: "foo" }], Space), @77-85 Apply(@77-85 Var { module_name: "", ident: "bar" }, [@82-85 Var { module_name: "", ident: "foo" }], Space)))], BangSuffix))] }"#, + ); + } } #[cfg(test)] diff --git a/crates/compiler/parse/src/ast.rs b/crates/compiler/parse/src/ast.rs index 9d5f881a3f..970c0e0231 100644 --- a/crates/compiler/parse/src/ast.rs +++ b/crates/compiler/parse/src/ast.rs @@ -610,7 +610,7 @@ pub fn is_expr_suffixed(expr: &Expr) -> bool { Expr::Expect(a, b) | Expr::Dbg(a, b) => { is_expr_suffixed(&a.value) || is_expr_suffixed(&b.value) } - Expr::LowLevelDbg(_, _, _) => todo!(), + Expr::LowLevelDbg(_, a, b) => is_expr_suffixed(&a.value) || is_expr_suffixed(&b.value), Expr::UnaryOp(a, _) => is_expr_suffixed(&a.value), Expr::When(a, _) => is_expr_suffixed(&a.value), Expr::SpaceBefore(a, _) => is_expr_suffixed(a),