" TERM=dumb C-6ren">
gpt4 book ai didi

使用 PTY.spawn 打开的 Ruby kill 虚拟 shell

转载 作者:数据小太阳 更新时间:2023-10-29 07:54:11 25 4
gpt4 key购买 nike

在 ruby​​ 脚本中,我启动了多个虚拟 shell,每个都由一个 shell 管理器对象管理,如下所示:

@shell = PTY.spawn 'env PS1="\w>" TERM=dumb COLUMNS=63 LINES=21 sh -i'

在稍后的某个时间点,我想销毁这个实例并终止相关的 shell 进程。可悲的是,我无法正常工作。这是我尝试过的方法,按照工作的可能性排序:

  • 没有,也就是说,期望在管理对象被销毁时关闭 shell proc。
  • 使用 kill 命令杀死 shell 上运行的所有进程(这有效),然后使用 system("kill #{@shell[2]") 杀死 shell 本身。这没有效果。
  • 在上面使用-9。这会使 shell 进程失效。

当 ruby​​ 程序退出时,所有 shell 都会关闭,但我想在保持程序运行的同时杀死它们。有人遇到过这样的事情吗?

最佳答案

问题是僵尸。是的,真的。

所有 Unix 风格的内核都将进程留在身边,直到有人等待它。 (这是为了跟踪 PID、退出状态和其他一些东西。)它们被称为僵尸,在 ps(1) 列表中有一个 Z 状态。你不能杀死他们,因为他们已经死了。当你等待他们时,他们会离开。

下面是清理@shell 对象的方法:

@shell[0].close
@shell[1].close
begin
Process.wait @shell[2]
rescue PTY::ChildExited
end

您可能不需要救援 block ,具体取决于您是否有更高级别的层来广泛捕获异常。 (叹气,就像我的 irb。)

顺便说一下,当 Ruby 程序退出时你的进程最终消失的原因是因为僵尸也变成了孤儿(没有父进程)并且 shell 或 init(8) 最终将等待所有孤儿。

关于使用 PTY.spawn 打开的 Ruby kill 虚拟 shell,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/6310858/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com