The _pipe function creates a pipe. A pipe is an artificial I/O channel that a program uses to pass information to other programs. A pipe is similar to a file in that it has a file pointer, a file descriptor, or both and can be read from or written to using the standard library's input and output functions. However, a pipe does not represent a specific file or device. Instead, it represents temporary storage in memory that is independent of the program's own memory and is controlled entirely by the operating system.
_pipe is similar to _open but opens the pipe for reading and writing, returning two file descriptors instead of one. The program can use both sides of the pipe or close the one it does not need. For example, the command processor in Windows NT creates a pipe when executing a command such as:
The standard output descriptor of PROGRAM1 is attached to the pipe's write descriptor. The standard input descriptor of PROGRAM2 is attached to the pipe's read descriptor. This eliminates the need for creating temporary files to pass information to other programs.
The _pipe function returns two file descriptors to the pipe in the pfds argument. The element pfds[0] contains the read descriptor and the element pfds[1] contains the write descriptor. Pipe file descriptors are used in the same way as other file descriptors. (The low-level input and output functions _read and _write can read from and write to a pipe.) To detect the end-of-pipe condition, check for a _read request that returns 0 as the number of bytes read.
The psize argument specifies the amount of memory, in bytes, to reserve for the pipe. The textmode argument specifies the translation mode for the pipe. The manifest constant _O_TEXT specifies a text translation, and the constant _O_BINARY specifies binary translation. (See fopen for a description of text and binary modes.) If the textmode argument is 0, _pipe uses the default translation mode specified by the default-mode variable _fmode.
In multithreaded programs, no locking is performed. The file descriptors returned are newly opened and should not be referenced by any thread until after the _pipe call is complete.
To use the _pipe function to communicate between a parent and a child process, each process must have only one descriptor open on the pipe. The descriptors must be opposites: if the parent has a read descriptor open, then the child must have a write descriptor open. The easiest way to do this is to OR (|) the _O_NOINHERIT flag with textmode. Then, use _dup or _dup2 to create an inheritable copy of the pipe descriptor you want to pass to the child. Close the original descriptor, and spawn the child process. On returning from the spawn call, close the duplicate descriptor in the parent process. For more information, see example 2 below.
In the Windows operating system, a pipe is destroyed when all its descriptors have been closed. (If all read descriptors on the pipe have been closed, writing to the pipe causes an error.) All read and write operations on the pipe wait until there is enough data or enough buffer space to complete the I/O request.