【问题标题】:How to properly sigint a bash script that is run from another bash script?如何正确签署从另一个 bash 脚本运行的 bash 脚本?
【发布时间】:2014-08-27 15:47:48
【问题描述】:

我有两个脚本,其中一个正在调用另一个,并且需要在一段时间后将其杀死。下面给出了一个非常基本的工作示例。

main_script.sh:

#!/bin/bash
cd "${0%/*}" #make current working directory the folder of this script
./record.sh &
PID=$!
# perform some other commands
sleep 5
kill -s SIGINT $PID
#wait $PID
echo "Finished"

record.sh:

#!/bin/bash
cd "${0%/*}" #make current working directory the folder of this script
RECORD_PIDS=1
printf "WallTimeStart: %f\n\n" $(date +%s.%N) >> test.txt
top -b -p $RECORD_PIDS -d 1.00 >> test.txt
printf "WallTimeEnd: %f\n\n" $(date +%s.%N) >> test.txt

现在,如果我运行 main_script.sh,它不会在完成时很好地关闭 record.sh:top 命令将继续在后台运行(test.txt 会不断增长,直到您手动终止 top 进程),即使main_script 已完成,并且使用 SIGINT 终止记录脚本。

如果我 ctrl+c main_script.sh,一切都会正常关闭。如果我自己运行 record.sh 并 ctrl+c 它,一切都会正常关闭。

如果我取消注释等待,脚本将挂起,我需要 ctrl+z 它。

我已经尝试了各种方法,包括在收到 SIGINT、EXIT 和/或 SIGTERM 时使用“trap”启动一些清理脚本,但没有任何效果。我还尝试使用 fg 将 record.sh 带回前台,但这也无济于事。我已经搜索了将近一天,不幸的是现在很幸运。我做了一个丑陋的解决方法,它使用 pidof 来查找顶级进程并手动终止它(从 main_script.sh),然后我必须手动从 main_script.sh 向它编写“WallTimeEnd”语句。对我来说不是很满意...

期待任何提示!

干杯, 科恩

【问题讨论】:

    标签: linux bash shell kill


    【解决方案1】:

    您的问题是SIGINT 被传送到bash 而不是top。一种选择是使用新会话并将信号发送到进程组,例如:

    #!/bin/bash
    cd "${0%/*}" #make current working directory the folder of this script
    setsid ./record.sh &
    PID=$!
    # perform some other commands
    sleep 5
    kill -s SIGINT -$PID
    wait $PID
    echo "Finished"
    

    这会在新进程组中启动子脚本,并且 -pid 告诉 kill 向该组中的每个进程发出信号,其中将包括 top

    【讨论】:

      猜你喜欢
      • 2023-01-13
      • 1970-01-01
      • 2012-06-22
      • 2016-03-01
      • 2021-08-28
      • 1970-01-01
      • 2017-11-04
      • 2017-06-10
      • 1970-01-01
      相关资源
      最近更新 更多