天天看點

10個 Linux/Unix下 Bash 和 KSH shell 的作業控制執行個體

10個 Linux/Unix下 Bash 和 KSH shell 的作業控制執行個體

linux 和 unix 屬于多任務的作業系統,也就是說一個系統在同一時間段内能運作多重任務(程序)。在這個新的部落格系列,我将會列出相關的 linux 和 unix 作業(job)控制的指令,你可以通過這些指令在 bash 或 korn 還有 posix shell 下實作執行多重任務。

<a target="_blank"></a>

作業控制不隻是能夠停止/挂起(stop/suspend)正在執行的程序(指令),也可以繼續/喚醒(continue/resume)執行你需要的每一個程序。這完全可以用你的作業系統和 bash/ksh 之類的 shell 或 posix shell 完成。

bash / korn shell,或者是 posix shell 提供給了作業控制的環境。

你的 shell 會留有一張目前作業的表單,稱為作業表。當你鍵入指令時,shell 會給它配置設定一個 jobid(也稱作 jobspec)。一個 jobid 或 jobspec隻是很小的整數數值。

我要運作一個名為 xeyes 的指令,它會在螢幕上顯示兩個橢圓的眼睛,輸入: $ xeyes &amp;

輸出樣例:

10個 Linux/Unix下 Bash 和 KSH shell 的作業控制執行個體

fig.01: 在背景運作 xeyes 指令

我使用&amp;符号讓一個 job 在背景運作。shell 會列印一行資訊類似如下:

[1] 6891

在這個例子中,有兩個數字輸出,分别表示:

6891 : 作業1的程序id。

我在多執行一些 job:

## 啟動一個文本編輯器,x 的系統負載顯示,和 sleep 指令 ##

gedit /tmp/hello.c &amp;

xload &amp;

sleep 100000 &amp;

$ jobs

$ jobs -l

輸出如下:

[1] 9379 running xeyes &amp;

[2] 9380 running gedit /tmp/hello.c &amp;

[3]- 9420 running xload &amp;

[4]+ 9421 running sleep 100000 &amp;

簡要描述如下:

字段

描述

示例

1

[1]

jobid 或 job_spec - 工作号要與fg, bg, wait, kill和其他shell指令一起使用。你必須在工作号字首添加一個百分号:(%)。

加号 (+) 辨別着預設的或是現在的作業。

減号 (-) 辨別着前一個作業。

%1

fg %1

kill %2

2

9379

程序 id - 系統自動為每個程序建立并配置設定地獨有的身份标志号。

kill 9379

3

running

狀态 - 關于作業的狀态:

running - 該 作業正在運作,還沒有被外部信号挂起。

stopped - 該作業已經被挂起。

n/a

4

xeyes &amp;

command - 由shell給出的指令。

script &amp;

firefox url&amp;

你也可以用 ps 命名列出目前系統正在運作的程序:

$ ps

kill -s stop pid

10個 Linux/Unix下 Bash 和 KSH shell 的作業控制執行個體

animated gif 01: 挂起 ping 指令作業

## ping 指令的作業号的值為5 ##

fg %5

我也可以規定指令行開端符合字元串"ping"的作業[譯注:不能出現不明确的字元串,例如如果背景有兩個 vim 程序而你敲入 fg %vim 會報錯。]:

## %string ##

fg %ping

64 bytes from www.cyberciti.biz (75.126.153.206): icmp_req=3 ttl=53 time=265 ms

64 bytes from www.cyberciti.biz (75.126.153.206): icmp_req=4 ttl=53 time=249 ms

64 bytes from www.cyberciti.biz (75.126.153.206): icmp_req=5 ttl=53 time=267 ms

^c

# yum -y update &amp;&gt;/root/patch.log &amp;

然而,由于一些原因(例如,過載問題)我決定停止這個作業20分鐘:

# kill -s stop %yum

[7]+ stopped yum -y update &amp;&gt;/root/patch.log &amp;

用 bg 重新開機停止在背景的 yum 程序

# bg %7

或者:

# bg %yum

[7]+ yum -y update &amp;&gt;/root/patch.log &amp;

# kill %7

或者

# kill 程序id

[7]+ terminated yum -y update &amp;&gt;/root/patch.log &amp;

~/scripts/www/pdfwriter.py --profile=faq --type=clean --header=logo\

--footer-left "nixcraft is git ul++++ w+++ c++++ m+ e+++ d-" \

--footer-right "page [of] of [total]" &amp;

$ ~/scripts/www/pdfwriter.py --profile=faq .... &amp;

$ disown

$ exit

$ nohup ~/scripts/www/pdfwriter.py --profile=faq .... &amp;

為了查找最近在背景執行的(異步)指令的程序id,可使用 bash shell 的特殊參數 $!

$ gedit foo.txt &amp;

$ echo "最近在背景執行的job 的pid - $!"

最近在背景執行的job 的pid - 9421

wait 指令會等候給予的程序id 或 作業id指定的程序,然後報告它的終止狀态。文法如下:

/path/to/large-job/command/foo &amp;

wait $!

/path/to/next/job/that-is-dependents/on-foo-command/bar

這是我的一個工作腳本:

#!/bin/bash

# a shell script wrapper to create pdf files for our blog/faq section

########################################################################

# init() - must be run first

# purpose - create index file in $_tmp for all our wordpress databases

init(){

_php="/usr/bin/php"

_phpargs="-d apc.enabled=0"

_base="~/scripts"

_tmp="$_base/tmp"

_what="$1"

for i in $_what

do

[[ ! -d "$_tmp/$i" ]] &amp;&amp; /bin/mkdir "$_tmp/$i"

$_php $_phpargs -f "$_base/php/rawsqlmaster${i}.php" &gt; "$_tmp/$i/output.txt"

done

}

#####################################################

# without index file, we can out generate pdf files

init blog

###########################################################

# do not run the rest of the script until init() finished

## alright, create pdf files

~/scripts/www/pdfwriter.py --profile=blog --type=clean --header=logo\

--footer-right "page [of] of [total]"

指令

&amp;

将作業置入背景

指令 &amp;

%n

設定作業号為 n (數字)的作業

指令 %1

%word

引用指令行開端包含 word 的作業

指令 %yum

%?word

引用指令行包含 word 的作業

指令 %?ping

%%

%+

引用目前作業

kill %%

kill %+

%-

引用先前作業

bg %-

ctrl-z

kill -s stop jobid

挂起或停止作業

kill -s stop %ping

jobs

jobs -l

列出活動的作業

bg

将 作業置入背景

bg %1

bg %ping

fg

将作業置入前台

fg %2

fg %apt-get

運作下面的 type 指令找出給予指令是否屬于内部或外部的。

type -a fg bg jobs disown

輸出樣式:

fg is a shell builtin

fg is /usr/bin/fg

bg is a shell builtin

bg is /usr/bin/bg

jobs is a shell builtin

jobs is /usr/bin/jobs

disown is a shell builtin

在幾乎所有情況下,你都需要使用 shell 的内置指令。所有外部指令例如 /usr/bin/fg 或 /usr/bin/jobs 工作在一個不同的 shell 環境下,而不能用在父 shell 的環境下。

原文釋出時間為:2014-03-13

本文來自雲栖社群合作夥伴“linux中國”