Los pipes (tuberías, en inglés) son una forma de redirección que se utiliza en los sistemas operativos Linux y de la familia Unix para enviar la salida de un programa a la entrada de otro (para continuar el procesamiento). La redirección consiste en transferir la salida estándar a otro destino, como un programa o archivo, en lugar de ser mostrado por pantalla (salida estándar por defecto en una consola). De esta forma un pipe puede ser visto como un pipeline de comandos. Es decir, una secuencia de comandos por los cuales se procesa un dato. Esto significa que los pipes conforman un mecanismo de comunicación entre procesos (IPC), ya que consisten en un mecanismo de comunicación entre procesos de un pipeline.

Este artículo presenta el concepto de "named pipes" y el uso de la herramienta mkfifo.



Los pipes se identifican con una barra vertical (|). Esta barra representa la conexión entre la salida estándar del comando actual y la entrada estándar del comando siguiente.

Veamos un ejemplo básico: deseo recuperar sólo los archivos y directorios que contengan la palabra "samba" desde el listado del directorio /etc:

emi@hal9000:~$ ls -l /etc | grep samba
drwxr-xr-x  2 root root    4096 Nov  7 08:41 samba

La salida de ls es reenviada a grep para su filtrado.

Lógicamente podría haber obtenido el mismo resultado utilizando comodines o find. Sin embargo el objetivo del ejemplo es ilustrar el uso de pipes:

emi@hal9000:~$ ls -ld /etc/*samba*
drwxr-xr-x 2 root root 4096 Nov  7 08:41 /etc/samba
emi@hal9000:~$ find /etc -maxdepth 1 -name samba -exec ls -ld {} \;
drwxr-xr-x 2 root root 4096 Nov  7 08:41 /etc/samba

Esta forma de pipe sin nombre es la forma tradicional de conectar procesos de forma unidireccional en los sistemas Unix. Los datos en el pipe se procesan en orden FIFO (first in, first out).

Ahora bien, esta forma básica de pipe permite establecer la comunicación (implementando efectivamente un mecanismo de IPC) entre procesos de una misma sesión. Más precisamente entre sub-procesos (procesos hijos) de una sesión. ¿Qué pasa si deseamos establecer un pipe entre procesos de sesiones independientes e incluso distintos usuarios, pero dentro de un mismo sistema? Para este fin se dispone de "named pipes" (tubería nombrada, digamos).

Un "named pipe" es una extensión a los pipes tradicionales. Estos pueden durar todo lo que dure el sistema encendido, mientras que los pipes tradicionales duran sólo lo que dura el proceso que genera la salida. Sin embargo pueden ser borrados si no se usan más. A tal fin utilizan el sistema de archivos, tanto para ser identificados, como para establecer los permisos de acceso al mismo. Aparecen listados como archivos, aunque su tipo es especial. Basta con pasar la ruta al pipe para poder ser leído por cualquier proceso desde cualquier sesión (siempre que se cuente con los permisos de lectura necesarios).

En los sistemas operativos GNU/Linux, la herramienta mkfifo permite crear un named pipe, sólo se necesita una ruta o nombre de archivo como parámetro:

emi@hal9000:~$ mkfifo npipe

Se observa que, por defecto, sólo el usuario actual puede escribir en el pipe, y todo el mundo tiene acceso de lectura al mismo:

emi@hal9000:~$ ls -l npipe
prw-r--r-- 1 emi emi 0 Dec  2 14:05 npipe
emi@hal9000:~$ file npipe
npipe: fifo (named pipe)

Además, el tipo de archivo es "fifo (named pipe)". Esto significa que no es un archivo regular, sino el nombre con el que se identifica a un pipe.

Veamos un ejemplo gráfico para entender cómo es posible comunicar entre procesos de diferentes sesiones:

En la terminal posterior se ha creado un pipe al cual se le envía la salida de ls. Para retomar el control de la sesión se lanza en segundo plano. Esto se debe a que hasta que ningún proceso lea el pipe, el proceso quedará "colgado" (hang).

Se observa además, que el pipe no ocupa espacio en disco (0 bytes). Hablando en criollo, esto significa que la salida está "contenida" en el proceso que la genera, hasta que alguien lea desde el named pipe.

Sólo cuando otro proceso lee el pipe, la salida es transmitida desde el proceso que escribe al que lee. Y una vez transmitida toda la salida, el proceso que escribe finaliza. Por esta razón es conveniente utilizar named pipes en lugar de archivos: no ocupan espacio en disco. Los datos se transfieren directamente en memoria desde la salida del proceso que escribe el named pipe hacia la entrada del proceso que lo lee.

Si no se desea utilizar más un named pipe, es posible eliminarlo con rm como cualquier archivo convencional.

Referencias


Tal vez pueda interesarte


Compartí este artículo