This is basically a negative answer. It appears that neither dd
, nor mbuffer
, nor even pv
works is all cases, in particular if the rate of data generated by the producer can vary a lot. I give some testcases below. After typing the command, wait for about 10 seconds, then type >
(to go to the end of the data, i.e. wait for the end of the input).
zsh -c 'echo foo0; sleep 3; \
printf "Line %060d\n" {1..123456}; \
echo foo1; sleep 5; \
echo foo2' | dd bs=64K | less
Here, after typing >
, one has to wait for 5 seconds, meaning that the producer (zsh script) has blocked before the sleep 5
. Increasing the bs
size to e.g. 32M doesn't change the behavior, though the 32MB buffer is large enough. I suspect that this is because dd
blocks on output instead of going on with the input. Using oflag=nonblock
is not a solution because this discards data.
zsh -c 'echo foo0; sleep 3; \
printf "Line %060d\n" {1..123456}; \
echo foo1; sleep 5; \
echo foo2' | mbuffer -q | less
With mbuffer
, the problem is that the first line (foo0) doesn't appear immediately. There doesn't seem to be any option to enable line-buffering on input.
zsh -c 'echo foo0; sleep 3; \
printf "Line %060d\n" {1..123456}; \
echo foo1; sleep 5; \
echo foo2' | pv -q -B 32m | less
With pv
, the behavior is similar to dd
. Worse, I suspect that it does wrong things to the terminal since sometimes less
can no longer receive input from the terminal; for instance, one cannot quit it with q
.
stdbuf
tool appears to be asize
parameter. I'm not sure if it works though.