STREAMS-UX Programmer's Guide (February 2007)

Modules and Drivers
Flush Handling
Chapter 4
83
Flush Handling in a Pipe
Message flushing in a pipe is complicated in nature because the write queue of one end of stream head is
connected to the read queue of the other, and vice versa. As a result, FLUSHW and/or FLUSHR bits have to
switched appropriately to ensure that wrong queues are not flushed. The point of switching is called the
midpoint of a pipe. Midpoint in a STREAMS based pipe is where the write queues point to the read queues.
For example, when a stream head receives an M_FLUSH message with FLUSHW set, it turns around on the write
side of the stream. Write queues of all the modules will be flushed until it reaches a midpoint where FLUSHW is
switched to FLUSHR. Then onwards, the read queues of all the modules including read queue of stream head
will be flushed.
STREAMS framework sets the MSGNOLOOP flag in b_flag the very first time when an M_FLUSH reaches a
stream head. This is done to ensure that it is not reflected back to the other side of the stream when this
message reaches the other stream head.
The midpoint of a stream can be difficult to determine if modules are being pushed from both ends of the pipe.
To make the midpoint deterministic, STREAMS provides the pipemod module. This module must be pushed
onto a pipe for message flushing to work properly. It defines the midpoint of a stream and can be pushed from
either end of a pipe. The only requirement is that pipemod must be the first module pushed onto a pipe.
The pipemod module handles only M_FLUSH messages. All other messages are passed to the next module in
the stream using putnext() utility.
Summary of pipemod functionality:
1. If pipemod receives an M_FLUSH message with FLUSHW bit set, it shuts off the FLUSHW and sets FLUSHR and
pass it to the next module.
2. If FLUSHR bit is set in an M_FLUSH message, then pipemod unsets the FLUSHR bit and sets the FLUSHW bit
before passing to the next module.
3. If FLUSHRW is set then this message is not processed, instead it is passed to the next module.