Zsh Mailing List Archive
Messages sorted by: Reverse Date, Date, Thread, Author

fd used for saving redirected fds leaked to child processes



In:

mkfifo fifo
zsh -c '{ echo GO > fifo & echo $!; } > pid; echo done' | cat

"cat" hangs until some process  open the fifo in read mode, even
though that "echo GO > fifo" command was run in background and
"done" is output straight away.

What we see is the child zsh process opening the "fifo" having
a fd open on the pipe to cat:

zsh     28400 chazelas   12w  FIFO   0,10      0t0  125690 pipe 28399,cat,0r

I think that fd was the one that was dupped from stdout by its
parent to /save/ stdout before doing the > pid redirection (so
it can be used to restore stdout after the command group
returns).

That fd is not needed/used in the child so should be closed
there.

(here, the work around and more obvious way to do it is with
zsh -c 'echo GO > fifo & echo $! > pid; echo done' | cat
that was just an example to illustrate the problem).

bash and dash seem to also have the problem. pdksh, ksh93 and
yash are OK. Looking at strace outputs, they seem to be closing
those fds in the children.

The Bourne shell and rc are OK, but only because they don't use
a dupped fd to "save" stdout when redirecting compound commands.
They run the compound command in a subshell.

Note that those fds have the CLOEXEC flag, so the circumstances
in which it becomes a problem are few.

-- 
Stephane



Messages sorted by: Reverse Date, Date, Thread, Author