I'm reading an example bash shell script:


# This script makes a backup of my home directory.

cd /home

# This creates the archive
tar cf /var/tmp/home_franky.tar franky > /dev/null 2>&1

# First remove the old bzip2 file.  Redirect errors because this generates some if the archive
# does not exist.  Then create a new compressed file.
rm /var/tmp/home_franky.tar.bz2 2> /dev/null
bzip2 /var/tmp/home_franky.tar

# Copy the file to another host - we have ssh keys for making this work without intervention.
scp /var/tmp/home_franky.tar.bz2 bordeaux:/opt/backup/franky > /dev/null 2>&1

# Create a timestamp in a logfile.
date >> /home/franky/log/home_backup.log
echo backup succeeded >> /home/franky/log/home_backup.log

I'm trying to understand the use of "/dev/null 2>&1" here. At first, I thought this script uses /dev/null in order to gracefully ignore errors, without causing the script to crash (kind of like try catch exception handling in programming languages). Because I don't see how using tar to compress a directory into a tar file could possibly cause any type of errors.

  • 5
    Redirecting to /dev/null won't prevent crashing, but will clean up the stdout and stderr output streams. tar could cause errors in a variety of ways. You might not have write access, the file might already exist, etc. – Sparhawk Mar 14 '14 at 4:27
  • 5
    Just a trick to avoid unnecessary output. As for why tar can cause errors: because the target directory does not exist, because the source doesn't, because you don't have write access to the target, or read to the source, because tar is not in your $PATH, because tar crashed (you never know), because there's no space left on the device, because the tar version changed and now requires different syntax, because the disk caused an I/O error. I'm sure you could find more. – terdon Mar 14 '14 at 5:48

No, this will not prevent the script from crashing. If any errors occur in the tar process (e.g.: permission denied, no such file or directory, ...) the script will still crash.

This is because of using > /dev/null 2>&1 will redirect all your command output (both stdout and stderr) to /dev/null, meaning no outputs are printed to the terminal.

By default:

stdin  ==> fd 0
stdout ==> fd 1
stderr ==> fd 2

In the script, you use > /dev/null causing:

stdin  ==> fd 0
stdout ==> /dev/null
stderr ==> fd 2

And then 2>&1 causing:

stdin  ==> fd 0
stdout ==> /dev/null
stderr ==> stdout
| improve this answer | |
  • 16
    probably not too important, but what is fd? – kev Jul 28 '16 at 0:13
  • 7
    @kev en.wikipedia.org/wiki/File_descriptor – Alex Bitek Sep 11 '16 at 10:56
  • 10
    Why does: CMD > /dev/null 2>&1 work but CMD 2>&1 > /dev/null still give me STDERR? – dbmikus Jan 14 '17 at 16:39
  • 4
    Recommended: Use 2>& 1 in code examples to stress that the number and the ampersand are considered to be part of the redirection operator. It is common for redirection to a file to have a space between > and /path/to/file, redirection to a file descriptor is essentially the same thing. – Henk Langeveld May 7 '18 at 10:25
  • 4
    @dbmikus You should have asked that as a separate question :) Nevertheless, the first one says "redirect writes to file descriptor 1 to /dev/null, and then redirect writes to file descriptor 2 to the same place as the writes to file descriptor 1 are going" . The second one says "redirect writes to file descriptor 2 to the same place as the writes to file descriptor 1 are going, and then redirect writes to file descriptor 1 to /dev/null". I also struggled with this. Idea from a coworker and from unix.stackexchange.com/a/497215/12428 for a detailed description. – törzsmókus May 23 '19 at 12:45

I'm trying to understand the use of "> /dev/null 2>&1" here.

(note that I added the redirection before /dev/null in your question.)

The above would redirect the STDOUT and STDERR to /dev/null. It works by merging the STDERR into the STDOUT. (Essentially all the output from the command would be redirected to the null device.)

... without causing the script to crash (kind of like try catch exception handling in programming languages).

It's not quite like a try/catch or anything. It simply silences any sort of output (including error) from the command.

Because I don't see how using tar to compress a directory into a tar file could possibly cause any type of errors.

It could result in errors for a number of reasons, including:

  • Inadequate permissions on the file(s) you're attempting to archive or on the file that you're attempting to write to
  • Lack of disk space in order to create the archive
| improve this answer | |

When you run CMD > /dev/null 2>&1

STDOUT redirects to /dev/null, and then STDERR redirects to THE ADDRESS of STDOUT, which has been set to /dev/null , consequently both STDOUT and STDERR point to /dev/null

Oppositely, when you run CMD 2>&1 >/dev/null

STDERR redirects to THE ADDRESS of STDOUT (File descriptor 1 in that moment, or /proc/self/fd/1), and then STDOUT redirects to /dev/null , but STDERR keeps redirecting to fd1!! As a result the normal output from STDOUT is discarded, but the errors coming from STDERR are still being written onto the console.

| improve this answer | |
  • 2
    A more brief way to redirect both stdout and stderr to /dev/null is: command &> /dev/null. – TNT Jan 16 at 18:24
  • 2
    &> /dev/null did not work for me in a script file, outputting the whole stderr after the script is completed, but > /dev/null 2>&1 worked well. – vstepaniuk Feb 1 at 13:20

To understand easily, write it out explicitly. Below is an example command that tries to remove a nonexisting file (to simulate an error)

rm nonexisting.txt 1>/dev/null 2>/dev/null
  • 1 is for stdout. Sends info logs to /dev/null
  • 2 is for stderr. Sends error logs to /dev/null

Below are couple of enhancements.

Enhancement 1 : You can replace 1> with just >. This is because 1 is the default stdout and you can ignore mentioning defaults.

 rm nonexisting.txt >/dev/null 2>/dev/null

Enhancement 2 : You can replace the 2nd /dev/null with &1. This is because /dev/null is already by pointed to by stdout 1.

rm nonexisting.txt 1> /dev/null 2> &1

My suggestion : Stick to the first option. Write out the commands explicitly instead of using pointers. Takes little effort but much easier to understand and explain.

| improve this answer | |
  • 1
    this is actually quite the better answer, as it is a "this means that", rather than a generic "this does that" – NONONONONO Oct 2 at 6:54

Bash I/O Redirection

redirection definition

This code:

command > filename 2>&1
  • > filename redirects stdout to filename
  • (2>&1) redirects stderr to stdout (now filename)

(file descriptor 1 is the default, so > is short for 1>)

Here is the ABSG explanation (Ch. 20).

Another common example:

command >>/dev/null 2>&1

redirects stderr and stdout to /dev/null ... which means to nowhere. Things sent to /dev/null are not saved, cached, or remembered in any way.

They are just sent to 'nowhere' and forgotten. This is a way of running programs and making sure they produce NO output and will never be seen on the command line or in a log file.

I see this type of question quite a bit ... mainly because I've had to look it up myself since I haven't been coding in years. Here is some handy information from the ABSG:

"Redirection simply means capturing output from a file, command, program, or script and sending it as input to another file, command, program, or script."

# Redirects stderr to stdout.

command >>filename 2>&1
# Appends both stdout and stderr
#+  to the file "filename" ...

ABSG: Advanced Bash Scripting Guide: The Chapter 20 link above is a link to the I/O redirection page of the open source tldp.org document called the Advanced Bash Scripting Guide by Mendel Cooper. It is listed as "An in-depth exploration of the art of shell scripting " and I absolutely agree. It is a terrific resource and has tons of answers to all sorts of crazy situations.

Other Valuable Resources: There are many valuable resources in the current/maintained section (in several handy formats like html, pdf, text, etc) on the Linux Documentation Project Guides page. Here are a few I have found useful:

| improve this answer | |
  • 2
    No, redirections are handled left to right. In your example, standard output is redirected to filename, then standard error is redirected to wherever standard output is currently going (to filename). If it was the opposite way around, standard error would end up on the terminal while only standard output was redirected to filename. Also, in command >file1 2>file2, file2 would not be created if file1 could not be created (no matter whether file1 and file2 were actually totally different pathnames). – Kusalananda Jul 23 '19 at 22:41

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

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