Linux shell 学习笔记(12)— linux 信号、后台运行脚本、作业控制、定时运行任务
1. 處理信號
1.1 Linux 信號
常見的 Linux 信號如下表所示:
| 信號 | 值 | 描述 |
|---|---|---|
| 1 | SIGHUP | 掛起進程 |
| 2 | SIGINT | 終止進程 |
| 3 | SIGQUIT | 停止進程 |
| 9 | SIGKILL | 無條件終止進程 |
| 15 | SIGTERM | 盡可能終止進程 |
| 17 | SIGSTOP | 無條件停止進程,但不是終止進程 |
| 18 | SIGTSTP | 停止或暫停進程,但不終止進程 |
| 19 | SIGCONT | 繼續運行停止的進程 |
默認情況下,bash shell 會忽略收到的任何 SIGQUIT (3) 和 SIGTERM (5) 信號(正因為這樣,交互式 shell 才不會被意外終止)。但是 bash shell 會處理收到的 SIGHUP (1) 和 SIGINT (2) 信號。
如果 bash shell 收到了 SIGHUP 信號,比如當你要離開一個交互式 shell,它就會退出。但在退出之前,它會將 SIGHUP 信號傳給所有由該 shell 所啟動的進程(包括正在運行的 shell 腳本)。
通過 SIGINT 信號,可以中斷 shell。Linux 內核會停止為 shell 分配 CPU 處理時間。這種情況發生時,shell 會將 SIGINT 信號傳給所有由它所啟動的進程,以此告知出現的狀況。
1.2 生成信號
-
中斷進程
Ctrl+C 組合鍵會生成 SIGINT 信號,并將其發送給當前在 shell 中運行的所有進程。
-
暫停進程
Ctrl+Z 組合鍵會生成一個 SIGTSTP 信號,停止 shell 中運行的任何進程。停止(stopping)進程跟終止(terminating)進程不同:停止進程會讓程序繼續保留在內存中,并能從上次停止的位置繼續運行。
$ sleep 100 ^Z [1]+ Stopped sleep 100 $方括號中的數字是 shell 分配的作業號(job number)。shell 將 shell 中運行的每個進程稱為作業,并為每個作業分配唯一的作業號。
2. 以后臺模式運行腳本
2.1 后臺運行腳本
以后臺模式運行 shell 腳本非常簡單。只要在命令后加個 & 符就行了。
$ cat test4.sh
#!/bin/bash
# Test running in the background
#
count=1
while [ $count -le 10 ]
do
sleep 1
count=$[ $count + 1 ]
done
#
$
$ ./test4.sh &
[1] 3231
$
方括號中的數字是 shell 分配給后臺進程的作業號。下一個數是 Linux 系統分配給進程的進程ID(PID)。Linux 系統上運行的每個進程都必須有一個唯一的 PID。
2.2 運行多個后臺作業
可以在命令行提示符下同時啟動多個后臺作業。
$ ./test6.sh &
[1] 3568
$ This is Test Script #1
$ ./test7.sh &
[2] 3570
$ This is Test Script #2
$ ./test8.sh &
[3] 3573
$ And...another Test script
$ ./test9.sh &
[4] 3576
$ Then...there was one more test script
$
每次啟動新作業時,Linux 系統都會為其分配一個新的作業號和 PID。通過 ps 命令,可以看到所有腳本處于運行狀態。
$ ps
PID TTY TIME CMD
2431 pts/0 00:00:00 bash
3568 pts/0 00:00:00 test6.sh
3570 pts/0 00:00:00 test7.sh
3573 pts/0 00:00:00 test8.sh
3574 pts/0 00:00:00 sleep
3575 pts/0 00:00:00 sleep
3576 pts/0 00:00:00 test9.sh
3577 pts/0 00:00:00 sleep
3578 pts/0 00:00:00 sleep
3579 pts/0 00:00:00 ps
$
注意,在 ps 命令的輸出中,每一個后臺進程都和終端會話(pts/0)終端聯系在一起。如果終端會話退出,那么后臺進程也會隨之退出。
2.3 在非控制臺下運行腳本
有時你會想在終端會話中啟動 shell 腳本,然后讓腳本一直以后臺模式運行到結束,即使你退出了終端會話。這可以用 nohup 命令來實現。
nohup 命令運行了另外一個命令來阻斷所有發送給該進程的 SIGHUP 信號。這會在退出終端會話時阻止進程退出。
nohup 命令的格式如下:
$ nohup ./test1.sh &
[1] 3856
$ nohup: ignoring input and appending output to 'nohup.out'
$
和普通后臺進程一樣,shell 會給命令分配一個作業號,Linux 系統會為其分配一個 PID 號。區別在于,當你使用 nohup 命令時,如果關閉該會話,腳本會忽略終端會話發過來的 SIGHUP 信號。
3. 作業控制
啟動、停止、終止以及恢復作業的這些功能統稱為作業控制。通過作業控制,就能完全控制shell環境中所有進程的運行方式了。
3.1 查看作業
jobs 命令允許查看 shell 當前正在處理的作業。腳本用 $$ 變量來顯示 Linux 系統分配給該腳本PID。
jobs 命令可以查看分配給 shell 的作業。jobs 命令會顯示這兩個已停止/運行中的作業,以及它們的作業號和作業中使用的命令。
$ jobs
[1]+ Stopped ./test10.sh
[2]- Running ./test10.sh > test10.out &
$
要想查看作業的 PID,可以在 jobs 命令中加入 -l 選項(小寫的 L)。
$ jobs -l
[1]+ 1897 Stopped ./test10.sh
[2]- 1917 Running ./test10.sh > test10.out &
$
帶加號的作業會被當做默認作業。當前的默認作業完成處理后,帶減號的作業成為下一個默認作業。任何時候都只有一個帶加號的作業和一個帶減號的作業,不管 shell 中有多少個正在運行的作業。
jobs 命令參數
| 參數 | 描述 |
|---|---|
| -l (小寫的L) | 列出進程的PID以及作業號 |
| -n | 只列出上次shell發出的通知后改變了狀態的作業 |
| -p | 只列出作業的PID |
| -r | 只列出運行中的作業 |
| -s | 只列出已停止的作業 |
3.2 重啟停止的作業
在 bash 作業控制中,可以將已停止的作業作為后臺進程或前臺進程重啟。要以后臺模式重啟一個作業,可用 bg 命令加上作業號。
$ ./test11.sh
^Z
[1]+ Stopped ./test11.sh
$
$ bg
[1]+ ./test11.sh &
$
$ jobs
[1]+ Running ./test11.sh &
$
因為該作業是默認作業(從加號可以看出),只需要使用 bg 命令就可以將其以后臺模式重啟。注意,當作業被轉入后臺模式時,并不會列出其 PID。
如果有多個作業,你得在 bg 命令后加上作業號。
$ ./test11.sh
^Z
[1]+ Stopped ./test11.sh
$
$ ./test12.sh
^Z
[2]+ Stopped ./test12.sh
$
$ bg 2
[2]+ ./test12.sh &
$
$ jobs
[1]+ Stopped ./test11.sh
[2]- Running ./test12.sh &
$
命令 bg 2用于將第二個作業置于后臺模式。注意,當使用 jobs 命令時,它列出了作業及其狀態,即便是默認作業當前并未處于后臺模式。
要以前臺模式重啟作業,可用帶有作業號的 fg 命令。
$ fg 2
./test12.sh
This is the script's end...
$
4. 定時運行作業
待補充
總結
以上是生活随笔為你收集整理的Linux shell 学习笔记(12)— linux 信号、后台运行脚本、作业控制、定时运行任务的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: Linux shell 学习笔记(11)
- 下一篇: Linux shell 学习笔记(15)