Intereting Posts
Определите конкретный TTL для каждого интерфейса как полностью пустой видеовыход при загрузке (без регистрации ядра, вывода grub и т. д.) Почему последняя функция, выполняемая в конвейере сценария оболочки POSIX, не сохраняет значения переменных? Как ядро ​​Linux сравнивается с микроядрами? Являются ли данные дешифрованы и повторно зашифрованы сервером OpenVPN при отправке между клиентами? Как перенаправление файлов bash на стандарт отличается от shell (`sh`) в Linux? Почему используется своп, когда большая часть памяти по-прежнему свободна? Почему эта первая запятая в этом массиве printf? tcpdump / tshark: просмотр только исходящих запросов TCP-соединений Почему псевдоним работает иногда как nameref, а иногда нет? Рекурсивный grep, совместимый с POSIX, без ошибок для недоступных каталогов Как systemd выжить в kill -9? pfSense: какой пакет я могу установить для команды `make`? ошибочно удаленная / загрузочная папка и перезагрузка Как проверить, распространяется ли дистрибутив на Fedora?

Выполнять команду или функцию, когда SIGINT или SIGTERM отправляются самому родительскому скрипту, а не дочерним процессам

Предположим, у меня есть этот script.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 

Я хочу, чтобы script.sh выполнял функцию exit_script всякий раз, когда он получал SIGINT или SIGTERM Например:

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

и я хочу, чтобы мой скрипт выполнял этот

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

Я попытался реализовать эту функцию, используя trap

 trap exit_script SIGINT SIGTERM 

Человек, который ответил на мой вопрос, оказался неправильным.
но это не сработало, потому что trap похоже, реагирует только на сигналы, посылаемые дочерним / вспомогательным процессам. Будучи новичком, я не мог расшифровать страницу руководства trap поэтому я, вероятно, пропустил это решение.

Наверное, это то, что делают «настоящие» программы, такие как Chromium, когда вы отправляете их SIGTERM

От https://major.io/2010/03/18/sigterm-vs-sigkill/

Приложение может определить, что он хочет сделать, как только SIGTERM будет получен. В то время как большинство приложений очищают свои ресурсы и останавливаются, некоторые могут этого не делать.

trap реагирует на сигналы вызывающего процесса. Но вы должны позвонить ему до получения сигнала. Я имею в виду, в начале вашего скрипта.

Кроме того, если вы хотите использовать kill -- -$$ , который посылает сигнал также вашему сценарию, вам нужно очистить ловушку перед запуском kill, иначе вы закончите бесконечный цикл kill && trap .

Например:

 #!/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 

Как поясняется в комментариях, проблема заключается в том, что скрипт получает сигнал, но ожидает завершения программы сна до обработки принятого сигнала. Таким образом, вы должны убить дочерние процессы (процесс сна в этом случае), чтобы запустить действие trap. Вы можете сделать что-то вроде следующего:

 kill -- -$(pgrep script.sh) 

Или, как указано в комментариях:

 killall -g script.sh