[squeak-dev] Re-signalling an already signaled exception
Jaromir Matas
mail at jaromir.net
Sun Jun 12 16:36:26 UTC 2022
Hi Christoph,
+1 Hooray, I guess now the re-signaling is working as intended at last :)
Thanks for noticing it wasn’t still right and showing the example.
Best,
Jaromir
--
From: Thiede, Christoph<mailto:Christoph.Thiede at student.hpi.uni-potsdam.de>
Sent: Sunday, June 12, 2022 17:29
To: The general-purpose Squeak developers list<mailto:squeak-dev at lists.squeakfoundation.org>
Subject: Re: [squeak-dev] Re-signalling an already signaled exception
Hi Jaromir,
yes, my TBInterrupt was broken indeed, and yes, your proposed patch fixed it indeed. :-) I have put Kernel-ct.1481 & Tests-ct.490 into the inbox. Do you think we can merge it in this form? :)
Best,
Christoph
Von: Squeak-dev <squeak-dev-bounces at lists.squeakfoundation.org> im Auftrag von Jaromir Matas <mail at jaromir.net>
Gesendet: Samstag, 11. Juni 2022 09:50:21
An: The general-purpose Squeak developers list
Betreff: Re: [squeak-dev] Re-signalling an already signaled exception
Hi Christoph,
Let me know if it works; if not whether the “copy refresh” fix below works. I’ve never seen re-signaling an exception in real code, thanks for the link. At least it makes sense trying to fix it :)
(different systems struggle too; little survey: https://forum.world.st/The-Inbox-Kernel-jar-1399-mcz-tp5129370p5129434.html)
Thanks,
Jaromir
From: Christoph Thiede<mailto:christoph.thiede at student.hpi.uni-potsdam.de>
Sent: Saturday, June 11, 2022 1:20
To: The general-purpose Squeak developers list<mailto:squeak-dev at lists.squeakfoundation.org>
Subject: Re: [squeak-dev] Re-signalling an already signaled exception
Fyio - here is a practical example of resignaling an exception (but I won't guarantee that it's idiomatic): https://sourcegraph.com/search?q=context:global+repo:%5Egithub%5C.com/LinqLover/TelegramBot%24%40098a29b+deferDuring&patternType=literal
I suppose that it's broken now, but I haven't checked yet.
Am 11.06.2022 00:21 schrieb Jaromir Matas <mail at jaromir.net>:
Hi Christoph,
Yes, the “fresh copy” of an exception is probably the best and simplest solution and you and Chris were right! I forgot about the subclasses and their instance variables :)
So what would you think about this simple fix:
#signal
"Ask ContextHandlers in the sender chain to handle this signal. The default is to execute and return my defaultAction.
Sending #signal to an already signaled exception generates a new exception of the same type with the same messageText"
signalContext ifNotNil: [^self copy refresh signal].
signalContext := thisContext contextTag.
^(thisContext nextHandlerContextForSignal: self) handleSignal: self
… where:
#refresh
signalContext := handlerContext := outerContext := nil
From: Jaromir Matas<mailto:mail at jaromir.net>
Sent: Friday, June 10, 2022 23:56
To: The general-purpose Squeak developers list<mailto:squeak-dev at lists.squeakfoundation.org>
Subject: Re: [squeak-dev] Re-signalling an already signaled exception
Hi Christoph,
I think I remember… My original interpretation of ANSI about sending #signal to an existing exception resulted in Kernel-jar.1407. However, later I noticed this wording in #messageText section:
“Subsequent sends of the message #messageText to a signaled exception generated by sending the message #signal to the receiver of this message will also return this value.”
… this “generated by” lead me to a more limited/conservative interpretation that is currently in the Trunk.
I believe Kernel-jar.1407 could be considered an extension of ANSI specification - your example indicates it’d be probably more logical or practical than the current one. I haven’t seen re-sending signal to existing exceptions implemented in other systems though.
How about to try after the release? :)
Thanks for bringing this up!
Best,
jaromir
From: Jaromir Matas<mailto:mail at jaromir.net>
Sent: Friday, June 10, 2022 17:18
To: The general-purpose Squeak developers list<mailto:squeak-dev at lists.squeakfoundation.org>
Subject: Re: [squeak-dev] Re-signalling an already signaled exception
Hi Christoph,
Thanks for the example! This was actually my original idea how re-signaling an existing exception should work :) It’s implemented in Kernel-jar.1407 (now in Treated) - check it out… it really returns
`Key not found: plonk`
as you would expect too.
Unfortunately I can’t recall why I went with the less ambitious Kernel-jar.1446 (now in Trunk) eventually.
If you find this more reasonable, why not try to revive it?
Thank you,
best,
Jaromir
From: christoph.thiede at student.hpi.uni-potsdam.de<mailto:Christoph.Thiede at student.hpi.uni-potsdam.de>
Sent: Friday, June 10, 2022 13:30
To: squeak-dev at lists.squeakfoundation.org<mailto:squeak-dev at lists.squeakfoundation.org>
Subject: Re: [squeak-dev] Re-signalling an already signaled exception
Hi Jaromir,
Thanks for working on this! I'm possibly a bit late on the party, but I noticed that current #signal only keeps the messageText, not any other custom properties of an exception. I'm not sure whether this is the expected behavior. :)
Think of this revised example:
[(KeyNotFound key: #plonk) signal] on: Error do: [:ex |
[ex signal] on: KeyNotFound do: [:ex2 | Transcript show: ex2]]
It will print out "Key not found: nil" to the Transcript, instead of printing the original key.
Without diving deeper into this discussion, my first impression would have been that some kind of #freshCopy (maybe with a better name?) would be a more holistic approach to honor any state in subclasses of Exception. What do you think? :-)
Best,
Christoph
---
Sent from Squeak Inbox Talk<https://github.com/hpi-swa-lab/squeak-inbox-talk>
On 2022-02-06T11:42:46+01:00, mail at jaromir.net wrote:
> Hi,
> just an update: I've sent a proposal to the Inbox: Kernel-jar.1446 with the following code:
>
> signal
> "Ask ContextHandlers in the sender chain to handle this signal. The default is to execute and return my defaultAction.
> Sending #signal to an already signaled exception generates a new exception of the same type with the same messageText"
>
> signalContext ifNotNil: [^self class signal: messageText].
> signalContext := thisContext contextTag.
> ^(thisContext nextHandlerContextForSignal: self) handleSignal: self
>
> If possible I'd like to withdraw my previous contribution to #signal making repeated #signal sends equivalent to sending #outer, to prevent future code from using that misleading approach. Subsequent #signal sends are NOT equivalent to #outer and they have their own subtly different meaning discussed here - provided my interpretation of ANSI is right this time :)
>
> Thanks for your time and apologies for previous confusion.
>
> best,
> Jaromir
> ^[^
> --
> Sent from Squeak Inbox Talk
>
> On 2022-02-05T18:48:39+01:00, mail at jaromir.net wrote:
>
> > Hi Chris,
> >
> > On 2022-02-04T17:11:35-06:00, asqueaker at gmail.com wrote:
> >
> > > Hi Jaromir,
> > >
> > > Here's a motivation example:
> > > >
> > > > [1/0] on: Error do: [:ex |
> > > > [ex signal] on: ZeroDivide do: [Transcript show: #ZeroDivide]
> > > > ]
> > > >
> > > > Would you expect this code to work and pick up the ZeroDivide handler?
> > > >
> > > ...
> > >
> > > > The point or a use case is to provide additional (finer, more specific)
> > > > handlers inside the general handler rather than wrap the general handler
> > > > inside more specific handlers. More specific handlers can even be inside a
> > > > method so the readability would not degrade.
> > > >
> > >
> > > I was able to do it by creating a new exception instance and signaling it:
> > >
> > > [1/0] on: Error do: [: err |
> > > [err copy signal] on: ZeroDivide do: [Transcript show:
> > > #ZeroDivide] ]
> > >
> > > I don't know about #copy, though, you might want to implement your own
> > > special #freshCopy that throws out the signalContext, handlerContext and
> > > outerContext, but the above "worked". :)
> > >
> >
> > Precisely, it crossed my mind too and yes, it has to be a "fresh" copy with blank instance variables (except messageText). A simple copy fails tests with nested outer etc...
> >
> > I've checked ANSI again and they say, quote: [5.5.3.1 messageText][...] Subsequent sends of of the message #messageText to a signaled exception generated by sending the message #signal to the receiver of this message [note: the receiver is an exception instance] will also return this value.
> >
> > So what I'm actually looking for is this: (and it's equivalent to the "fresh" copy idea)
> >
> > [1/0] on: Error do: [: err |
> > [err class signal: err messageText] on: ZeroDivide do: [Transcript show: #ZeroDivide] ]
> >
> > If I'm interpreting ANSI's intention correctly then we could update our #signal like this:
> >
> > signal
> > "Ask ContextHandlers in the sender chain to handle this signal. The default is to execute and return my defaultAction.
> > Signaling an already signaled exception is interpreted as signaling a new exception of the same type with the same messageText"
> >
> > - signalContext ifNotNil: [^self outer].
> > + signalContext ifNotNil: [^self copy signal: self messageText].
> > signalContext := thisContext contextTag.
> > ^(thisContext nextHandlerContextForSignal: self) handleSignal: self
> >
> > It was my idea last year to make subsequent sends of #signal to an already signaled exception equivalent to #outer and now I can see it was wrong and I'd like to really fix it this time :) All test are green, even the ones in Tests-jar.464.
> >
> > Thanks, Chris, for discussing this.
> >
> > best,
> > Jaromir
> > ^[^
> > --
> > Sent from Squeak Inbox Talk
> >
> >
>
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.squeakfoundation.org/pipermail/squeak-dev/attachments/20220612/8b1080bc/attachment-0001.html>
-------------- next part --------------
A non-text attachment was scrubbed...
Name: 2954D7231E624B8B8507739EB7747B04.png
Type: image/png
Size: 142 bytes
Desc: 2954D7231E624B8B8507739EB7747B04.png
URL: <http://lists.squeakfoundation.org/pipermail/squeak-dev/attachments/20220612/8b1080bc/attachment-0001.png>
More information about the Squeak-dev
mailing list
|