-
Notifications
You must be signed in to change notification settings - Fork 1
Description
At the point I'm writing this, we haven't merged #270 yet, but on that branch:
> (catch (map [throw 'aha] '(a b c)))
('unboundb throw)
That, in case you're unsure, is a bug; it should output aha.
I had a sinking suspicion what was going on, so I manually switched off the code that calls fastfuncs — gotta make an environment variable for that — and lo and behold:
> (catch (map [throw 'aha] '(a b c)))
aha
The bug manifests in the presence of fastfuncs.
More precisely, since map has a fastfunc that makes a call to the provided callback using the Perl stack, there's no way it ever could work correctly. The throw in that callback writes a check that the Perl stack can not cash.
The above minimal case was not the first one I found, which was this one when playing around with #136 . After adding this epiloge to the code for testing purposes:
(prn (run '(10 5) '(2 2) '(1 3 1 1 1 0)))
(Note in particular that the final 0 triggers a throw.)
The program output the baffling result (t t t t t (5 1)). I don't know for sure, but I suspect that the extraneous t values come from the or call in checkbounds; they really shouldn't be there.
I confirmed that removing the 0 resulted in the correct output (5 1).
Trying to run the script with fastfuncs entirely turned off took too long. I ran it for five minutes, then killed it.
Just now, I ran it but selectively turning off the map fastfunc. It correctly outputs (5 1). This suggests a way forward, for the short term. We need to switch off the fastfuncs which call one of their parameters, because the way they make that call is not compatible with continuation calls.
As part of de-activating these fastfuncs, we should write regression tests for each of them that exposes the correct behavior. Like, a whole test file full of them.
For the longer term, I dunno. We do have a fastfunc compiler these days. We could maybe use it to compile to a CPS form of these functions. That could work.