I/O stream redirection in a Linux shell. How does

2020-04-08 12:23发布

问题:

Currently I'm coding a small shell (redirection, pipes, exec, etc.). Been trying to figure out the steps the Linux shell takes in addressing I/O redirection.

Some questions on what I need help on:

  1. In which direction does the shell read from the command line when it is looking for the redirection? Left to right or the opposite? Uses recursion?

  2. What are the cases the shell needs to look for? (not sure if there are many or just a couple that can encompass a lot of variation)

Anyways, some I can think of are (correct me if I'm wrong):

cmd > file1       # stdout of cmd goes to file

cmd file1 > file2 # stdout of cmd with file1 as an argument goes to file2

cmd file2 < file1 # stdin on file2 comes from file1

Now I don't know the process on the following cases (as in how the shell looks for and handles these). The steps the shell takes are unbeknown to me

cmd file2 > file3  < file1 # using "tee" in place of "cmd" I don't know
                           # how to do the dups and when to exec

cmd file2 < file3 > file1  # same ^

回答1:

As long as you only redirect stdin and stdout, the order in which the redirections are processed don't matter so the last two examples are exactly the same.

BASH processes IO redirection from left to right.

> cmd1 > file 2>&1
> cmd2 2>&1 > file

These two are different. In the first case, I bind stdout to file and then bind stderr to stdout: Both stderr and stdout now go into the file.

In the second case, I bind (the child's) stderr to stdout (of the parent) and then I find the child's stdout to file. The result is that you now get the child's stderr output on stdout and the stdout goes to the file. This is useful for processing stderr in a pipe, for example.

If you look at the source code of BASH, you can see that the execution of a command is split in several steps:

  • Replace all variables
  • Split input into "words"
  • Process IO redirection (and remove the involved words)
  • Create a new child process with the correct IO setup and the remaining words as arguments.