Почему SIGTERM работает для завершения bash, но не для ash или dash?

Идеальным инструментом для этого является rmadison, который представляет собой простой Perl-скрипт с несколькими зависимостями, (модуль URIи wgetили curl), так что он может работать практически везде. Он опрашивает службы Madison, размещенные в Debian и Ubuntu, для определения доступности пакетов :

.

rmadison gcc-7

сообщает вам, какие версии GCC 7 доступны в различных комплектах Debian,

rmadison -u ubuntu gcc-7

делает то же самое для Ubuntu.

Вы можете ограничить вывод определенной версией:

rmadison -u ubuntu -s bionic gcc-7

2
04.03.2020, 19:35
2 ответа

Это происходит только тогда, когда bash использует библиотеку редактирования строк readlineи только когда bashожидает ввода от пользователя.

bash --noeditingне будет убит SIGTERMи bashне убьет себя при запуске kill -TERM $$.

Это происходит потому, что функция readline(), используемая bash для получения ввода от пользователя, устанавливает собственный обработчик сигнала для SIGTERMи восстанавливает исходное расположение сигнала перед возвратом. Если SIGTERMпроисходит, когда readlineожидает ввода от пользователя, readline()возвращает NULL.

Функция bash, которая вызывает readline()(yy_readline_get()), интерпретирует возврат NULLкак EOF, вызывая выход из оболочки. Сценарий очень похож на этот ответ .

Это означает, что интерактивный bash также может быть создан, чтобы пережить SIGTERM, установив IGNOREEOF;-):

$ bash
$ IGNOREEOF=10
$ echo $$
11096
<kill -TERM 11096 from another terminal>
$ Use "exit" to leave the shell.
<kill -TERM 11096 from another terminal>
$ Use "exit" to leave the shell.
...
<the 10th will get it>
$ exit
$
4
20.08.2021, 10:49

Это было неожиданно для меня, но выполнение нескольких сборок показало, что это воспроизводилось в последнем коде bash из git, но не в bash 4.0. Таким образом, git bisectпомог определить следующую фиксацию как ответственную:

% git bisect good                     
ac50fbac377e32b98d2de396f016ea81e8ee9961 is the first bad commit
commit ac50fbac377e32b98d2de396f016ea81e8ee9961
Author: Chet Ramey <chet.ramey@case.edu>
Date:   Wed Feb 26 09:36:43 2014 -0500

    Bash-4.3 distribution sources and documentation

Индивидуальные коммиты git в Bash, как правило, довольно большие и не очень ограничены по объему, но, потратив несколько минут на просмотр этого коммита, можно увидеть ряд изменений в том, как readline обрабатывает SIGTERM, включая новое событие rl _signal _. _хук, который SIGTERM должен обходить, и множество новых мест, которые мы проверяем на наличие SIGTERM и вызываем termsig_handler.

Часть этих изменений совпадает с этой новой записью в журнале изменений:

Readline calls an application-set event hook (rl_signal_event_hook) after it gets a signal while reading input (read returns -1/EINTR but readline does not handle the signal immediately) to allow the application to handle or otherwise note it. Not currently called for SIGHUP or SIGTERM.

Судя по этому сообщению, я считаю, что изменение поведения может быть непреднамеренным.

Я собираюсь направить эту тему в список рассылки -bash, чтобы выяснить, было ли это преднамеренным или нет.

3
20.08.2021, 10:49

Теги

Похожие вопросы