我必须杀死一个我通过它打开的程序
$pid = open(FH, "program|")
或者
$pid = or open(FH, "-|", "program")
但是,程序(具体来说是 mosquittto_sub)仍然在后台徘徊,因为open
它正在返回 perl 用来运行程序的 PID sh
,所以我只是杀死了sh
包装程序而不是实际程序。
有没有办法让程序真正的PID?获取sh
的 PID 有什么意义?
我必须杀死一个我通过它打开的程序
$pid = open(FH, "program|")
或者
$pid = or open(FH, "-|", "program")
但是,程序(具体来说是 mosquittto_sub)仍然在后台徘徊,因为open
它正在返回 perl 用来运行程序的 PID sh
,所以我只是杀死了sh
包装程序而不是实际程序。
有没有办法让程序真正的PID?获取sh
的 PID 有什么意义?
有几种方法可以解决这个问题。
首先,您可以使用列表形式打开一个进程,然后不涉及 shell,因此子进程(由 pid 返回open
)正是您需要停止的程序的那个
my @cmd = ('progname', '-arg1', ...);
my $pid = open my $fh, '-|', @cmd // die "Can't open \"@cmd\": $!";
...
my $num_signaled = kill 15, $pid;
这个草图需要添加一些检查。请参阅链接文档(查找“管道”)。
如果由于某种原因这不合适——也许你需要shell 来运行那个程序——那么你可以找到程序的 pid,而Proc::ProcessTable模块很适合这个。一个基本的演示
use Proc::ProcessTable;
my $prog_name = ...
my $pid;
my $pt = Proc::ProcessTable->new();
foreach my $proc (@{$pt->table}) {
if ($proc->cmndline =~ /\Q$prog_name/) { # is this enough to identify it?
$pid = $proc->pid;
last;
}
}
my $num_signaled = kill 15, $pid;
请注意通过名称识别程序——在现代系统上,可能有各种正在运行的进程包含您要终止的程序的名称。有关更多详细信息和讨论,请参阅这篇文章和这篇文章,供初学者参考。
最后,您可以使用一个模块来运行您的外部程序,然后您将能够更好地管理和控制它们。在这里我推荐IPC::Run。