bash 如何检查进程 ID (PID) 是否存在
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/3043978/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
How to check if a process id (PID) exists
提问by Richard H
In a bash script, I want to do the following (in pseudo-code):
在 bash 脚本中,我想执行以下操作(以伪代码形式):
if [ a process exists with $PID ]; then
kill $PID
fi
What's the appropriate expression for the conditional statement?
条件语句的适当表达式是什么?
采纳答案by Christoffer Hammarstr?m
To check for the existence of a process, use
要检查进程是否存在,请使用
kill -0 $pid
But just as @unwind said, if you're going to kill it anyway, just
但正如@unwind 所说,如果你无论如何要杀死它,就
kill $pid
or you will have a race condition.
否则你会遇到竞争条件。
If you want to ignore the text output of kill
and do something based on the exit code, you can
如果你想忽略文本输出kill
并根据退出代码做一些事情,你可以
if ! kill $pid > /dev/null 2>&1; then
echo "Could not send SIGTERM to process $pid" >&2
fi
回答by FDS
The best way is:
最好的办法是:
if ps -p $PID > /dev/null
then
echo "$PID is running"
# Do something knowing the pid exists, i.e. the process with $PID is running
fi
The problem with:
问题在于:
kill -0 $PID
is the exit code will be non-zero even if the pid is running and you dont have permission to kill it. For example:
即使pid正在运行并且您无权杀死它,退出代码也将是非零的。例如:
kill -0 1
and
和
kill -0 $non-running-pid
have an indistinguishable (non-zero) exit code for a normal user, but the init process (PID 1) is certainly running.
对于普通用户,有一个无法区分的(非零)退出代码,但 init 进程(PID 1)肯定正在运行。
DISCUSSION
讨论
The answers discussing kill and race conditions are exactly right if the body of the test is a "kill". I came looking for the general "how do you test for a PID existence in bash".
如果测试的主体是“kill”,那么讨论 kill 和 Race conditions 的答案是完全正确的。我来寻找一般的“你如何测试 bash 中的 PID 存在”。
The /proc method is interesting, but in some sense breaks the spirit of the "ps" command abstraction, i.e. you dont need to go looking in /proc because what if Linus decides to call the "exe" file something else?
/proc 方法很有趣,但从某种意义上说,它打破了“ps”命令抽象的精神,也就是说,您不需要去查看 /proc,因为如果 Linus 决定将“exe”文件称为别的东西怎么办?
回答by user2683246
if [ -n "$PID" -a -e /proc/$PID ]; then
echo "process exists"
fi
or
或者
if [ -n "$(ps -p $PID -o pid=)" ]
In the latter form, -o pid=
is an output format to display only the process ID column with no header. The quotes are necessaryfor non-empty string operator -n
to give valid result.
在后一种形式中,-o pid=
是仅显示没有标题的进程 ID 列的输出格式。非空字符串运算符需要引号-n
才能给出有效结果。
回答by oherrala
ps
command with -p $PID
can do this:
ps
命令 with-p $PID
可以做到这一点:
$ ps -p 3531
PID TTY TIME CMD
3531 ? 00:03:07 emacs
回答by elcuco
You have two ways:
你有两种方法:
Lets start by looking for a specific application in my laptop:
让我们首先在我的笔记本电脑中寻找一个特定的应用程序:
[root@pinky:~]# ps fax | grep mozilla
3358 ? S 0:00 \_ /bin/sh /usr/lib/firefox-3.5/run-mozilla.sh /usr/lib/firefox-3.5/firefox
16198 pts/2 S+ 0:00 \_ grep mozilla
All examples now will look for PID 3358.
现在所有示例都将查找 PID 3358。
First way: Run "ps aux" and grep for the PID in the second column. In this example I look for firefox, and then for it's PID:
第一种方法:在第二列中为 PID 运行“ps aux”和 grep。在这个例子中,我寻找 firefox,然后寻找它的 PID:
[root@pinky:~]# ps aux | awk '{print }' | grep 3358
3358
So your code will be:
所以你的代码将是:
if [ ps aux | awk '{print }' | grep -q $PID 2> /dev/null ]; then
kill $PID
fi
Second way: Just look for something in the /proc/$PID
directory. I am using "exe" in this example, but you can use anything else.
第二种方式:只需在/proc/$PID
目录中查找内容。我在这个例子中使用了“exe”,但你可以使用其他任何东西。
[root@pinky:~]# ls -l /proc/3358/exe
lrwxrwxrwx. 1 elcuco elcuco 0 2010-06-15 12:33 /proc/3358/exe -> /bin/bash
So your code will be:
所以你的代码将是:
if [ -f /proc/$PID/exe ]; then
kill $PID
fi
BTW: whats wrong with kill -9 $PID || true
?
BTW:kill -9 $PID || true
怎么了?
EDIT:
编辑:
After thinking about it for a few months.. (about 24...) the original idea I gave here is a nice hack, but highly unportable. While it teaches a few implementation details of Linux, it will fail to work on Mac, Solaris or *BSD. It may even fail on future Linux kernels. Please - use "ps" as described in other responses.
经过几个月的思考......(大约24......)我在这里给出的最初想法是一个很好的黑客,但非常不可移植。虽然它讲授了 Linux 的一些实现细节,但它无法在 Mac、Solaris 或 *BSD 上运行。它甚至可能在未来的 Linux 内核上失败。请 - 使用“ps”,如其他回复中所述。
回答by Gagan Gami
It seems like you want
好像你想要
wait $PID
which will return when $pid
finishes.
$pid
完成后将返回。
Otherwise you can use
否则你可以使用
ps -p $PID
to check if the process is still alive (this is more effective than kill -0 $pid
because it will work even if you don't own the pid).
检查进程是否还活着(这比kill -0 $pid
因为即使您不拥有 pid 也能工作更有效)。
回答by unwind
I think that is a bad solution, that opens up for race conditions. What if the process dies between your test and your call to kill? Then kill will fail. So why not just try the kill in all cases, and check its return value to find out how it went?
我认为这是一个糟糕的解决方案,它为竞争条件开辟了道路。如果进程在您的测试和您的 kill 调用之间终止了怎么办?那么kill就会失败。那么为什么不在所有情况下都尝试 kill 并检查其返回值以了解它是如何进行的呢?
回答by inukaze
For example in GNU/Linux you can use:
例如在 GNU/Linux 中,您可以使用:
Pid=$(pidof `process_name`)
if [ $Pid > 0 ]; then
do something
else
do something
fi
Or something like
或者类似的东西
Pin=$(ps -A | grep name | awk 'print }')
echo $PIN
and that shows you the name of the app, just the name without ID.
这会显示应用程序的名称,只是没有 ID 的名称。
回答by invalidmagic
here i store the PID in a file called .pid (which is kind of like /run/...) and only execute the script if not already being executed.
在这里,我将 PID 存储在一个名为 .pid 的文件中(类似于 /run/...),并且仅在尚未执行的情况下才执行脚本。
#!/bin/bash
if [ -f .pid ]; then
read pid < .pid
echo $pid
ps -p $pid > /dev/null
r=$?
if [ $r -eq 0 ]; then
echo "$pid is currently running, not executing #!/bin/bash
PID=$(ps aux | grep '/usr/bin/python2.7 manage.py SES__boto3_sqs_read' | grep -v grep | awk '{print }')
if [[ -z $PID ]]; then
/usr/bin/python2.7 /home/brian/djcode/proyectoONE/manage.py SES__boto3_sqs_read
else
echo "do nothing, just smile =)"
fi
exit $?
twice, exiting now..."
exit 1
fi
fi
echo $$ > .pid
# do things here
rm .pid
note:there is a race condition as it does not check how that pid is called. if the system is rebooted and .pid exists but is used by a different application this might lead 'unforeseen consequences'.
注意:存在竞争条件,因为它不检查该 pid 的调用方式。如果系统重新启动并且 .pid 存在但被不同的应用程序使用,这可能会导致“不可预见的后果”。
回答by Brian Sanchez
code below checks if my process is running, if so do nothing.
下面的代码检查我的进程是否正在运行,如果正在运行,则不执行任何操作。
let's check new messages from Amazon SQS every hour only and only if the process is not running.
让我们每小时检查一次来自 Amazon SQS 的新消息,并且仅在进程未运行时检查。
##代码##