[plt-scheme] R6RS exception handling and dynamic extent [was: SXML for R6RS]

From: Robby Findler (robby at cs.uchicago.edu)
Date: Thu Jul 10 10:42:11 EDT 2008

The operational semantics of R6 indicates that there is no
exit/re-enter for raise-continuable (altho it only covers
with-exception-handler, raise and raise-continuable, not guard).


On Thu, Jul 10, 2008 at 9:23 AM, Derick Eddington
<derick.eddington at gmail.com> wrote:
> On Thu, 2008-07-10 at 06:02 -0600, Matthew Flatt wrote:
>> At Thu, 10 Jul 2008 00:36:32 -0700, Derick Eddington wrote:
>> > On Wed, 2008-07-09 at 07:18 -0600, Matthew Flatt wrote:
>> > > Suppose that you actually want ports to be closed when control escapes
>> > > (for any reason), so you write
>> > >
>> > >  (define (call-with-input-file* file proc)
>> > >    (let ([p #f])
>> > >      (dynamic-wind
>> > >        (lambda () (set! p (open-input-file file)))
>> > >        (lambda () (proc p))
>> > >        (lambda () (close-input-port p) (set! p #f)))))
>> > >
>> > > and use that, instead. Then, doesn't my objection about `ssax:warn' and
>> > > `guard' hold?
>> >
>> > Using dynamic-wind like that would have the same issue with any possible
>> > exception re-raised by a guard, and if there were multiple guards which
>> > re-raise, it would exit and re-enter for each guard.  Or what if
>> > somewhere down in proc's dynamic extent it uses a procedure which
>> > escapes to some continuation and then re-enters back?  Assuming the
>> > dynamic extent will only be entered and exited once just seems like a
>> > bad idea unless you can be certain of that.
>> You're right.
>> Under normal circumstances, you can be sure quite often, because few
>> library functions capture and restore continuations. Indeed, in
>> building PLT Scheme libraries and tools, we've often found it necessary
>> to ensure that a continuation is not restored when unknown code is
>> called, which is why PLT Scheme includes constructs like continuation
>> barriers.
>> > I don't see how making ssax:warn raise an exception
>> > singles it out when there are other ways control could escape and
>> > re-enter.
>> Turning the above around, if a library captures and restores
>> continuations, then it's placing an extra burden on users of the
>> library to accommodate continuation jumps. That sounds like a big price
>> to pay to get warnings from SSAX --- but perhaps I'm not enough of an
>> SSAX user to say. If SSAX users understand that functions capture and
>> restore continuations anytime that they might report a warning, and if
>> they're happy with that API, then it's all fine.
> I agree that would be a big price, too big and too unexpected of a
> price.  Now I think I realize there's another issue you are considering
> that I was not: in PLT at the moment, `raise-continuable' is capturing
> its continuation which gets restored if the handler returns, and this is
> why my `ssax:warn' would be capturing and restoring continuations.  I
> realized I've been assuming this would not be PLT's final design,
> because of what the R6RS seems to say about how exception handling and
> dynamic extent is supposed to work -- that raising an exception,
> continuable or not, calling the handler, and possibly returning for a
> continuable exception, does not exit and re-enter the dynamic
> extent (unless `guard' handlers which re-raise are involved, but
> that's an argument against using `guard' I think, not against using
> continuable exceptions).
>        (raise obj)    procedure
>        Raises a non-continuable exception by invoking the current
>        exception handler on obj. The handler is called with a
>        continuation whose dynamic environment is that of the call to
>        raise, except that the current exception handler is the one that
>        was in place when the handler being called was installed. When
>        the handler returns, a non-continuable exception with condition
>        type &non-continuable is raised in the same dynamic environment
>        as the handler.
>        (raise-continuable obj)    procedure
>        Raises a continuable exception by invoking the current exception
>        handler on obj. The handler is called with a continuation that
>        is equivalent to the continuation of the call to
>        raise-continuable, with these two exceptions: (1) the current
>        exception handler is the one that was in place when the handler
>        being called was installed, and (2) if the handler being called
>        returns, then it will again become the current exception
>        handler. If the handler returns, the values it returns become
>        the values returned by the call to raise-continuable.
> Maybe I'm reading into this too much thinking it means the dynamic
> extent will not be exited and re-entered.  But if my interpretation is
> wrong, doesn't that mean any and all uses of `raise-continuable' are
> going to be effectively verboten in an implementation that captures and
> restores continuations, because they'll be imposing that unexpectedly?
> (I agree imposing that unexpectedly would be bad.)  But then what's the
> use of continuable exceptions, &warning, and an initial/default handler
> that returns for non-&serious?
> In Ikarus, calling `raise' or `raise-continuable', calling the handler,
> the handler's dynamic extent possibly calling `raise' or
> `raise-continuable', and the handler returning all do not capture or
> restore continuations, it's all one series/stack of normal procedure
> calls and returns (again, unless `guard' handlers are called).
> --
> : Derick
> ----------------------------------------------------------------
> _________________________________________________
>  For list-related administrative tasks:
>  http://list.cs.brown.edu/mailman/listinfo/plt-scheme

Posted on the users mailing list.