Tag top-level bindings even when optimizations are disabled
One complication in implementing top-level unlifted bindings (#23637) concerns missing tags on imported bindings. For example if we have this Core:
b :: B Bool
b = B a
Where B :: Type -> UnliftedType
and a :: Bool
. Currently, if a
is imported from a module that has been compiled with optimizations disabled then this Stg tag inference will rewrite b
to:
b :: B Bool = \r [] case a of a_tCP { __DEFAULT -> B [a_tCP]; };
Which means b
is not fully evaluated, but it is also unlifted so there is no thunk that can postpone that evaluation. This is a problem.
To avoid this, SPJ proposes a new invariant:
All toplevel values are properly tagged, so that
x
will never be eval'd by the STG-rewrite pass.
This can be done cheaply, so it shouldn't add that much extra time and space usage to unoptimized builds.
However, we should still be careful. @simonmar warned that exporting more information in interface files can cause more recompilation:
Similar arguments about recompilation apply to
LFInfo
- we should be careful to minimize the impact this might have on recompilation. So long as we only expose the tag I think we should be OK, the only impact will be changing something from a constructor to non-constructor or vice-versa while keeping its type unchanged, which I imagine is rare.
SPJ also suggested that @clyring might have already done some work in this direction. Is that right?