Как отправить сигнал SIGINT из скрипта в скрипт? BASH
Я хочу перехватить сигнал, посылаемый из Script-A.sh в Script-B.sh, поэтому в Script-A.sh я использую команду
(Отправить SIGINT на Script-B.sh)
убить -2 $PID_Script-B.sh
А в Script-B.sh я ловлю сигнал и вызываю функцию Clean
ловушка "Чистая" 2
Это не работает, вместо этого Script-B.sh убивается сразу, не выполняя Clean!!
Я также заметил, что если я хочу отправить SIGINT из терминала на любой скрипт, который его перехватывает, ctrl-c
будет перехвачен правильно, но нет, если я укажу сигнал с помощью команды kill -2 $pid_of_script
Любая идея о разнице между двумя методами для отправки SIGINT (ctrl-c
В.С. kill -2 $pid_of_script
), а как я могу отправить SIGINT из скрипта в другой?
С Уважением,
дебаггер
2 ответа
Я смог воспроизвести поведение, о котором вы сообщаете. Моя гипотеза состоит в том, что поскольку скрипт выполняется из неинтерактивной оболочки (как дочерний элемент сценария), SIGINT
, который является сигналом клавиатуры, игнорируется.
От info bash
:
Фоновые процессы - это те, чей ID группы процессов отличается от терминала; такие процессы невосприимчивы к сигналам, генерируемым клавиатурой.
Я обнаружил, что если вы trap
а также kill
используя другой сигнал, такой как SIGUSR1
оно работает.
Дополнительная информация от man bash
:
У не встроенных команд, запускаемых bash, в обработчиках сигналов установлены значения, унаследованные оболочкой от ее родителя. Когда управление заданиями не действует, асинхронные команды игнорируют SIGINT и SIGQUIT в дополнение к этим унаследованным обработчикам.
а также
Если bash ожидает завершения команды и получает сигнал, для которого установлена ловушка, ловушка не будет выполнена, пока команда не завершится.
а также
Любая ловушка на SIGCHLD выполняется для каждого выходящего ребенка.
В сценарии A: функция Trap будет выглядеть следующим образом, которая вызовет функцию trap_mesg() в файле scriptA.sh. Сигнал KILL (2/INTerrupt, 5/TERMinate-default). Все, что вам нужно сделать, это получить PID запущенного процесса / сеанса scriptB.sh после вызова scriptB.sh из файла scriptA.sh (nohup ... & даст вам команду ps)
trap_mesg ()
{
#...do something here for script B..
# i.e.
kill -2 PID_of_ScriptB.sh_running_process_session
sleep 10; #just in case, not reqd though.
#show using ps -eAf|grep "scriptB" ... if null means, scriptB is gone. user is happy now.
#...before actually exiting out...
#show script A is exiting out as ScriptB is dead already, time for scriptA now.
#...do something here..
}
#####################################
## Trap signals : INT, TERM. catch ##
#####################################
#Set NULL/Blank value to trap_call. This variable will help in running trap_mesg only once during the life of this script.
trap_call="";
trap 'if [ -z ${trap_call} ]; then trap_call="1"; trap_mesg ; fi' 2 15
##################################
Теперь, внутри scriptB.sh, сделайте то же самое / подобное, но только для ловушек scriptB (например, вызов clean).
clean ()
{
echo "karoge seva to milega meva";
rm -fr /some/folder_file
}
trap_mesg ()
{
#...do something here JUST for script B trap message work..
# i.e.
clean;
#...do something here..
}
#####################################
## Trap signals : INT, TERM. catch ##
#####################################
#Set NULL/Blank value to trap_call. This variable will help in running trap_mesg only once during the life of this script.
trap_call="";
trap 'if [ -z ${trap_call} ]; then trap_call="1"; trap_mesg ; fi' 2 15
##################################
Таким образом, вам не нужно искать / вызывать scriptB.sh внутри scriptA.sh как ". ScriptB.sh ...."