Beim Senden an eine benannte Pipe wird der Prozess unerwartet beendet

Beim Senden an eine benannte Pipe wird der Prozess unerwartet beendet

Ich habe zwei Prozesse und eine benannte Pipe.

Ein Prozess liest aktiv aus der Pipe und ein Prozess sendet kontinuierlich Daten an die Pipe.

Der an die Pipe gesendete Befehl ist der folgende:

sudo iotop -b -P > diskfifo

Der Leser hingegen führt einfach eine Schleifenleseoperation auf der Pipe aus

pipe=./diskfifo

while read line <$pipe
do
    if [[ "$line" == 'quit' ]]; then
        break
    fi
    echo $line
done

Problem: Der iotop-Befehl stoppt manchmal nach einer bestimmten Anzahl von Iterationen und ich kann nicht herausfinden, warum.

Mir ist jedoch aufgefallen, dass der iotop-Befehl nicht stoppt, wenn ich die Menge der gesendeten Daten reduziere.

Antwort1

In jeder Iteration Ihrer Schleife readwird die Pipe zum Lesen geöffnet, eine Datenzeile gelesen und dann geschlossen.

Wenn iotopversucht wird, in die Pipe zu schreiben, während readnicht aktiv daraus gelesen wird, erhält es ein PIPESignal, da es versucht, in eine Pipe zu schreiben, aus der niemand liest. Die Standardaktion nach dem Empfang des PIPESignals besteht darin, dass der Prozess beendet wird.

Anstatt die Pipe zum Lesen in der Schleife zu öffnen und zu schließen (und zu hoffen, dass iotopnicht in die Pipe geschrieben wird, während nicht aus ihr gelesen wird), leiten Sie die Eingabe von der Pipe zur Schleife selbst um:

pipe=./diskfifo

while read word; do
    [ "$word" = 'quit' ] && break
    printf '%s\n' "$word"
done <"$pipe"

Dadurch bleibt die Pipe für die gesamte Dauer der Schleife geöffnet. Jeder Aufruf von readwürde seinen Standardeingabestrom von der Standardeingabe der Schleife erben, die mit der Pipe verbunden ist.


Eine mögliche andere Formulierung der Schleife:

while read word && [ "$word" != 'quit' ]; do
    printf '%s\n' "$word"
done <"$pipe"

verwandte Informationen