I/O Redirection: Swap stdout And stderr

Basic Pipe Usage

Programs which write to standard output are good members of a pipeline:

Couting directory entries below /etc
$ find /etc | wc -l
find: `/etc/cron.daily': Permission denied
find: `/etc/sudoers.d': Permission denied
find: `/etc/cron.weekly': Permission denied
... 18 - 3 = 15 errors on stderr omitted ...

Basic Pipe Usage: What The Shell Does

  • Allocates pipe

  • Duplicates find ‘s stdout to go into the pipe’s write-end

  • Duplicates wc ‘s stdin to come from the pipe’s read-end


And How Do I Count Lines On stderr?

Obviously: standard output and standard error need to be swapped!

$ find /etc 3>&1 1>&2 2>&3 | wc -l
... stderr omitted ...


  1. A>&B: make file descriptor A refer to the object that is pointed to by file descriptor B

  2. Redirections are applied/evaluated left to right


Create file descriptor 3 to point to stdout (which goes into the pipe)


Redirect stdout to go where stderr currently points to (i.e. the terminal)


Redirect stderr to where file descriptor 3 currently points to (the pipe)


More Tricks

The original find output (the entries that it finds) still go on the terminal. Silence that by discarding output on 1:

$ find /etc 3>&1 1>&2 2>&3 1>/dev/null | wc -l

Being overly correct, we can close file descriptor 3 after all redirections have been applied:

$ find /etc 3>&1 1>&2 2>&3 1>/dev/null 3>- | wc -l