I would like to exchange data between 2 processes (A
and B
) using 2 named pipes (a2b
and b2a
) as follows:
A
creates the a2b
and b2a
pipes using mkfifo(3)
.A
starts process B
(either using fork()
, exec*()
or even system()
)A
waits until B
open()
s a2b
and b2a
A
write()
s data to a2b
B
read()
s data from a2b
B
write()
s data to b2a
A
read()
s data from b2a
How can I make process A
wait until process B
open()
s the other ends of the named pipes? -- i.e. How do I implement step 3?
EDIT 1: As mentioned by @EJP, it is possible to implement step 3 using read/write/select. However, I would like to know if there are other approaches.
Processes can use the open() function to access named pipes and then use the regular I/O functions for files, such as read() , write() , and close() , when manipulating named pipes. Buffered I/O functions can also be used to access and manipulate named pipes.
An unnamed pipe is a direct connection between two commands running in the same terminal. If we want to send output from a command in one terminal to another command in a different terminal, we can use a named pipe, or FIFO. FIFO stands for first in, first out. This is a pipe that exists in the file system.
Unnamed pipes They can be used even among unrelated processes. They can be used only between related processes. They are bidirectional, which means the same FIFO can be read from as well as written into.
Also unlike their Unix counterparts, named pipes are volatile (removed after the last reference to them is closed).
The behavior of POSIX open is specified for FIFOs. If you're using Linux, man 7 fifo
has some nice discussion:
The kernel maintains exactly one pipe object for each FIFO special file that is opened by at least one process. The FIFO must be opened on both ends (reading and writing) before data can be passed. Normally, opening the FIFO blocks until the other end is opened also.
A process can open a FIFO in nonblocking mode. In this case, opening for read-only succeeds even if no one has opened on the write side yet and opening for write-only fails with ENXIO (no such device or address) unless the other end has already been opened.
So you have two options:
open
call will block till the other end is open, or open
call until it succeeds.If your requirements permit, you can skip a named pipe (FIFO) altogether and just use a pipe
. The child process inherits open file descriptors to each end of the pipe and can use either one as needed (don't forget to close the unneeded descriptor).
However, considering your end goal is bi-directional communication, might I suggest a (unix domain) socket
and some IO multiplexing strategy (select
, poll
, epoll
, kqueue
, etc.)?
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With