Ich habe zwei Bash-Skripte, die versuchen, Hosts zu überprüfen, die aktiv sind:
Skript 1:
#!/bin/bash
for ip in {1..254}; do
ping -c 1 192.168.1.$ip | grep "bytes from" | cut -d" " -f 4 | cut -d ":" -f 1 &
done
Skript 2:
#!/bin/bash
for ip in {1..254}; do
host=192.168.1.$ip
(ping -c 1 $host > /dev/null
if [ "$?" = 0 ]
then
echo $host
fi) &
done
Da ich einen großen Bereich überprüfe, möchte ich jeden Ping-Befehl parallel verarbeiten. Mein zweites Skript scheint jedoch fehlgeschlagene Verzweigungsversuche aufgrund von Ressourcenbeschränkungen nicht erneut zu versuchen. Dies führt dazu, dass das zweite Skript inkonsistente Ergebnisse aufweist, während mein erstes Skript konstante Ergebnisse liefert, obwohl beide zeitweise nicht verzweigen. Kann mir das jemand erklären? Gibt es überhaupt eine Möglichkeit, ausgefallene Gabeln erneut zu versuchen?
bash
shell-script
fork
subshell
MykelXIII
quelle
quelle
apt-get install fping
: - / (odernmap -sP
)parallel
davon, dass Sie Dienstprogramme (z. B. ) verwenden, um dies für Sie zu tun, müssen Sie nachverfolgen, von welchen Kindern Sie erzeugt haben (Sie erhalten die PID$!
, warten Sie, bis sie beendet werden (und finden Sie ihren Beendigungscode heraus)wait
. usw. PersönlichAntworten:
Es gibt bereits eine Antwort, die ein verbessertes Code-Snippet für die Aufgabe liefert, auf die sich die ursprünglichen Posterfragen bezogen, während sie möglicherweise noch nicht direkter auf die Frage geantwortet hat.
Die Frage betrifft Unterschiede von
Lassen Sie uns diese Unterschiede überprüfen, indem wir 2 Tests ausführen
Ausgänge
während
gibt so etwas aus wie:
** Testergebnisse:**
In diesem Test (der nur a
sleep 2
ausführt) unterscheidet sich die Subshell-Version tatsächlich, da zwei untergeordnete Prozesse (dh zweifork()
/exec
Operationen und PID) und damit mehr als der direkte Hintergrund des Befehls verwendet würden.In der
script 1
Frage war der Befehl jedoch kein einzelner,sleep 2s
sondern einpipe
von 4 Befehlen, die wir in einem zusätzlichen Fall testenergibt dies
und zeigt, dass das in der Tat
script 1
eine viel höhere Belastung in Bezug aufPIDs
undfork()
s wäre.Als grobe Schätzung hätte das Skript etwa 254 * 4 ~ = 1000 PIDs und damit sogar mehr als
script 2
bei 254 * 2 ~ = 500 PIDs verwendet. Ein Problem, das aufgrund der Erschöpfung der PIDs auftritt, scheint noch unwahrscheinlich, da höchstens Linux-Boxengibt Ihnen 32x mal die auch für Fall benötigt PIDs
script 1
und die Prozesse / beteiligten Programme (dhsed
,ping
scheinen, usw.) auch unwahrscheinlich , dass die inkonstant Ergebnisse zu verursachen.Wie von Benutzer @derobert erwähnt, bestand das eigentliche Problem hinter dem Fehler darin,
scripts
dass derwait
Befehl fehlte. Dies bedeutet, dass nach dem Hintergrund der Befehle in der Schleife das Ende des Skripts und damit die Shell dazu führte, dass alle untergeordneten Prozesse beendet wurden.quelle
wait
gibt es eindeutig ein Rennen , da es keine Garantie dafür gibt, die erzeugten Unterprozesse nicht vorzeitig zu beenden ..... Das Ende ist, nachdem das Skript die for-Schleife durchlaufen hat ...script 1
liefert bessere Ergebnisse, weil (a) jede Inscript1
-Schleife länger dauert (script1
: Pipe mit 4 Prozessenscript2
starten VS : Subshell starten), bis das Material in den Hintergrund gestellt wurde. Zusätzlich werden die in (b)script2
ping wird nur ausgeführt , nachdem der Subshell warfork()
und damit später als inscript1
und es dauert eine andereif
,[
undecho
Befehl ....script2
die nicht zur Verfügung steht, wenn die Schleife endet (siehe (a) schnell)Dies wird das tun, was Sie erwarten:
Speichern Sie es als Parallelping und führen Sie es aus.
Es hilft dir? Es kann in eine große Funktion umgewandelt werden, die auch in einer schnellen while-Schleife verwendet werden kann, sodass Sie Ihre Fantasieprogrammierung damit verwenden können.
Hinweis: Sie müssen bash verwenden.
quelle
wait
, um auf die Beendigung der untergeordneten Prozesse im Hintergrund zu warten, ja? Oder war der entscheidende Punkt die Verwendung einer Shell-Funktion ? Wie in dem Kommentar von @LucianoAndressMartini geschrieben, scheint es das zu seinwait
, aber dies wird aus der Antwort nicht wirklich klar.