シェルスクリプトの「kill -0 $ pid」は何をしますか?


回答:


136

指定されたものにシグナル0を送信することは、指定されたPIDプロセスPIDが実行されているかどうか、およびシグナルを送信する権限があるかどうかを確認するだけです。

詳細については、次のマンページを参照してください。

kill(1)
$ man 1 kill
...
If sig is 0, then no signal is sent, but error checking is still performed.
...
kill(2)
$ man 2 kill
...
If sig is 0, then no signal is sent, but error checking is still performed; this 
can be used to check for the existence of a process ID or process group ID.
...

7
この情報の場所(存在する場合)は、システムに大きく依存します。最近のDebianベースのシステムでは、man 2 kill代わりに使用してください。
トッドA.ジェイコブス

2
両方man 1 killman 2 kill私のFedora 20システムでそれを持っていた。ただし、これらの両方のmanページに埋め込まれているため、特定するのは困難です。
slm 2014年

または、代わりにposixマニュアルを利用してください:If sig is 0 (the null signal), error checking is performed but no signal is actually sent. The null signal can be used to check the validity of pid. pubs.opengroup.org/onlinepubs/009695399/functions/kill.html
Thomas Hughes

2
コマンドman 2 killは第1改正の外にあるように私は感じます:)
JBaczuk 2017

126

これは良い質問です...

...この特別な信号に関するドキュメントを見つけるのは難しい場合があります。他の人が言ったことにもかかわらずman 1 kill、Debianベースのシステムにおけるこのシグナルの唯一の言及は次のとおりです。

特に有用な信号には、HUP、INT、KILL、STOP、CONT、および0があります。

特に信号が何をするのかまだわからない場合は特に役に立ちません。また、の出力にはリストされないkill -lため、すでに知らない限り、そのことを知ることはできません。

文書化されている場所

DebianおよびUbuntuシステムでman 2 killは、一部は次のように出力されます。

sigが0の場合、シグナルは送信されませんが、エラーチェックは実行されます。これは、プロセスIDまたはプロセスグループIDの存在を確認するために使用できます。

何が良いのか

を使用kill -0して、プロセスが実行されているかどうかを確認できます。これらの例を検討してください。

# Kill the process if it exists and accepts signals from
# the current user.
sleep 60 &
pid=$!
kill -0 $pid && kill $pid

# Check if a PID exists. When missing, this should result
# in output similar to:
#    bash: kill: (6228) - No such process
#    Exit status: 1
kill -0 $pid; echo "Exit status: $?"

また、を使用kill -0して、現在のユーザーが特定のプロセスにシグナルを送る権限を持っているかどうかを確認することもできます。例えば:

# See if you have permission to signal the process. If not,
# this should result in output similar to:
#     bash: kill: (15764) - Operation not permitted
#     Exit status: 1
sudo sleep 60 &
kill -0 $!; echo "Exit status: $?"

MacとBSDでそれはまたに記載されますkill(2) :ここでは、スニペットだThe kill() function sends the signal specified by sig to pid, a process or a group of processes. Typically, Sig will be one of the signals specified in sigaction(2). A value of 0, however, will cause error checking to be performed (with no signal being sent). This can be used to check the validity of pid.
ルーク・キャンベル

8
これは受け入れられる答えになるはずです。他のものよりもはるかに優れています。シグナル0のドキュメントを見つけるのは難しいです。中に埋もれていますkillmanページ:「sigが0であれば、何の信号が送信されませんが、エラーチェックがまだ行われています。」
slm 2014年

6

このコマンドは、$ pidのPIDを持つプロセスが生きているかどうかをチェックします。


1
マニュアルページには、「sigが0の場合、シグナルは送信されませんが、エラーチェックは実行されます」と書かれています。ここで参照しているエラーチェックは何ですか?
gjain

2
-1(PIDのあるプロセス$pidが実行されている可能性があるが、シグナルを送信する権限がないため)。
dwalter

2
@dwalter:権限がない場合は、EPERMを取得します。存在しない場合は、ESRCHを取得します。kill(1)それぞれに異なるエラーを出力します。したがって、シグナルを送信する権限があるかどうかに関係なく、pidが有効かどうかを確認できます。さらに、の一般的な使用方法はkill -0、pidが常に正しく使用されていなくても、pidが生きているかどうかを確認することです。この答えは正しいと思います(スペルは別として)。
camh

3
@camh:の戻り値はkill -0 $pidどちらの場合も同じにはなりません。それは戻ります1、あなたがのouputを解析せずに言うことはできませんので、killあなたがそれに信号を送信する権限を持っていない場合、プロセスが実行されているかどうかを。編集:はい私はそれがプロセスが生きているかどうかをチェックするためにほとんどの時間使用されることを知っています、しかしあなたがシグナルを送る許可を持っていることを保証できない限り(例えば:rootである)
dwalter

2
@dwalter:私のポイントは、答えが正しいということでした。あなたは知識を深めようとし、別のエラーケースがあったことを指摘しましたが、killbashの組み込み(質問にはタグが付けられていますbash)がstderrにエラーのタイプを出力するため、技術的にはそのケースもカバーすることを私は伝えています戻りコードのエラーの。つまり、出力を正しく解釈すれば、「このコマンドは、$ pidにPIDを持つプロセスが存在するかどうかを確認します」は完全に正しいです。[答えに-1を与えたと言わなかったら、私はコメントしなかったでしょう。あなたのコメントはそれ以外の場合は有効です。
cam

6

Kill -0 $ pidは、pidを持つプロセスが存在するかどうかをチェックします。

'kill -0 $ pid'を使用してプロセスの存在を確認するときは注意してください。

  1. 目的のプロセスが終了すると、そのpidを他の新しく作成されたプロセスに割り当てることができます。(つまり、特定のプロセスが生きているかどうかを確認することはできません)

  2. ゾンビプロセスの場合、子は親が待機を呼び出すのを待っています。ここでは$ pidを保持し、そのプロセスが実行されていないときに肯定的な結果を提供します。


1

Kill -0 $ pidは、$ pidで実行されているプロセスが生きているかどうかを確認するために使用されます。ただし、プロセスが終了して新しいプロセスが実行されると、プロセスIDを再割り当てできるため、これは注意が必要です。killall -0を使用して、特定のプロセスが実行されているかどうかを確認できます。


0

EXITシグナルの送信、または0プロセスへの送信:

  1. プロセスの存在を確認します。
  2. プロセス(PID、PGIDなど)でさまざまなエラーチェックを実行します。
  3. stdout成功した場合、出力は送信されません。
  4. stderr何かが正しくない場合は、エラーメッセージを送信します。
  5. プロセスが機能していない場合(ゾンビなど)は、誤検知を与えます。

より明確には、シェルスクリプトに役立つ関数は次のようになります。

function isProcess ()
{
    kill -s EXIT $1 2> /dev/null
}

これはstdout成功時にはテキストを返さずstderr、失敗時にはエラーメッセージを返します(ただし、そのエラーメッセージをにリダイレクトしました/dev/null)。

無効/ゾンビプロセスステータスが心配な場合は、を使用してps、できれば--no-headersスイッチを使用する必要があります。

#!/bin/ksh

function trim ()
{
    echo -n "$1" | tr -d [:space:]
}

function getProcessStatus ()
{
    trim $(ps -p $1 -o stat --no-headers)
}

function isZombie ()
{
    typeset processStatus=$(getProcessStatus $1)

    [[ "$processStatus" == "Z" ]]
    return $?
}
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.