Führen Sie den Befehl oder die Funktion aus, wenn SIGINT oder SIGTERM an das übergeordnete Skript selbst gesendet wird, nicht an die untergeordneten Prozesse.

Führen Sie den Befehl oder die Funktion aus, wenn SIGINT oder SIGTERM an das übergeordnete Skript selbst gesendet wird, nicht an die untergeordneten Prozesse.

Nehmen wir an, ich habe dasscript.sh

#!/bin/bash
exit_script() {
    echo "Printing something special!"
    echo "Maybe executing other commands!"
    kill -- -$$ # Sends SIGTERM to child/sub processes
}

echo "Some other text"
#other commands here
sleep infinity

Ich möchte script.shdie Funktion immer dann ausführen, exit_scriptwenn sie empfängt SIGINToder SIGTERM Zum Beispiel:

killall script.sh # it will send SIGTERM to my script

und ich möchte, dass mein Skript dies ausführt

exit_script() {
    echo "Printing something special!"
    echo "Maybe executing other commands!"
    kill -- -$$ # Sends SIGTERM to child/sub processes
}

Ich habe versucht, diese Funktion zu implementieren mittrap

trap exit_script SIGINT SIGTERM

Die Person, die meine Frage beantwortet hat, hat mir das Gegenteil bewiesen.
Aber es hat nicht funktioniert, weil es trapanscheinend nur auf Signale reagiert, die an untergeordnete/untergeordnete Prozesse gesendet werden. Als Anfänger konnte ich trapdie Manpage nicht entziffern, also habe ich die Lösung wahrscheinlich übersehen.

Ich denke, das ist, was "echte" Programme wie Chromium tun, wenn Sie sie sendenSIGTERM

Aushttps://major.io/2010/03/18/sigterm-vs-sigkill/

Die Anwendung kann bestimmen, was sie tun möchte, sobald ein SIGTERM empfangen wird. Während die meisten Anwendungen ihre Ressourcen bereinigen und anhalten, tun dies manche nicht.

Antwort1

trapreagiert selbst auf die Signale des aufrufenden Prozesses. Sie müssen es jedoch aufrufen, bevor das Signal empfangen wird. Ich meine, am Anfang Ihres Skripts.

Wenn Sie außerdem verwenden möchten kill -- -$$, das das Signal auch an Ihr Skript sendet, müssen Sie die Falle löschen, bevor Sie den Kill ausführen, sonst erhalten Sie eine unendlichetöten und fangenSchleife.

Zum Beispiel:

#!/bin/bash
exit_script() {
    echo "Printing something special!"
    echo "Maybe executing other commands!"
    trap - SIGINT SIGTERM # clear the trap
    kill -- -$$ # Sends SIGTERM to child/sub processes
}

trap exit_script SIGINT SIGTERM

echo "Some other text"
#other commands here
sleep infinity

Wie in den Kommentaren erklärt, besteht das Problem darin, dass das Skript das Signal empfängt, aber wartet, bis das Sleep-Programm beendet ist, bevor es das empfangene Signal verarbeitet. Sie sollten also die untergeordneten Prozesse (in diesem Fall den Sleep-Prozess) beenden, um die Trap-Aktion auszuführen. Sie können das etwa mit Folgendem tun:

kill -- -$(pgrep script.sh)

Oder wie in den Kommentaren angegeben:

killall -g script.sh

verwandte Informationen