当前位置: 首页>>技术教程>>正文


如何杀死在终端中运行的脚本,而不关闭终端(Ctrl + C不起作用)?

, ,

问题描述

我编写了一个bash脚本,调用其他几个程序并执行一堆命令。我从终端运行这个脚本。现在我要杀死脚本。

Ctrl + C有时不会削减它,我认为因为有时脚本正在执行另一个程序,并且由于某种原因,kill信号不起作用。

但是,如果我关闭终端窗口,它会杀死脚本。

有什么我能做的(键盘组合),类似于关闭终端窗口,而不是实际关闭终端窗口(我不想丢失命令历史,当前目录,输出历史等)?

最佳解决方法

你有几个选择。一种是停止脚本(Ctrl Z),获取脚本的PID并将SIGKILL发送到进程组。

在shell中执行命令时,它启动的进程及其所有子进程都是同一process group(在本例中为前台进程组)的一部分。要向该组中的所有进程发送信号,请将其发送给进程负责人。对于kill命令,进程负责人如下表示:

kill -PID

其中PID是脚本的进程ID。

例:

考虑一个启动某些进程的脚本test.sh。假设你在shell中运行它:

$ ./test.sh

在另一个终端,

$ pgrep test.sh
17802
$ pstree -ps `!!`
pstree -ps `pgrep test.sh`
init(1)───sshd(1211)───sshd(17312)───sshd(17372)───zsh(17788)───test.sh(17802)─┬─dd(17804)
                                                                               ├─sleep(17805)
                                                                               └─yes(17803)

在这种情况下,要向test.sh创建的进程组发送信号,您需要执行以下操作:

kill -INT -17802

-INT用于发送SIGINT,因此该命令相当于在终端上按Ctrl C。要发送SIGKILL

kill -KILL -17802

如果无法打开另一个终端,则只需停止脚本即可。如果可以,请使用pgrep查找PID。

脚本启动的命令之一可能是捕获SIGINT,这可能是Ctrl C无效的原因。但是,SIGKILL不能被捕获,它通常是last-resort选项。在进行杀戮之前,你可能想尝试SIGTERM(-TERM)。 SIGKILLSIGTERM都不能像SIGINT那样设置为keyboard shortcut

如果你的脚本不包含shebang行,那么这一切都没有实际意义。来自this SO answer

Usually the parent shell guesses that the script is written for the the same shell (minimal Bourne-like shells run the script with /bin/sh, bash runs it as a bash subprocess) …

因此,在执行脚本时,您将找不到以脚本命名的进程(或在命令行中具有脚本名称的进程),并且pgrep将失败。

总是使用shebang线。

次佳解决方法

如果您知道与脚本关联的进程,则可以使用它来查找其PID

 ps -A

然后使用PID号来杀死相应的进程

 kill -9 PID_Number

参考资料

本文由Ubuntu问答整理, 博文地址: https://ubuntuqa.com/article/6316.html,未经允许,请勿转载。