我正在尝试按名称杀死一个进程,我将其作为变量传递给系统命令。
以下是我所拥有的:
my $processName=$ARGV[0];
print "$processName\n";
system(q/kill -9 `ps -ef | grep '$processName' | grep -v grep | awk '{print $2}'`/);
上面的脚本会抛出一个错误:
kill: usage: kill [-s sigspec | -n signum | -sigspec] pid | jobspec ... or kill -l [sigspec]
但是,如果我直接在系统命令中输入进程名称,它就可以工作。
有人可以帮我吗?
最佳答案
一个问题是调用脚本的命令行具有您随后查询的进程的名称,这是设计使然;所以发现的一件事就是脚本本身。
这是可以防备的,但是为什么要用那么大的管道去系统呢?
在 Perl 中查询进程,例如使用 Proc::ProcessTable
use warnings;
use strict;
use Proc::ProcessTable;
my $proc_name = shift // die "Usage: $0 process-name\n"; #/
my $pid;
my $pt = Proc::ProcessTable->new();
foreach my $proc (@{$pt->table}) {
next if $proc->cmndline =~ /$0.*$proc_name/; # not this script
if ($proc->cmndline =~ /\Q$proc_name/) {
$pid = $proc->pid;
last;
}
}
die "Not found process with '$proc_name' in its name\n" if not defined $pid;
kill 9, $pid; # must it be 9 (SIGKILL)?
my $gone_pid = waitpid $pid, 0; # then check that it's gone
请注意,通过发送
SIGTERM
来“杀死”一个进程要好得多。 (通常为 15),而不是 SIGKILL
.寻找进程“名称”可能很危险,因为在可能包含该词的现代系统上运行着许多具有长命令行的进程。该代码使用您的要求,只需按提交的名称进行查询,但我建议通过额外的检查来加强它。
模块可以查询的很多流程细节见其stub module .
即使您宁愿自己解析进程表,我也只会得到
ps -ef
然后在脚本中解析它。这为确保您真正终止您想要的内容提供了更大的灵 active 。
关于perl - 从 perl 脚本中杀死一个进程,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/49379374/