Newcomers to Bash programming will sooner or later come across /dev/null and another obscure jargon: > /dev/null 2>&1. It may look confusing but it?s fairly simple to understand and a fundamental part of shell programming. So let?s break it down with step-by-step examples.
To begin, /dev/null is a special file called the null device in Unix systems. Colloquially it is also called the bit-bucket or the blackhole because it immediately discards anything written to it and only returns an end-of-file EOF when read.
Let?s see what happens when we try writing to it with the file redirection operator (>).
# First let’s try writing to this file.$ echo ‘text’ > /dev/null# Upon inspection, we see that the write was successfully. $ echo $?0
The $? symbol is a special variable that always contains the exit status of the previous command; it will be overwritten every time you run a new command. By convention, an exit code of 0 indicates that the previous command was successful while anything greater indicates an error code for that specific program.
For example, if we lookup ls in the man pages, we?ll see that the exit code 1 corresponds to a minor problem.
http://man7.org/linux/man-pages/man1/ls.1.html
Let?s look at another example. Given the following two commands: the first (ls) is a valid command while the second (ls -0) is an invalid command because it contains an illegal option -0.
This is a valid command:
$ lsApplications Documents Library Music Public$ echo $?0
Now let?s look at the invalid command:
$ ls -0ls: illegal option — 0usage: ls [-ABCFGHLOPRSTUWabcdefghiklmnopqrstuwx1] [file …]$ echo $?1
The problem with the second script is that it displays any error messages into STDERR. However for our scripts, we want to suppress error messages. Luckily there?s a hack to do exactly what we want.
Let?s try that again with > /dev/null 2>&1:
$ ls -0 > /dev/null 2>&1$ echo $?1
Notice this time, that we didn?t see any error messages. To break this down, we?re suppressing the error output (stderr) of the ls -0 command, redirect it to standard output (stdout), writing it to /dev/null thereby immediately discarding it. The >& symbol is an operator that copies the output of the first file descriptor (2) and redirects to the output of the second file descriptor (1).
Now let?s see what the numbers in 2>&1 represent by looking at this chart of File Descriptors.
We can verify this by outputting to a regular file instead of /dev/null.
$ ls -0 > /tmp/devnull 2>&1$ echo $?1$ cat /tmp/devnullls: illegal option — 0usage: ls [-ABCFGHLOPRSTUWabcdefghiklmnopqrstuwx1] [file …]
This technique is commonly used to tell whether a command exists, which you can use for handling different operating systems, automatically installing packages, downloading files, and most importantly defending your scripts and systems from unexpected exceptions.
function cmd_exists() { command -v $1 > /dev/null 2>&1}# cmd_exists ls; echo $?# cmd_exists sl; echo $?
Hopefully /dev/null along with output redirection, exit statuses, file descriptors should make sense since they are fundamental to Bash programming. There are many other I/O operators each with their own specific purposes which you can view here: