Open toelli-msft opened 3 years ago
There are two potential gotchas to do with capturing.
body
(which is a TExpr -> TExpr
function) already mentions ksc$mkAtomicVar
, presumably bound by some other call of this function. E.g. suppose body x
returns ksc$mkAtomicVar + x
. Then the occurence of ksc$mkAtomicVar
in body
gets captured by this let.
Here's a concrete example:
mkAtomicNoFVs 3 (\v1 ->
mkAtomicNoFVs 5 (\v2 -> v1+v2))
This returns the expression
let ksc$mkAtomicVar = 3 in
let ksc$mkAtomicVar = 5 in
ksc$mkAtomicVar + ksc$mkAtomicVar
which is obviously wrong.
body
binds ksc$mkAtomicVar
and mentions x
inside that binding. Example
mkAtomicNoFVs (Lit 4) (\x. Lam "ksc$mkAtomicVar" x)
This will produce
Let "ksc$mkAtomicVar" (Lit 4) (
Lam "ksc$mkAtomicVar" (Var "ksc$mkAtomicVar"))
which is obviously wrong.
So long as body
neither mentions no binds ksc$mkAtomicVar
we are fine.
mkAtomicNoFVs
is very useful because it provides a cheap way of preserving sharing whilst using a Haskell-level function to do "substitution" into anExpr
. It comes with the caveatHowever, it would be helpful if the
body
s could bind variables! (In particular it would help Hybrid shapes https://github.com/microsoft/knossos-ksc/pull/766). I think that NB3 below is correct, isn't it? (thismkAtomicNoFVs
is the same as inmaster
but with a different variable name).@simonpj Is there a reason we wouldn't want to use
mkNoAtomicFVs
like this? Perhaps it's too delicate? But it is very useful!