That's shell dependant and not documented AFAICS. In ksh
and bash
, in the first case, foo
will share the same stdin as bar
. They will fight for the output of echo
.
So for instance in,
$ seq 10000 | paste - <(tr 1 X)'
1 X
2 X042
3 X043
4 X044
5 X045
[...]
You see evidence that paste
reads every other block of text from seq
's output while tr
reads the other ones.
With zsh
, it gets the outer stdin (unless it's a terminal and the shell is not interactive in which case it's redirected from /dev/null
like in cmd &
). ksh
(where it originated), zsh
and bash
are the only Bourne-like shells with support for process substitution AFAIK.
In echo "bla" | bar < <(foo)
, note that bar
's stdin will be the pipe fed by the output of foo
. That's well defined behaviour. In that case, it appears that foo
's stdin is the pipe fed by echo
in all of ksh
, zsh
and bash
.
If you want to have a consistent behaviour across all three shells and be future-proof since the behaviour might change as it's not documented, I'd write it:
echo bla | { bar <(foo); }
To be sure foo
's stdin is also the pipe from echo
(I can't see why you'd want to do that though). Or:
echo bla | bar <(foo < /dev/null)
To make sure foo
does not read from the pipe from echo
. Or:
{ echo bla | bar 3<&- <(foo <&3); } 3<&0
To have foo
's stdin the outer stdin like in current versions of zsh
.
| foo | bar
or| bar <(foo)
? – Volker Siegel Sep 09 '14 at 21:03