0

How to explain the output of cat /etc/passwd | cat </etc/issue?

In this case, the second cat receives contents from /etc/passwd as $STDIN and again /etc/issue is redirected. Why there is only /etc/issue left?

What's more, cat </etc/passwd </etc/issue only outputs the contents in /etc/issue. Is /etc/passwd overwritten?

I am not looking for a solution how to cat two files, but confused with how pipeline works.

2 Answers 2

3

Piping and redirection are processed from left to right.

So first the input of cat is redirected to the pipe. Then it is redirected to /etc/issue. Then the program is run, using the last redirection, which is the file.

When you do cat <file1 <file2, stdin is first redirected to file1, then it is redirected to file2. Then the program is run, and it gets its input from the last redirection.

It's like variable assignments. If you do:

stdin=passwd
stdin=issue

The value of stdin at the end is the last one assigned.

This is explained in the bash documentation, in the first paragraph of the section on Redirection:

Before a command is executed, its input and output may be redirected using a special notation interpreted by the shell. Redirection may also be used to open and close files for the current shell execution environment. The following redirection operators may precede or appear anywhere within a simple command or may follow a command. Redirections are processed in the order they appear, from left to right.

(emphasis mine). I assume it's also in the POSIX shell specification, I haven't bothered to look it up. This is how Unix shells have always behaved.

2
  • Thanks for you answer. Can you give some details (proof) why it behaves this way? For example, where can I find a rule stating that Piping and redirection are processed from left to right.?
    – eccstartup
    Commented Jul 1, 2014 at 11:26
  • 1
    I've copied the section of the documentation.
    – Barmar
    Commented Jul 1, 2014 at 14:43
0

The pipe is created first: the standard output of cat /etc/passwd is sent to write side of the pipe, and the standard input of cat </etc/issue is set to the read side of the pipe. Then the command on each half of the pipe is processed. There's no other I/O redirection on the LHS, but on the RHS, the standard input is redirected so it comes from /etc/issue. That means there's nothing actually reading the read end of the pipe, so the LHS cat is terminated with a SIGPIPE (probably; alternatively, it writes data to the pipe but no process ever reads it). The LHS cat never knows about the pipe input — it only has the the file input for its standard input.

Not the answer you're looking for? Browse other questions tagged or ask your own question.