[Cuis-dev] Follow-up: #terminate and #suspend update

Jaromir Matas mail at jaromir.net
Fri Jan 20 12:08:19 PST 2023


Hi Juan,

Apologies for my previous message sent prematurely.

Process Browser is checking termination status of all processes very often and hence occasionally the procedure gets preempted and breaks as you noted in #isDeadOrAtEnd comment. The same happens in my #isDone (just open an image and a Process Browser and wait – sooner or later a debugger pops up with an MNU error inside #isDone. So, the idea is to rewrite #isDone to eliminate message sends at critical points:

isDone
                "Answer if the receiver has no unexecuted code left."

                ^pc
                                ifNil: [ true ]
                                ifNotNil: [ :aPC | (self atEnd: aPC) and: [
                                                sender
                                                                ifNil: [ true ]
                                                                ifNotNil: [ :ctx | ctx isDone]]]

It’s similar to your #isDeadOrAtEnd.

Question: in #isDeadOrAtEnd you have a block [ :aPC | self atEnd: pc ]. I wonder if you by any chance meant [ :aPC | self atEnd: aPC ], i.e. to use block’s argument rather than the instance variable? Or maybe it doesn’t make any difference, I’m just not sure now.

I hope this time it’s ok.

Best,
Jaromir



From: Jaromir Matas via Cuis-dev<mailto:cuis-dev at lists.cuis.st>
Sent: Thursday, January 19, 2023 12:25
To: Juan Vuletich<mailto:juan at cuis.st>; Discussion of Cuis Smalltalk<mailto:cuis-dev at lists.cuis.st>
Cc: Jaromir Matas<mailto:mail at jaromir.net>
Subject: Re: [Cuis-dev] Follow-up: #terminate and #suspend update

Hi Juan,

I’ve observed the debugger to pop up all of a sudden a few times when working with the Process Browser. The root cause seems to be my #isDone method:

isDone
                "Answer if the receiver has no unexecuted code left."

                self isDead ifTrue: [^true].
                self isBottomContext ifTrue: [^self atEnd].
                self atEnd ifTrue: [^self sender isDone].
                ^false

The second line checks if the sender variable is nil and hence the third line assumes the sender is not nil – however it may still be nil if the method computation is preempted and the higher priority process being checked terminates in the meantime.

Here’s my improved version (also enclosed):

isDone
                "Answer if the receiver has no unexecuted code left."

                ^sender ifNil: [self isDeadOrAtEnd] ifNotNil: [:ctx | ctx isDone]

I think this should work as expected because ifNil:ifNotNil: is inlined (not a send).

PS: as a side-effect the ProcessorTest suite now works fine consistently; before, some of the tests failed occasionally (on my Win10/Intel machine).

Best,
Jaromir


--

Jaromír Matas

mail at jaromir.net


From: Juan Vuletich<mailto:juan at cuis.st>
Sent: Tuesday, September 6, 2022 16:25
To: Discussion of Cuis Smalltalk<mailto:cuis-dev at lists.cuis.st>
Cc: Jaromir Matas<mailto:mail at jaromir.net>
Subject: Re: [Cuis-dev] #terminate and #suspend update

Hi Jaromir,

On 8/27/2022 7:12 AM, Jaromir Matas via Cuis-dev wrote:
Hi Juan,

> There is one problem left. #isTerminated will always answer false if #suspend primitive failed and old primitive 88 fallback method is called. I just pushed to github update #5458 to address this. Please check it carefully. Maybe you prefer a different solution, I'll be happy to review and integrate it.

Oops, I forgot to mention the backward compatibility consideration but you caught it :) (meaning: to be able to run new images with older VMs, not only older images with the new VM). Squeak decided to maintain only its ability to run older images with the new VM - so no change in #isTerminated in Squeak; however I agree with you that "fixing" #isTerminated is worth the effort provided the fix is pretty easy.

I'm enclosing my original suggestion for #isTerminated; I think the semantics is very similar to your version (checking whether the remaining context chain has anything useful left) except one thing: Your version allows a process with its suspended context's pc = nil to be considered not terminated. My understanding was: if a process's suspended context's pc is nil, it implies the process would be considered terminated. Is this right or would you define 'being terminated' differently?

Check this example:

ctx _ [] asContextWithSender: [] asContext.
p _ Process forContext: ctx priority: 40.
ctx pc: nil.
p isTerminated.  "answers false in your version and true in mine"

I already noticed a while ago my previous version of #isTerminated failed to catch pc = nil in a process's suspended context and evaluate the process as 'terminated'. I wonder now what definition of 'terminated' state is actually 'the right one'.

I had assumed there would always be sender frames. I believe my code worked correctly unless there were no sender frames of the frame with pc=nil. In any case, your version is more robust and nicer code. I just integrated it. Thanks!
Another question: in the example above - how do you look at the bytecodes of ctx? In Squeak the Explorer shows the bytecodes right away but in Cuis I have to open an extra inspector for 'method' and look at 'allBytecodes', right?

Yes. You are right. The explorer could be improved, to behave like Squeak's in this case. If you happen to have a couple of hours to hack this, it would be useful.
In Squeak the process p answers true to #isTerminated even without nilling its pc, which is expected because each of the two contexts consists only of a single instruction, a return. But in Cuis I'm not sure how come the answer is false; I suspect I've got confused by the different implementation of Context / ContextPart in Squeak/Cuis.  Here's what I mean:

ctx _ [] asContextWithSender: [] asContext.
p _ Process forContext: ctx priority: 40.
p isTerminated.  "answers false in Cuis and true in Squeak because ctx atEnd differs"

Just tried the example above, and it answers false in Squeak 6.0 alpha 21576 on my Intel Mac. Maybe this has changed recently? Perhaps it needs fixing in both environments.
... while this works the same in both:

ctx _ [1] asContextWithSender: [] asContext.
p _ Process forContext: ctx priority: 40.
p isTerminated.  "answers false in both Cuis and Squeak because ctx is not atEnd"

Yes it does.
Thank you for your advice.

Best regards,
Jaromir


--

Jaromír Matas

mail at jaromir.net<mailto:mail at jaromir.net>


Thanks,

--

Juan Vuletich

cuis.st

github.com/jvuletich

researchgate.net/profile/Juan-Vuletich

independent.academia.edu/JuanVuletich

patents.justia.com/inventor/juan-manuel-vuletich

linkedin.com/in/juan-vuletich-75611b3

twitter.com/JuanVuletich



-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.cuis.st/mailman/archives/cuis-dev/attachments/20230120/8ce028ab/attachment-0001.htm>
-------------- next part --------------
A non-text attachment was scrubbed...
Name: ContextPart-isDone-v2.st
Type: application/octet-stream
Size: 342 bytes
Desc: ContextPart-isDone-v2.st
URL: <http://lists.cuis.st/mailman/archives/cuis-dev/attachments/20230120/8ce028ab/attachment-0001.obj>


More information about the Cuis-dev mailing list