[原創] Linux 中的 nohup 與 &

嘉興Xing發表於2018-11-29

背景

一直沒搞清楚 nohup& 的區別, 看著公司裡遺留的shell, 也就稀裡糊塗地用著… 這是很糟糕的態度

結論放前面

&

使程式在後臺執行, 預設輸出到標準輸出(即當前螢幕), 除非重定向輸出.

此時忽略 SIGINT 訊號.

==若關閉會話, 則程式會結束==


nohup

程式仍舊在前臺跑, 預設輸出到 nohup.out .

此時程式忽略 SIGHUP 訊號, 關閉會話不影響程式.

==Ctrl+c會使程式中斷==


nohup + &

程式在後臺跑, 忽略 SIGINT, SIGHUP 訊號.

測試

repeat=${1:-20}
echo 迴圈次數 $repeat
counter=0
while [ $counter -lt $repeat ]
do
    echo 第${counter}次迴圈
    let "counter ++"
    sleep 1
done
echo 結束迴圈

直接執行

[root@yjx214 tmp]# sh test.sh
迴圈次數 20
第0次迴圈
第1次迴圈
第2次迴圈
^C

此時不論是直接 Ctrl+c 或 關閉當前ssh連線, 都會導致程式停止

[root@yjx214 tmp]# sh test.sh > test.out
^C

此時程式仍在前端跑, 檢視 test.out 檔案會發現在輸出, 此時不論是直接 Ctrl+C 或 關閉當前ssh連線, 都會導致程式停止

單獨使用 &

[root@yjx214 tmp]# sh test.sh &
[1] 111418
[root@yjx214 tmp]# 迴圈次數 20
第0次迴圈
第1次迴圈
第2次迴圈
^C
[root@yjx214 tmp]# 第3次迴圈
第4次迴圈
第5次迴圈
^C
[root@yjx214 tmp]# 第6次迴圈
第7次迴圈
第8次迴圈
第9次迴圈
第10次迴圈
第11次迴圈

此時程式在後臺跑, 同時預設會輸出到螢幕上.

此時 Ctrl+c 無效, 即程式忽略了 SIGINT 訊號.

但若是直接關閉ssh連線(會話), 則該程式會被關閉, 這是因為程式受到了 SIGHUP 訊號影響.

系統對SIGHUP訊號的預設處理是終止收到該訊號的程式。所以若程式中沒有捕捉該訊號,當收到該訊號時,程式就會退出。
  

[root@yjx214 tmp]# sh test.sh > test.out &
[4] 111758
[root@yjx214 tmp]#

使程式在後臺跑, 輸出被重定向到指定檔案

可用 jobs -l 獲取當前的所有後臺程式

[root@yjx214 tmp]# jobs -l
[2]+ 113043 Running                 sh test.sh > /dev/null &

單獨使用 nohup

[root@yjx214 tmp]# nohup sh test.sh > test.out 2>&1

執行後是在前端跑, 若關閉會話, 程式不受影響.

但此時 Ctrl+c會結束程式.

nohup + &

[root@yjx214 tmp]# nohup sh test.sh &
[2] 112987
[root@yjx214 tmp]# nohup: 忽略輸入並把輸出追加到"nohup.out"

[root@yjx214 tmp]#

忽略 Ctrl+c 以及 會話關閉的影響, 程式可以在後臺持續執行.

若會話未關閉, 可通過 jobs -l 檢視當前該程式

[root@yjx214 tmp]# jobs -l
[1]+ 112987 Running                 nohup sh test.sh &

相關文章