[squeak-dev] Re: Re: Running process after image save/stop/restart

Eliot Miranda eliot.miranda at gmail.com
Tue Mar 5 22:40:13 UTC 2013


Hi Lou,

On Tue, Mar 5, 2013 at 2:38 PM, Louis LaBrunda <Lou at keystone-software.com>wrote:

> I will bow to your knowledge of Squeak but take a look at the code below
> from VA Smalltalk.
>
> Pay special attention to #resume: which looks to me like it puts the new
> process at the top of the queue (there are 7 queues, one for each priority)
> and puts the current (activeProcess) at the bottom of the same queue and
> then switches to the highestPriorityProcess.  Which can be another process
> or the new process just put in front of the current process.
>

thanks, that's interesting, and good to know.


>
> Don't ask my why it works this way.  As I said, I added #forkReady which it
> seems works more like Squeak.  Most of the time I think it doesn't matter
> but sometimes it does.
>
> Lou
>
> fork
>         "Create a new Process which is scheduled by the
>          ProcessScheduler. The new process executes the receiver by
>          sending it the message value. The new process is created
>          with the same prority as the activeProcess. Answer the
>          receiver."
>
>         ^self newProcess resume
>
> resume
>         "Tell the process scheduler to add the process to the ready
>          to run queue."
>
>         self isResumable ifFalse: [^self error: (NlsCatKRN indexedMsg: 2)].
> "$NLS$ process cannot be resumed"
>         Processor resume: self.
>         ^ self
>
> resume: aProcess
>
>         | state |
>         state := self enableAsyncMessages: false.
>         (aProcess == self activeProcess or: [aProcess isDead]) ifTrue: [
>                 self enableAsyncMessages: state.
>                 ^self "Resuming a dead process or the active process is a
> nop."].
>
>         aProcess isRunable ifTrue: [
>                 (aProcess processState: ##ready) queue addFirst: aProcess].
>
>         (self activeProcess processState: ##ready) queue addLast: self
> activeProcess.
>         self activeProcess switchTo: self highestPriorityProcess.
>         self enableAsyncMessages: state
>
>
>
>
>
>
>
>
> On Tue, 5 Mar 2013 13:46:13 -0800, Eliot Miranda <eliot.miranda at gmail.com>
> wrote:
>
> >On Tue, Mar 5, 2013 at 1:36 PM, Louis LaBrunda <Lou at keystone-software.com
> >wrote:
> >
> >> Hi Eliot,
> >>
> >> Thanks for all the very valuable information.  I think I didn't ask my
> >> question properly but with all the answers I was able to accomplish
> exactly
> >> what I wanted.
> >>
> >> I do have a question about one thing you said.  See below.
> >>
> >> Lou
> >>
> >> >On Thu, Feb 28, 2013 at 2:30 PM, Bert Freudenberg <
> bert at freudenbergs.de
> >> >wrote:
> >> >
> >> >> On 2013-02-28, at 22:38, Louis LaBrunda <Lou at Keystone-Software.com>
> >> wrote:
> >> >>
> >> >> > If a process is running when an image is saved, is the process
> >> stopped at
> >> >> > any point in particular?
> >> >>
> >> >> The active process is stopped in the snapshot primitive (a.k.a.
> "image
> >> >> saving") and resumes after it on startup. All other processes are
> >> waiting
> >> >> on some semaphore anyway.
> >> >>
> >> >
> >> >Nope.  No processes are stopped.  Processes are simply unable to run
> while
> >> >in the snapshot.  The key to understanding this is understanding the
> >> >scheduler (the Processor global, an instance of ProcessorSheduler).  It
> >> >maintains an activeProcess and a set of runnable processes,
> implemented as
> >> >an Array of lists of processes at the same priority.  A runnable
> process
> >> >(one not sent suspend or not waiting on a semaphore) is either the
> >> >activeProcess or on one of the lists.  This state is saved to the
> >> snapshot.
> >> > At any time the scheduler's activeProcess is the first highest
> priority
> >> >process in the set of runnable processes.  It will only be deposed as
> >> >activeProcess when either another higher-priority process becomes
> runnable
> >> >or it yields or suspends or waits on a semaphore.  If it suspends or
> waits
> >> >on a semaphore it is removed from the set of runnable processes.  If it
> >> >yields it gets sent to the back of its run-queue and the next process
> in
> >> >that queue becomes the runnable process.  If it is the only runnable
> >> >process at its priority yield is a noop.
> >> >
> >> >On loading the image the VM activates the activeProcess; the
> activeProcess
> >> >will typically be in a method that has called the snapshot primitive
> and
> >> >the system will continue, with the snapshot primitive answering true.
>  All
> >> >the other processes in the run queues are runnable but, just as before
> the
> >> >snapshot, can't be run because the activeProcess is still runnable.
>  But
> >> as
> >> >soon as the activeProcess suspends, waits or yields, one of these
> >> processes
> >> >may run.
> >> >
> >> >Several processes are terminated (terminate is suspend + run unwinds)
> on
> >> >resuming the image.  This is done to inform the VM of additional state
> to
> >> >make these processes run.  For example, the Delay process needs to tell
> >> the
> >> >VM what the next delay expiry is on start-up.  The delay semaphore (the
> >> >semaphore the VM signals when the current active delay expires) is
> saved
> >> in
> >> >the image in the specialObjects array, so it persists across a
> snapshot,
> >> >but the VM doesn't persist the current delay expiry time.
> >> >
> >> >So any long-running process which doesn't need to inform the VM of
> >> anything
> >> >special at start-up will just keep truckin' along, and nothing need be
> >> >done.  A snapshot really is like a fermata, a pause.  It is not some
> kind
> >> >of shut-down.
> >> >
> >> >As a side-note what happens if one does
> >> >
> >> >     [Semaphore new wait] fork.
> >> >    Processor activeProcess yield.
> >> >
> >> >?
> >> >
> >> >This creates a new process and adds it to the Processor's run queue.
>  Once
> >> >the process has been sent fork the current process doesn't reference it
> >> >since it has been popped from the current process's stack, and so the
> only
> >> >reference to the new process is from one of the Processors' run queues,
> >> but
> >> >it isn't running yet because the activeProcess (the one that sent
> fork) is
> >> >running.  When the activeProcess yields the new process gets to run.
>  Once
> >> >it has created the new semaphore it sends wait to it.  At this point
> it is
> >> >removed from the Processor's run-queue and added to the semaphore's
> queue.
> >> > So now there is a circular reference between the process and the
> >> semaphore
> >> >and these are the only references to the process and the semaphore,
> and so
> >> >both get garbage collected.
> >>
> >> I think the forked process gets to run before the processor returns to
> the
> >> yield line.  This is the way it works in VA Smalltalk and from looking
> at
> >> the implementers of #fork, I think it is the way it works in Squeak.  I
> >> could be wrong, if so please be kind, I have been following the news
> group
> >> for a while but I'm new to playing with Squeak.
> >>
> >
> >No.  In Smalltalk-80 (VisualWorks, Squeak etc) fork creates a new process
> >with the same priority as the current process and then resumes it (resume
> >is the primitive that adds the process to the run queue).  So the new
> >process is effectively behind the activeProcess in the run-queue.  e.g.
> >
> >| who |
> >who := #me.
> >[who := #him. Semaphore new wait] fork.
> >who
> >=> #me
> >
> >
> >| who |
> >who := #me.
> >[who := #him. Semaphore new wait] fork.
> >Processor yield.
> >who
> >=> #him
> >
> >I can't speak for VA, but I doubt you;re right.  I expect VA to have the
> >same behaviour as the above.
> >
> >
> >
> >> There were times when I wanted to create a new fork but didn't want it
> to
> >> run until the method creating it finished.  So, I added #forkReady (and
> >> friends) that would create the process but not run it right away.
> >>
> >
> >there's also forkAt: Processor activePriority - 1, or
> >
> >| gate result |
> >gate := Semaphore new.
> >[gate wait.
> > self doStuff] fork.
> >result := self getResult.
> >gate signal.
> >^result
> >
> >
> >> >>
> >> >> > If the saved image is started, is there any way the process can
> tell?
> >> >>
> >> >> Not the process itself. But you surely keep the process in a class
> >> >> somewhere, and the class can arrange to get notified on startup by
> >> adding
> >> >> itself to the startup list. See addToStartUpList:.
> >> >>
> >> >
> >> >exactly. one could also e.g. poll OSProcess to get the process ID of
> the
> >> VM
> >> >process and see if that changes, but that's a horrible hack, and once
> in a
> >> >blue moon will fail (cuz process ids are not unique and get reused).
> >> >
> >> >> I'm running a process that keeps running for a look time.  It loops
> >> with a
> >> >> > delay and in the loop gets the date and time.  If the date and time
> >> were
> >> >> > obtained just before the save, they would be old at the time of the
> >> image
> >> >> > restart and need to be refreshed.
> >> >>
> >> >>
> >> >> Delays get adjusted after resuming from snapshot. So it should just
> >> work.
> >> >>
> >> >
> >> >exactly.  the snapshot will look just like a long time on the run-queue
> >> >whole the process is preempted by higher-priroity processes,
> >> >
> >> >
> >> >> - Bert -
> >> >>
> >> -----------------------------------------------------------
> >> Louis LaBrunda
> >> Keystone Software Corp.
> >> SkypeMe callto://PhotonDemon
> >> mailto:Lou at Keystone-Software.com http://www.Keystone-Software.com
> >>
> >>
> >>
> -----------------------------------------------------------
> Louis LaBrunda
> Keystone Software Corp.
> SkypeMe callto://PhotonDemon
> mailto:Lou at Keystone-Software.com http://www.Keystone-Software.com
>
>
>


-- 
best,
Eliot
-------------- next part --------------
An HTML attachment was scrubbed...
URL: http://lists.squeakfoundation.org/pipermail/squeak-dev/attachments/20130305/3d5cab94/attachment.htm


More information about the Squeak-dev mailing list