次の例のようなジョブを実行すると、ログアウト時にそのジョブが終了します。
$ ./job.sh &
ただし、次の例のようにstdoutをstdoutに/dev/null
、stderrをstdoutにリダイレクトしてジョブをバックグラウンドに配置して実行すると、ログアウト時にそのジョブは終了しません。出力が/dev/null
ファイルの代わりにファイルに移動することを除いて、nohupと少し似ています。
$ ./job.sh > /dev/null 2>&1 &
一部のデーモンがこのように動作することがわかり、ログアウト時になぜデーモンが終了しないのか疑問に思いました。
誰かが理由を説明できますか?
編集1:
@Patrickが自分の意見で提案したように、同じ結果で同じ単純な操作を試しました。ログアウトしてもジョブは消えません。
# while true; do sleep 1; done > /dev/null 2>&1 &
[1] 4320
# logout
luis-macbook:~ luis$
luis-macbook:Downloads luis$ ssh server
luis.alen@server's password:
# jobs
#
# ps -ef | grep 4320
root 4320 1 0 01:17 ? 00:00:00 -bash
編集2:
Patrickが再び尋ねたときにストリームをリダイレクトせずに同じテストを実行しましたが、驚くべきことにプロセスは終了しませんでした。今は完全に混乱しています…ログアウトすると、バックグラウンドに入れておいたプロセスが消えるのを覚えています。私は完全に間違っていますか?
# while true; do sleep 1; done &
[1] 20720
# logout
luis-macbook:~ luis$ ssh server
# jobs
#
# ps -ef | grep 20720
root 20720 1 0 23:31 ? 00:00:00 -bash
答え1
これを実行するデーモンの場合、プロセスの入出力ストリームをどのようにリダイレクトするかに関係なく、生成できるすべての出力またはエラーメッセージを削除したいので、セッションに接続されており、そのセッションはSIGHUP信号です。プロセスを実行し続けるには終了してください。
プロセスを実行し続ける方法はいくつかあります。
セッションから切り離します。デーモンは新しいプロセスをフォークし、元のプロセスを終了してこれを行います。これで、新しいプロセスには親プロセスがなく、ユーザーが採用します。
init
bash内部コマンドdisownを使用してこれを実行することもできます。セッションの終了時にプロセスがSIGHUPを受信しないようにするために使用されます
nohup
。プロセスはSIGHUPを取得できず、終了せず、親プロセスが終了し、initがそれを取得します。消えないセッションへの接続 - 画面の使用
> /dev/null 2>&1 &
「実行中にログアウトしてもジョブは終了しません」というフレーズの操作をもう一度確認してください。
答え2
私が知っている限り、これはbashでの動作です。
sergiopa@sergiopa:~/Downloads$ find / -print >/dev/null 2>&1 &
[1] 14152
sergiopa@sergiopa:~/Downloads$ jobs
[1]+ Running find / -print > /dev/null 2>&1 &
sergiopa@sergiopa:~/Downloads$ ps -ef | grep find
sergiopa 14152 13913 10 15:47 pts/18 00:00:01 find / -print
sergiopa 14195 13913 0 15:48 pts/18 00:00:00 grep --color=auto find
sergiopa@sergiopa:~/Downloads$
sergiopa@sergiopa:~/Downloads$ lsof -c find
COMMAND PID USER FD TYPE DEVICE SIZE/OFF NODE NAME
find 14152 sergiopa cwd DIR 252,1 4096 4808 /usr/src/linux-headers-2.6.35-22/drivers/rapidio
find 14152 sergiopa rtd DIR 252,1 4096 2 /
find 14152 sergiopa txt REG 252,1 141980 391686 /usr/bin/find
find 14152 sergiopa mem REG 252,1 1421892 26489 /lib/libc-2.12.1.so
find 14152 sergiopa mem REG 252,1 118084 26452 /lib/ld-2.12.1.so
find 14152 sergiopa mem REG 252,1 149392 26485 /lib/libm-2.12.1.so
find 14152 sergiopa mem REG 252,1 30684 26469 /lib/librt-2.12.1.so
find 14152 sergiopa mem REG 252,1 121578 26490 /lib/libpthread-2.12.1.so
find 14152 sergiopa mem REG 252,1 2768240 391861 /usr/lib/locale/locale-archive
find 14152 sergiopa 0u CHR 136,18 0t0 21 /dev/pts/18 <<<<
find 14152 sergiopa 1w CHR 1,3 0t0 4293 /dev/null <<<<
find 14152 sergiopa 2w CHR 1,3 0t0 4293 /dev/null <<<<
find 14152 sergiopa 3r DIR 252,3 4096 16777344 /home/sergiopa/Downloads
find 14152 sergiopa 4r DIR 252,3 4096 16777344 /home/sergiopa/Downloads
find 14152 sergiopa 5r DIR 252,1 4096 4808 /usr/src/linux-headers-2.6.35-22/drivers/rapidio
sergiopa@sergiopa:~/Downloads$
「<<<<」行を見ると、STDIN、STDOUT、STDERRがあります。シェルを閉じましたが、findはまだ実行中です。