Support passing values into dbg with the pipe operator

In order to desugar `dbg` in a pipeline we need to allow a bare `dbg`
node in desugaring and only report it as an error if the bare node
survives to the next step of canonicalization. This means we move the
error code out of `desugar_expr` and into `canonicalize_expr`. This is
much simpler to do now that these functions use the same `env` struct,
since previously we would have had to pass down extra args to
`canonicalize_expr`. Sharing the `env` struct means that we also don't
have to worry about calculating `line_info` more than once.
This commit is contained in:
Elias Mulhall 2024-09-03 22:27:45 -04:00
parent b515bfa77e
commit 19931ecd43
No known key found for this signature in database
GPG key ID: 8D1F3C219EAB45F2
10 changed files with 200 additions and 28 deletions

View file

@ -25,7 +25,7 @@ use roc_region::all::{Loc, Region};
fn new_op_call_expr<'a>(
env: &mut Env<'a>,
_scope: &mut Scope,
scope: &mut Scope,
left: &'a Loc<Expr<'a>>,
loc_op: Loc<BinOp>,
right: &'a Loc<Expr<'a>>,
@ -47,6 +47,7 @@ fn new_op_call_expr<'a>(
Apply(function, args, CalledVia::BinOp(Pizza))
}
Dbg => *desugar_dbg_expr(env, scope, left, region),
_ => {
// e.g. `1 |> (if b then (\a -> a) else (\c -> c))`
Apply(right, env.arena.alloc([left]), CalledVia::BinOp(Pizza))
@ -1020,14 +1021,8 @@ pub fn desugar_expr<'a>(
})
}
Dbg => {
env.problem(Problem::UnappliedDbg {
region: loc_expr.region,
});
env.arena.alloc(Loc {
value: *desugar_invalid_dbg_expr(env, scope, loc_expr.region),
region: loc_expr.region,
})
// Allow naked dbg, necessary for piping values into dbg with the `Pizza` binop
loc_expr
}
DbgStmt(condition, continuation) => {
let desugared_condition = &*env.arena.alloc(desugar_expr(env, scope, condition));
@ -1321,7 +1316,7 @@ fn desugar_dbg_expr<'a>(
/// Build a desugared `dbg {}` expression to act as a placeholder when the AST
/// is invalid.
fn desugar_invalid_dbg_expr<'a>(
pub fn desugar_invalid_dbg_expr<'a>(
env: &mut Env<'a>,
scope: &mut Scope,
outer_region: Region,

View file

@ -1209,8 +1209,20 @@ pub fn canonicalize_expr<'a>(
output,
)
}
ast::Expr::Dbg | ast::Expr::DbgStmt(_, _) => {
internal_error!("Dbg should have been desugared by now")
ast::Expr::Dbg => {
// Dbg was not desugared as either part of an `Apply` or a `Pizza` binop, so it's
// invalid.
env.problem(Problem::UnappliedDbg { region });
let invalid_dbg_expr = crate::desugar::desugar_invalid_dbg_expr(env, scope, region);
let (loc_expr, output) =
canonicalize_expr(env, var_store, scope, region, invalid_dbg_expr);
(loc_expr.value, output)
}
ast::Expr::DbgStmt(_, _) => {
internal_error!("DbgStmt should have been desugared by now")
}
ast::Expr::LowLevelDbg((source_location, source), message, continuation) => {
let mut output = Output::default();