【问题标题】:Bash script dd and fsck not killedBash 脚本 dd 和 fsck 没有被杀死
【发布时间】:2014-11-26 11:31:36
【问题描述】:

我需要从在某个对等节点上执行 dd、fcsk 和其他一些任务的脚本中删除正在使用的 lv。所以我只是杀死脚本并尝试从该对等节点中删除 lv,但是它似乎无法使用错误打开 lvs。

但是对于同样的情况,如果我杀死 dd 然后删除 lv 其工作正常。 可能是在问一个愚蠢的问题,但需要知道为什么会这样?

【问题讨论】:

  • 应用程序/进程在被调度(抢占)然后被调度时接收信号。如果您的进程以高优先级运行,那么它有可能永远不会被抢占。因此,您的进程永远不会收到信号。或者,您的进程可能会卡在某些内核驱动程序中。

标签: linux bash process kill-process


【解决方案1】:

如果您终止向其 PID 发送 SIGTERM 或 SIGKILL 的脚本,通常您只会将信号发送到父进程。 dd 在不会接收信号的子进程中运行。一旦父进程被杀死,子进程就会被 init 继承并继续运行。

要将信号发送到整个进程组,请使用:

kill -- -PID

kill -9 -PID

其中 PID 是脚本的 PID。注意 PID 前面的减号。 来自man kill

-n     where n is larger than 1.  All processes in process group n are signaled.

示例

我正在从 shell 脚本运行 dd:

 PID  TGID   TID  PGID  PPID COMMAND
 5828  5828  5828  5828 20127 sh
 5829  5829  5829  5828  5828 dd

进程组 ID (PGID) 是父进程的 PID (5828)。

如果我运行以下命令:

kill -9 5828

我得到以下情况:

 PID  TGID   TID  PGID  PPID COMMAND
 5829  5829  5829  5828     1 dd

dd 仍在运行,它已被 init 继承(PPID 为 1)。 相反,如果我运行:

kill -9 -5828

脚本和 dd 都被杀死了。

编辑:您要杀死的进程是通过 ssh 远程启动的。

让 ssh 远程启动 dd/fsck 会改变一切。一个简单但不推荐的解决方案可能如下。

脚本在后台通过 ssh 远程启动 dd/fsck 并获取 PID。

remote_pid=$(ssh user@host 'dd if=/dev/urandom of=/dev/zero & echo $!')

那么脚本不能返回并捕获您的信号。您的处理程序打开一个新的 ssh 连接并发出信号 remote_pid

不建议在第二个 ssh 连接中清理,因为它可能会失败并留下很多混乱。

如需更高级的解决方案,请参阅https://unix.stackexchange.com/questions/40023/get-ssh-to-forward-signals

【讨论】:

  • 感谢@mguerri,但我的情况有点扭曲。问题是正在执行 ssh,然后在其他节点(此处为 fsck)上运行该进程。因此,如果我发出 kill -9 -PGID 它只会杀死正在运行的 ssh 和当前脚本,但不会杀死其他节点上的进程。我不能写陷阱,因为在这种情况下我只需要发送 SIGKILL。那么有没有办法杀死在其他节点上运行的进程呢?
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2015-03-01
  • 2021-05-02
  • 1970-01-01
  • 2016-01-24
  • 1970-01-01
  • 1970-01-01
  • 2017-03-31
相关资源
最近更新 更多