On Linux and Unix-based operating systems, pipes are very useful since they are a simple way to achieve IPC (inter-process communication). When we connect two processes in a pipeline, the output of the first one is used as the input of the second one. To build a so called “anonymous” pipe, all we have to do is to use the
| operator. Anonymous, or unnamed pipes last just as long as the processes they connect. There is, however, another type of pipe we can use: a FIFO, or named pipe. In this article we will see how named pipes work and in what they are different from the standard pipes.
In this tutorial you will learn:
- What is a named pipe
- How to create a named pipe
- How to recognize a named pipe
- How named pipes work
- How to delete a named pipe
Software requirements and conventions used
|Category||Requirements, Conventions or Software Version Used|
|Software||The utilities used in this tutorial are available by default|
|Other||Root permissions to perform administrative tasks|
|Conventions||# - requires given linux-commands to be executed with root privileges either directly as a root user or by use of |
$ - requires given linux-commands to be executed as a regular non-privileged user
A quick reminder of how pipes work
In a previous tutorial we already saw how pipes work and what they can be used for in the Introduction to shell redirections, but let’s just make a quick recap. On our scripts or in our interactive shell sessions, we can use the pipe operator (
|) to connect two processes together, so that the standard output (stdout) of the process at the left side of the pipe is used as the standard input (stdin) of the process at the right side of it. Here is a quick and trivial demonstration:
$ echo "goot" | tr 't' 'd' good
In the example above, the output of the
echo command is used as the standard input of the
tr one. For those of you who don’t know, the
tr command can be used to translate or delete characters: here we used it to substitute all the occurrences of the
t character with the
d one. The result of the two commands piped together in what is called a pipeline, is the string “good”.
What we used in the example above, is called an unnamed pipe. Such type of pipe exists only until the commands are executed, and cannot be accessed afterwards. If we want to build a pipe and be able to reference it after its use we must use the so called named pipes, let’s see what they are, and how they work.
What is a named pipe?
On Unix-based operating system like Linux, a named pipe, or FIFO (first-in, first-out), is a “special” kind of file used to establish a connection between processes. Unlike a “standard” pipe, a named pipe is accessed as part of the filesystem, just like any other type of file. Once created, a named pipe, will indeed appear as a standard file; it, however, will always appear to be empty, since it will not be used to “store” information. The data which will pass through the pipe will be managed directly by the kernel: the FIFO file will is just used as a reference.
Creating a named pipe
To create a named pipe, in modern Linux-based operating systems, all we must do is to use the
mkfifo command. In its most basic usage, all we have to pass as argument to the program is the name we want to use for the FIFO file. For instance, to create a named pipe called
pipe0, we would run:
$ mkfifo pipe0
If desired, a named pipe can also be created with a specific set of permissions using the
-m option (short for
--mode) of the
mkfifo command. The option accepts the file permission bits as argument, so for example, to create a named pipe with
644 permissions, we would run:
$ mkfifo -m 644 pipe0
Let’s take a look at the file that was created as the result of running the command above:
$ ls -l pipe0 prw-r--r--. 1 egdoc egdoc 0 Dec 15 11:55 pipe0
Here we ran the
ls command with the
-l option, so that the long listing format was used. In the output of the command we can see that the first letter which appears before the permissions bits is a
p: this indicates that the file is indeed a named pipe.
Using a named pipe
We know how “standard” pipes work: the standard output of the process at the left of the pipe
| is used as the standard input of the one at its right. Named pipes works similarly. Let’s demonstrate it. The first thing we want to do is to write something to the named pipe. To do that we can use a simple redirection; we open a new terminal emulator and we run the following command:
$ echo "input message" > pipe0
Something apparently unexpected happens just as soon as we press enter: the command appears to hang. This is due to how named pipes work: for data to be passed through a named pipe, the FIFO file must be opened on both ends, by a process who is writing to it, and by at least one who wants to read from it.
In this case, since there is nothing that is “reading” from the pipe and “consuming” its content, we say that the pipe is blocked. To demonstrate this, let’s open another terminal emulator and use the
cat command to “read” from the named pipe:
$ cat pipe0 input message
As you can see, the message we wrote to the named pipe has been printed on screen and on the terminal we used to write to the pipe, everything is back to normal (the command is not hanging anymore, and the shell prompt appears again). As you can see in the clip below, the same thing happens if we first open the pipe for reading, and there is nothing writing to it:
Once again, nothing is actually written on the
pipe0 file, and once the content of a named pipe is “consumed” the pipe is cleared. One of the advantages of named pipes over standard pipes is that the writer and reader processes doesn’t have to start at the same time.
Deleting a named pipe
Since a named pipe is just a file, to remove one, assuming we have the right permissions to perform the action, we can use the
rm command. To remove the pipe we created in the previous examples, we would therefore run:
$ rm pipe0
In this article we learned how named pipes work on Linux. We saw how they are accessed as part of the filesystem, since they appear to be just like any other file. We saw how to create named pipes using the mkfifo command, what are their peculiarity, and an example of their usage. Finally, we saw how to delete a named pipe.