mirror of
https://github.com/roc-lang/roc.git
synced 2025-11-25 21:37:48 +00:00
Work around symbol specializations not getting captured
This commit is contained in:
parent
b797e9c0c8
commit
447e1492e1
1 changed files with 25 additions and 1 deletions
|
|
@ -7537,7 +7537,31 @@ where
|
|||
// if this is an imported symbol, then we must make sure it is
|
||||
// specialized, and wrap the original in a function pointer.
|
||||
let mut result = result;
|
||||
for (_, (variable, left)) in needed_specializations_of_left {
|
||||
|
||||
let no_specializations_needed = needed_specializations_of_left.len() == 0;
|
||||
let needed_specializations_of_left = needed_specializations_of_left
|
||||
.map(|(_, spec)| Some(spec))
|
||||
// HACK: sometimes specializations can be lost, for example for `x` in
|
||||
// x = Bool.true
|
||||
// p = \_ -> x == 1
|
||||
// that's because when specializing `p`, we collect specializations for `x`, but then
|
||||
// drop all of them when leaving the body of `p`, because `x` is an argument of `p` in
|
||||
// such a case.
|
||||
// So, if we have no recorded specializations, suppose we are in a case like this, and
|
||||
// generate the default implementation.
|
||||
//
|
||||
// TODO: we should fix this properly. I think the way to do it is to only have proc
|
||||
// specialization only drop specializations of non-captured symbols. That's because
|
||||
// captured symbols can only ever be specialized outside the closure.
|
||||
// After that is done, remove this hack.
|
||||
.chain(if no_specializations_needed {
|
||||
[Some((variable, left))]
|
||||
} else {
|
||||
[None]
|
||||
})
|
||||
.filter_map(std::convert::identity);
|
||||
|
||||
for (variable, left) in needed_specializations_of_left {
|
||||
add_needed_external(procs, env, variable, LambdaName::no_niche(right));
|
||||
|
||||
let res_layout = layout_cache.from_var(env.arena, variable, env.subs);
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue