On 23 April 2013 18:02, Sean P. DeNigris <sean@clipperadams.com> wrote:
Igor Stasenko wrote
but what you expecting? you refer to 'self' multiple times. sure thing it cannot be GC-ed, neither process will die because of plenty of references on stack. Even block closure which you creating for fork will have home context which keeps reference to 'self', e.g. receiver.
I'm expecting magic apparently because I am stupid when it comes to processes ;) I changed all the "self"s to array first, which also didn't work, but then I read your statement about the home context...
Luc's class-side trick seems to work: Timer>>start
| array | array := WeakArray with: self. process := self class createProcessFor: array. "tried passing self here, but it seemed to keep the process around"
of course, because the home context (will be the method below) of closure captures method's arguments, and holding them strongly..
Timer class>>createProcessFor: aWeakArray
[ [ aWeakArray first notNil ] whileTrue: [ | timer | aWeakArray first interval asDelay wait. "We have to check again if the timer was garbage collected during the wait" aWeakArray first ifNotNil: [ aWeakArray first value: aWeakArray first value + 1. aWeakArray first announcer announce: (TimerValueChanged to: aWeakArray first value) ] ] ] fork.
Wow, it would seem that an object using a process internally that is only valid when the object is around is a fairly common use case. I can't believe how complicated this is :/
it is not apparent to me why this is common use case. :) you can also simply pass a copy of 'self' to process. as long as copy accessing same announcer, your ticker process will work perfectly. then all you would need to do is: | copy | copy := self copy. process := self class createProcessFor: copy. WeakRegistry default add: self executor: copy. and implement: finalize process terminate. process := nil. Then createProcessFor: will be simple: Timer class>>createProcessFor: timer [ [ timer wait. " make Demeter a bit happier" timer tick. "this should increment counter and announce TimerValueChanged, like that we're not make Demeter unhappy" ] whileTrue ] fork. (actually , to make mr.Demeter completely happy, i would do [ timer waitAndTick ] whileTrue. ) and, tick, will be something like that: tick process ifNil: [ ^ false ]. self incrementCounter. self announce: (MyGreatAnnouncement with: whatever). ^ true. cheerz :)
----- Cheers, Sean -- View this message in context: http://forum.world.st/Terminating-a-Process-when-an-object-dies-tp4683036p46... Sent from the Pharo Smalltalk Users mailing list archive at Nabble.com.
-- Best regards, Igor Stasenko.