Idris2
Idris2 copied to clipboard
[ fix #2927 ] Do not eagerly evaluate expressions occurring inside `%delay` block
Description
This PR fixes #2927.
Thanks to @stefan-hoeck for his assistance in Discord. He suggested fixing the issue by using Scheme's delay
and force
to memoize constants, as in #2807 instead of #2817 that is currently used. However, this solution comes with a performance overhead.
To reduce the overhead, I modified CSE to track whether an expression occurs inside a %delay
block. If that is the case, the expression is lifted as memoized lazy value using Scheme's delay
and force
. Otherwise, it becomes an eagerly evaluated top-level constant. Benchmarking the bootstrapped compiler on idris2api.ipkg
showed 5% slowdown on my machine, which is an improvement compared to the 8.5% slowdown in #2807.
Should this change go in the CHANGELOG?
- [x] If this is a fix, user-facing change, a compiler change, or a new paper
implementation, I have updated
CHANGELOG.md
(and potentially alsoCONTRIBUTORS.md
).
Is this related to #2791 ? : )
Is this related to #2791 ? : )
No, not really. Moreover, this PR uses proper memoization instead of relying on #2791, as it yields better performance in this specific case
I guess the only way they are related is that both the need for #2791 and discovery of #2927 happened because of an attempt to manipulate large lazily-constructed data structures
This makes sense to me however it would be nice to know what the cause of the slowdown is. I don't think we're using many top level lazy constants in the compiler.
Seeing that the current CSE is unsound with respect to %delay
, I think this should be merged unless our backend maintainers (@stefan-hoeck, in particular) have concerns.
Seeing that the current CSE is unsound with respect to
%delay
, I think this should be merged unless our backend maintainers (@stefan-hoeck, in particular) have concerns.
To the best of my knowledge, we have (a) test(s) to verify that non-delayed top-level constants get converted to constants correctly. If these tests still pass (they do), I'm all for merging this.
I have rebased this PR, all the tests still do pass. Perhaps it's worth re-measuring compilation time as well
Thanks @stefan-hoeck! I am merging this now and am happy to take the blame if something goes wrong.
Software's not about blame! Don't feel pressure to mess up something.