bashembedded-linuxbusybox

How to flush named pipe(FIFO) in non-blocking mode in busybox shell script?


I tried using "cat" and "dd" commands to flush the FIFO and both commands blocks the operation.

Below are the commands used to flush,

Create FIFO

mkfifo tmp.fifo

Using "cat" command

cat tmp.fifo 

OR even using file descriptor with cat command like,

exec 200<> tmp/fifo; 
cat <&200 > /dev/null

Using "dd" command

dd if=tmp.fifo of=/dev/null

Note:

"dd" command works well (doesn't block) in Linux PC terminal with the help of 'iflag' like,

dd if=tmp/fifo iflag=nonblock of=/dev/null

(!) But this doesn't work with busybox's version of dd. How can I achieve it using busybox?


Solution

  • It's easy to check whether/how this is possible, just by looking at the busybox source: No references to O_NONBLOCK exist anywhere in the busybox codebase.

    Thus: With busybox alone, this is not possible.


    Now, what you can do (if your kernel's behavior is appropriate -- POSIX doesn't specify behavior of named pipes in this mode, leaving it implementation-defined) is open the pipeline with O_RW (so it doesn't need a writer) and perform a blocking read, with another process killing this after a timeout:

    exec 5<>yourpipe
    cat <&5 >/dev/null & cat_pid=$!
    sleep 1
    kill "$cat_pid"
    

    It's an ugly, inefficient, and questionably portable hack -- but without adding extra dependencies (Python, Perl, a tiny C helper), it's what you've got.