[Cuis-dev] Exception handler blocks with non-local returns
Andres Valloud
ten at smallinteger.com
Mon Oct 14 23:48:22 PDT 2019
Phil,
On 10/14/19 22:37, Phil B wrote:
> - Blue Book - Useless... the only thing remotely mentioning exceptions
> had nothing to do with them. I don't see #on:do: referenced anywhere.
> Wondering if Exception as we know it even existed back then? I see
> things like SyntaxError hanging directly off of Object.
IIRC, exceptions were a later invention.
> - ANSI draft - Now we're getting somewhere...
>
> On p.84 the define #on:do: an mention that 'The result of evaluating the
> receiver is returned.' It says nothing about the result of evaluating
> the exception block. Something interesting is that on p.84 when talking
> about #ensure: and #ifCurtailed: they go to the effort of explicitly
> stating 'the value returned from the evaluation of terminationBlock is
> discarded' but for whatever reason didn't say anything (the same or
> different) for #on:do:. >
> On p.92 they define the signaledException protocol which includes
> #return, #return: etc. and states 'These message are used to explicitly
> control how execution will continue when it leaves the handler block.'
See section 5.5.2.1, which (if I'm reading it right) says that if a
handler block does not tell the exception what to do, the behavior is
equivalent to doing ex return: (the value of the block).
However, the text prefixes that specification by stating "if the block
answers normally, as if returning from the message #value:". Ok, so now
we have an interpretation problem.
Does "answer normally" include non-local return?
1. Suppose the answer is 'yes'. Then what does it mean to do
ex return: anObject
in order to return to a block that is no longer in the stack, because
presumably the non-local return unwound the receiver of on:do: as well?
This interpretation does not make sense.
2. So suppose the answer is 'no'. Then what happens when the handler
block has a non-local return? I do not immediately see what the spec
says should happen, especially wrt the exception environment --- is that
even supposed to be reset? I'd like to believe so, because otherwise
consider the horrors of a non-local return skipping past exception
handlers without resetting the exception environment to the closest
still active handler.
Maybe I missed the text that says what happens?
> Taken together, I'd interpret that as any return value from the handler
> block is a gray area and implementer's choice.
IIRC, there's non-zero truth in this. But let's make sure, I'll do some
more digging tomorrow.
> So as I believe you've
> stated, the only way to ensure a specific return a value is to send
> #return (for nil) or #return: (for any other value.) I find that more
> than a bit scary since it means that the behavior before the most recent
> changes was valid. And so was the behavior after the most recent changes.
>
> Unless someone can find something else to make be feel better, I'm in
> full agreement that we do have a problem.
Repeatedly running into this kind of situation is one of the things that
often makes me wish programs were very explicit about what they want to
happen. Because then, if (say) we wanted to change how exceptions work,
then we can reimplement the messages the application sends so they
provide the expected behavior in the new world, and everyone's happy.
But if programs do not explicitly say what they mean, now we're in the
business of guessing. There's no way to win that, so the steady state
becomes 'nothing changes anymore'. Obviously that's unacceptable.
Andres.
More information about the Cuis-dev
mailing list