Summary: | shells/zsh: hangs upon '>(command)' redirections | ||
---|---|---|---|
Product: | Ports & Packages | Reporter: | danielsh |
Component: | Individual Port(s) | Assignee: | Baptiste Daroussin <bapt> |
Status: | Closed FIXED | ||
Severity: | Affects Only Me | ||
Priority: | Normal | ||
Version: | Latest | ||
Hardware: | Any | ||
OS: | Any |
Description
danielsh
2013-07-01 20:30:00 UTC
Responsible Changed From-To: freebsd-ports-bugs->bapt Over to maintainer (via the GNATS Auto Assign Tool) In FreeBSD PR ports/180178, you wrote: > zsh hangs when commands involving '>(command)' are involved: > [[[ > % ssh loki.apache.org 'zsh -fc "echo >(wc -l)"' > /tmp/zshJHGd5f > ]]] > It responds to ^C and ^Z but not to ^D or ^\. > Using ':' or 'true' inside the parentheses yields the same behaviour. A construct like >(CMD) is called process substitution and expands to a pathname that, when opened, writes to the standard input of CMD. In zsh (but not bash), the shell also waits for CMD to terminate when the outer command is done. The similar <(CMD) expands to a pathname that reads from the standard output of CMD; the shell does not wait for CMD to terminate. Depending on whether the full /dev/fd was available when zsh was compiled (look for zsh_cv_sys_path_dev_fd in configure.ac), zsh uses either /dev/fd or a fifo to generate the pathname. There is a special case for redirecting to or from a process substitution which uses an unnamed pipe. If zsh uses a fifo, the child process will block until the generated pathname is opened. If the pathname is never opened, such as when you echo it, the child process blocks indefinitely. It might be possible to fix this in zsh by opening the fifo with O_NONBLOCK before deleting it. If zsh uses /dev/fd, such as when the port is compiled using poudriere, process substitution does not work unless the full /dev/fd (fdescfs) is mounted (by default, only /dev/fd/0, /dev/fd/1 and /dev/fd/2 are available which is not good enough). -- Jilles Tjoelker |