All of lore.kernel.org
 help / color / mirror / Atom feed
* Fwd: bug? Spawned childs always remain in zombie state
       [not found] <CAMqPLXWsMhPBjYa3JnCmuO=M6m2F=hSdiEfRx390VKdgC5qxZg@mail.gmail.com>
@ 2013-01-20 12:04 ` Sjon Hortensius
  2013-08-23 10:44   ` Herbert Xu
  0 siblings, 1 reply; 3+ messages in thread
From: Sjon Hortensius @ 2013-01-20 12:04 UTC (permalink / raw)
  To: dash

Hi. I'm trying to create a script which monitors a directory using
inotify and spawns a background process for all events. However I
found that all childs will remain in zombie state until the script
quits and I am unable to find a proper fix.

A minimal testcase:

#!/bin/dash
while true
do
    sleep 1 &
#    jobs >/dev/null
done

If you open a second terminal you'll see that all the 'sleep'
processes end up being defunct. I have tried playing with `set -ma`
but the only workaround I found is the commented 'jobs' line.
Uncommenting that line will result in expected behavior where childs
are properly reaped. Is this a bug, or is there an alternative
solution I'm missing?

Thanks,
Sjon

^ permalink raw reply	[flat|nested] 3+ messages in thread

* Re: Fwd: bug? Spawned childs always remain in zombie state
  2013-01-20 12:04 ` Fwd: bug? Spawned childs always remain in zombie state Sjon Hortensius
@ 2013-08-23 10:44   ` Herbert Xu
  2013-08-23 12:20     ` Jilles Tjoelker
  0 siblings, 1 reply; 3+ messages in thread
From: Herbert Xu @ 2013-08-23 10:44 UTC (permalink / raw)
  To: Sjon Hortensius; +Cc: dash

On Sun, Jan 20, 2013 at 12:04:04PM +0000, Sjon Hortensius wrote:
> Hi. I'm trying to create a script which monitors a directory using
> inotify and spawns a background process for all events. However I
> found that all childs will remain in zombie state until the script
> quits and I am unable to find a proper fix.
> 
> A minimal testcase:
> 
> #!/bin/dash
> while true
> do
>     sleep 1 &
> #    jobs >/dev/null
> done
> 
> If you open a second terminal you'll see that all the 'sleep'
> processes end up being defunct. I have tried playing with `set -ma`
> but the only workaround I found is the commented 'jobs' line.
> Uncommenting that line will result in expected behavior where childs
> are properly reaped. Is this a bug, or is there an alternative
> solution I'm missing?

You need to wait on them as otherwise dash has to keep them around
in case you call wait(1) later on.

Cheers,
-- 
Email: Herbert Xu <herbert@gondor.apana.org.au>
Home Page: http://gondor.apana.org.au/~herbert/
PGP Key: http://gondor.apana.org.au/~herbert/pubkey.txt

^ permalink raw reply	[flat|nested] 3+ messages in thread

* Re: Fwd: bug? Spawned childs always remain in zombie state
  2013-08-23 10:44   ` Herbert Xu
@ 2013-08-23 12:20     ` Jilles Tjoelker
  0 siblings, 0 replies; 3+ messages in thread
From: Jilles Tjoelker @ 2013-08-23 12:20 UTC (permalink / raw)
  To: Herbert Xu; +Cc: Sjon Hortensius, dash

On Fri, Aug 23, 2013 at 08:44:44PM +1000, Herbert Xu wrote:
> On Sun, Jan 20, 2013 at 12:04:04PM +0000, Sjon Hortensius wrote:
> > Hi. I'm trying to create a script which monitors a directory using
> > inotify and spawns a background process for all events. However I
> > found that all childs will remain in zombie state until the script
> > quits and I am unable to find a proper fix.

> > A minimal testcase:

> > #!/bin/dash
> > while true
> > do
> >     sleep 1 &
> > #    jobs >/dev/null
> > done

> > If you open a second terminal you'll see that all the 'sleep'
> > processes end up being defunct. I have tried playing with `set -ma`
> > but the only workaround I found is the commented 'jobs' line.
> > Uncommenting that line will result in expected behavior where childs
> > are properly reaped. Is this a bug, or is there an alternative
> > solution I'm missing?

> You need to wait on them as otherwise dash has to keep them around
> in case you call wait(1) later on.

The shell need not remember the processes indefinitely. Per POSIX (XCU
2.9.3.1 Asynchronous Lists), the application must reference $! before
starting another asynchronous list if it wants to use the wait builtin
for that particular process later on. (Note that this means that jobs -p
is not good enough even when the job consists of a single process, and
that printing $! can add memory leaks to a script.)

POSIX also restricts an operandless wait builtin to "known process IDs".
This seems inappropriate: there are many scripts that start multiple
asynchronous lists without referencing $! and expect operandless wait to
wait for all of them. Therefore, all jobs must be remembered while they
are running. However, if $! was not referenced for them and they are not
the most recent asynchronous list, they can be discarded when they
terminate. I implemented this in FreeBSD sh and it appears to work well.

An additional issue occurs when multiple asynchronous lists are started
without a foreground process, here-document that requires a fork,
operandless jobs builtin or wait builtin in between. In that case, dash
never calls wait3() and zombies accumulate. Although the example could
be considered a fork bomb and relies on the child processes getting CPU
time often enough, this may legitimately happen if the loop contains a
read builtin. In FreeBSD sh, I added a check for zombies before forking
the first process of a background job. Some other shells call waitpid()
or similar from a SIGCHLD handler; this reaps zombies faster at the cost
of more complex code (signal handler performing non-trivial work).

-- 
Jilles Tjoelker

^ permalink raw reply	[flat|nested] 3+ messages in thread

end of thread, other threads:[~2013-08-23 12:20 UTC | newest]

Thread overview: 3+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
     [not found] <CAMqPLXWsMhPBjYa3JnCmuO=M6m2F=hSdiEfRx390VKdgC5qxZg@mail.gmail.com>
2013-01-20 12:04 ` Fwd: bug? Spawned childs always remain in zombie state Sjon Hortensius
2013-08-23 10:44   ` Herbert Xu
2013-08-23 12:20     ` Jilles Tjoelker

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.