mirror of
https://github.com/roc-lang/roc.git
synced 2025-07-24 15:03:46 +00:00
can::Expr::ParamsVar for lookups with params
This commit is contained in:
parent
5aebb7b570
commit
1526fc4aee
7 changed files with 67 additions and 5 deletions
|
@ -288,6 +288,15 @@ fn deep_copy_expr_help<C: CopyEnv>(env: &mut C, copied: &mut Vec<Variable>, expr
|
|||
loc_elems: loc_elems.iter().map(|le| le.map(|e| go_help!(e))).collect(),
|
||||
},
|
||||
Var(sym, var) => Var(*sym, sub!(*var)),
|
||||
ParamsVar {
|
||||
symbol,
|
||||
params,
|
||||
var,
|
||||
} => ParamsVar {
|
||||
symbol: *symbol,
|
||||
params: *params,
|
||||
var: sub!(*var),
|
||||
},
|
||||
&AbilityMember(sym, specialization, specialization_var) => {
|
||||
AbilityMember(sym, specialization, sub!(specialization_var))
|
||||
}
|
||||
|
|
|
@ -206,7 +206,9 @@ fn expr<'a>(c: &Ctx, p: EPrec, f: &'a Arena<'a>, e: &'a Expr) -> DocBuilder<'a,
|
|||
.append("]")
|
||||
.group(),
|
||||
),
|
||||
Var(sym, _) | AbilityMember(sym, _, _) => pp_sym(c, f, *sym),
|
||||
Var(sym, _) | ParamsVar { symbol: sym, .. } | AbilityMember(sym, _, _) => {
|
||||
pp_sym(c, f, *sym)
|
||||
}
|
||||
When {
|
||||
loc_cond, branches, ..
|
||||
} => maybe_paren!(
|
||||
|
|
|
@ -17,7 +17,7 @@ use roc_error_macros::internal_error;
|
|||
use roc_module::called_via::CalledVia;
|
||||
use roc_module::ident::{ForeignSymbol, Lowercase, TagName};
|
||||
use roc_module::low_level::LowLevel;
|
||||
use roc_module::symbol::Symbol;
|
||||
use roc_module::symbol::{LookedupSymbol, Symbol};
|
||||
use roc_parse::ast::{self, Defs, PrecedenceConflict, StrLiteral};
|
||||
use roc_parse::ident::Accessor;
|
||||
use roc_parse::pattern::PatternType::*;
|
||||
|
@ -107,6 +107,12 @@ pub enum Expr {
|
|||
|
||||
// Lookups
|
||||
Var(Symbol, Variable),
|
||||
/// Like Var, but from a module with params
|
||||
ParamsVar {
|
||||
symbol: Symbol,
|
||||
params: Symbol,
|
||||
var: Variable,
|
||||
},
|
||||
AbilityMember(
|
||||
/// Actual member name
|
||||
Symbol,
|
||||
|
@ -308,6 +314,11 @@ impl Expr {
|
|||
Self::SingleQuote(..) => Category::Character,
|
||||
Self::List { .. } => Category::List,
|
||||
&Self::Var(sym, _) => Category::Lookup(sym),
|
||||
&Self::ParamsVar {
|
||||
symbol,
|
||||
params: _,
|
||||
var: _,
|
||||
} => Category::Lookup(symbol),
|
||||
&Self::AbilityMember(sym, _, _) => Category::Lookup(sym),
|
||||
Self::When { .. } => Category::When,
|
||||
Self::If { .. } => Category::If,
|
||||
|
@ -1872,7 +1883,7 @@ fn canonicalize_var_lookup(
|
|||
var_store.fresh(),
|
||||
)
|
||||
} else {
|
||||
Var(lookup, var_store.fresh())
|
||||
lookup_to_expr(lookup, var_store.fresh())
|
||||
}
|
||||
}
|
||||
Err(problem) => {
|
||||
|
@ -1898,7 +1909,7 @@ fn canonicalize_var_lookup(
|
|||
var_store.fresh(),
|
||||
)
|
||||
} else {
|
||||
Var(lookup, var_store.fresh())
|
||||
lookup_to_expr(lookup, var_store.fresh())
|
||||
}
|
||||
}
|
||||
Err(problem) => {
|
||||
|
@ -1916,6 +1927,18 @@ fn canonicalize_var_lookup(
|
|||
(can_expr, output)
|
||||
}
|
||||
|
||||
fn lookup_to_expr(LookedupSymbol { symbol, params }: LookedupSymbol, var: Variable) -> Expr {
|
||||
if let Some(params) = params {
|
||||
Expr::ParamsVar {
|
||||
symbol,
|
||||
params,
|
||||
var,
|
||||
}
|
||||
} else {
|
||||
Expr::Var(symbol, var)
|
||||
}
|
||||
}
|
||||
|
||||
/// Currently uses the heuristic of "only inline if it's a builtin"
|
||||
pub fn inline_calls(var_store: &mut VarStore, expr: Expr) -> Expr {
|
||||
use Expr::*;
|
||||
|
@ -1934,6 +1957,7 @@ pub fn inline_calls(var_store: &mut VarStore, expr: Expr) -> Expr {
|
|||
| other @ RecordAccessor { .. }
|
||||
| other @ RecordUpdate { .. }
|
||||
| other @ Var(..)
|
||||
| other @ ParamsVar { .. }
|
||||
| other @ AbilityMember(..)
|
||||
| other @ RunLowLevel { .. }
|
||||
| other @ TypedHole { .. }
|
||||
|
@ -3100,6 +3124,11 @@ pub(crate) fn get_lookup_symbols(expr: &Expr) -> Vec<ExpectLookup> {
|
|||
while let Some(expr) = stack.pop() {
|
||||
match expr {
|
||||
Expr::Var(symbol, var)
|
||||
| Expr::ParamsVar {
|
||||
symbol,
|
||||
params: _,
|
||||
var,
|
||||
}
|
||||
| Expr::RecordUpdate {
|
||||
symbol,
|
||||
record_var: var,
|
||||
|
|
|
@ -1105,6 +1105,7 @@ fn fix_values_captured_in_closure_expr(
|
|||
| SingleQuote(..)
|
||||
| IngestedFile(..)
|
||||
| Var(..)
|
||||
| ParamsVar { .. }
|
||||
| AbilityMember(..)
|
||||
| EmptyRecord
|
||||
| TypedHole { .. }
|
||||
|
|
|
@ -266,6 +266,7 @@ pub fn walk_expr<V: Visitor>(visitor: &mut V, expr: &Expr, var: Variable) {
|
|||
walk_list(visitor, *elem_var, loc_elems);
|
||||
}
|
||||
Expr::Var(..) => { /* terminal */ }
|
||||
Expr::ParamsVar { .. } => { /* terminal */ }
|
||||
Expr::AbilityMember(..) => { /* terminal */ }
|
||||
Expr::If {
|
||||
cond_var,
|
||||
|
|
|
@ -575,6 +575,22 @@ pub fn constrain_expr(
|
|||
|
||||
constraints.and_constraint([store_expected, lookup_constr])
|
||||
}
|
||||
ParamsVar {
|
||||
symbol,
|
||||
params,
|
||||
var,
|
||||
} => {
|
||||
// Save the expectation in the variable, then lookup the symbol's type in the environment
|
||||
let expected_type = *constraints[expected].get_type_ref();
|
||||
let store_expected = constraints.store(expected_type, *var, file!(), line!());
|
||||
|
||||
let lookup_constr = constraints.lookup(*symbol, expected, region);
|
||||
|
||||
// todo(agus): check params
|
||||
// let params_constr = constraints.lookup(*params, expected, region);
|
||||
|
||||
constraints.and_constraint([store_expected, lookup_constr])
|
||||
}
|
||||
&AbilityMember(symbol, specialization_id, specialization_var) => {
|
||||
// Save the expectation in the `specialization_var` so we know what to specialize, then
|
||||
// lookup the member in the environment.
|
||||
|
@ -4115,7 +4131,8 @@ fn is_generalizable_expr(mut expr: &Expr) -> bool {
|
|||
| ZeroArgumentTag { .. }
|
||||
| Tag { .. }
|
||||
| AbilityMember(..)
|
||||
| Var(..) => return false,
|
||||
| Var(..)
|
||||
| ParamsVar { .. } => return false,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -4422,6 +4422,9 @@ pub fn with_hole<'a>(
|
|||
|
||||
specialize_naked_symbol(env, variable, procs, layout_cache, assigned, hole, symbol)
|
||||
}
|
||||
ParamsVar { .. } => {
|
||||
todo!("agus: handle params var")
|
||||
}
|
||||
AbilityMember(member, specialization_id, specialization_var) => {
|
||||
let specialization_symbol = late_resolve_ability_specialization(
|
||||
env,
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue