版權(quán)說明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權(quán),請進行舉報或認領(lǐng)
文檔簡介
1、<p><b> 實驗手冊內(nèi)容:</b></p><p> (一) 信號機制實驗</p><p><b> 實驗?zāi)康?lt;/b></p><p><b> 1、了解什么是信號</b></p><p> 2、熟悉LINUX系統(tǒng)中進程之間軟中斷通信的基本原理<
2、/p><p><b> 實驗內(nèi)容</b></p><p> 1、編寫程序:用fork( )創(chuàng)建兩個子進程,再用系統(tǒng)調(diào)用signal( )讓父進程捕捉鍵盤上來的中斷信號(即按^c鍵);捕捉到中斷信號后,父進程用系統(tǒng)調(diào)用kill( )向兩個子進程發(fā)出信號,子進程捕捉到信號后分別輸出下列信息后終止:</p><p> Child process1
3、is killed by parent!</p><p> Child process2 is killed by parent!</p><p> 父進程等待兩個子進程終止后,輸出如下的信息后終止:</p><p> Parent process is killed!</p><p> 2、分析利用軟中斷通信實現(xiàn)進程同步的機理<
4、;/p><p><b> 實驗指導(dǎo)</b></p><p><b> 一、信號</b></p><p><b> 1、信號的基本概念</b></p><p> 每個信號都對應(yīng)一個正整數(shù)常量(稱為signal number,即信號編號。定義在系統(tǒng)頭文件<signal.
5、h>中),代表同一用戶的諸進程之間傳送事先約定的信息的類型,用于通知某進程發(fā)生了某異常事件。每個進程在運行時,都要通過信號機制來檢查是否有信號到達。若有,便中斷正在執(zhí)行的程序,轉(zhuǎn)向與該信號相對應(yīng)的處理程序,以完成對該事件的處理;處理結(jié)束后再返回到原來的斷點繼續(xù)執(zhí)行。實質(zhì)上,信號機制是對中斷機制的一種模擬,故在早期的UNIX版本中又把它稱為軟中斷。</p><p> 信號與中斷的相似點:</p>
6、<p> ?。?)采用了相同的異步通信方式;</p><p> ?。?)當(dāng)檢測出有信號或中斷請求時,都暫停正在執(zhí)行的程序而轉(zhuǎn)去執(zhí)行相應(yīng)的處理程序;</p><p> (3)都在處理完畢后返回到原來的斷點;</p><p> ?。?)對信號或中斷都可進行屏蔽。</p><p><b> 信號與中斷的區(qū)別:</b
7、></p><p> ?。?)中斷有優(yōu)先級,而信號沒有優(yōu)先級,所有的信號都是平等的;</p><p> ?。?)信號處理程序是在用戶態(tài)下運行的,而中斷處理程序是在核心態(tài)下運行;</p><p> ?。?)中斷響應(yīng)是及時的,而信號響應(yīng)通常都有較大的時間延遲。</p><p> 信號機制具有以下三方面的功能:</p><
8、;p> ?。?)發(fā)送信號。發(fā)送信號的程序用系統(tǒng)調(diào)用kill( )實現(xiàn);</p><p> ?。?)預(yù)置對信號的處理方式。接收信號的程序用signal( )來實現(xiàn)對處理方式的預(yù)置;</p><p> (3)收受信號的進程按事先的規(guī)定完成對相應(yīng)事件的處理。</p><p><b> 2、信號的發(fā)送</b></p><p
9、> 信號的發(fā)送,是指由發(fā)送進程把信號送到指定進程的信號域的某一位上。如果目標(biāo)進程正在一個可被中斷的優(yōu)先級上睡眠,核心便將它喚醒,發(fā)送進程就此結(jié)束。一個進程可能在其信號域中有多個位被置位,代表有多種類型的信號到達,但對于一類信號,進程卻只能記住其中的某一個。</p><p> 進程用kill( )向一個進程或一組進程發(fā)送一個信號。</p><p><b> 3、對信號的
10、處理</b></p><p> 當(dāng)一個進程要進入或退出一個低優(yōu)先級睡眠狀態(tài)時,或一個進程即將從核心態(tài)返回用戶態(tài)時,核心都要檢查該進程是否已收到軟中斷。當(dāng)進程處于核心態(tài)時,即使收到軟中斷也不予理睬;只有當(dāng)它返回到用戶態(tài)后,才處理軟中斷信號。對軟中斷信號的處理分三種情況進行:</p><p> ?。?)如果進程收到的軟中斷是一個已決定要忽略的信號(function=1),進程不做
11、任何處理便立即返回;</p><p> ?。?)進程收到軟中斷后便退出(function=0);</p><p> ?。?)執(zhí)行用戶設(shè)置的軟中斷處理程序。</p><p> 二、所涉及的中斷調(diào)用</p><p><b> 1、kill( )</b></p><p><b> 系統(tǒng)調(diào)
12、用格式</b></p><p> int kill(pid,sig)</p><p><b> 參數(shù)定義</b></p><p> int pid,sig;</p><p> 其中,pid是一個或一組進程的標(biāo)識符,參數(shù)sig是要發(fā)送的軟中斷信號。</p><p> ?。?)
13、pid>0時,核心將信號發(fā)送給進程pid。</p><p> ?。?)pid=0時,核心將信號發(fā)送給與發(fā)送進程同組的所有進程。</p><p> ?。?)pid=-1時,核心將信號發(fā)送給所有用戶標(biāo)識符真正等于發(fā)送進程的有效用戶標(biāo)識號的進程。</p><p> 2、signal( )</p><p> 預(yù)置對信號的處理方式,允許調(diào)用進
14、程控制軟中斷信號。</p><p><b> 系統(tǒng)調(diào)用格式</b></p><p> signal(sig,function)</p><p><b> 頭文件為</b></p><p> #include <signal.h></p><p><b
15、> 參數(shù)定義</b></p><p> signal(sig,function)</p><p><b> int sig;</b></p><p> void (*func) ( )</p><p> 其中sig用于指定信號的類型,sig為0則表示沒有收到任何信號,余者如下表:</p
16、><p> function:在該進程中的一個函數(shù)地址,在核心返回用戶態(tài)時,它以軟中斷信號的序號作為參數(shù)調(diào)用該函數(shù),對除了信號SIGKILL,SIGTRAP和SIGPWR以外的信號,核心自動地重新設(shè)置軟中斷信號處理程序的值為SIG_DFL(進程終止),一個進程不能捕獲SIGKILL信號。</p><p> function 的解釋如下:</p><p> ?。?)f
17、unction=1(即SIG_IGN)時,進程對sig類信號不予理睬,亦即屏蔽了該類信號;</p><p> ?。?)function=0(即SIG_DFL)時,缺省值,進程在收到sig信號后應(yīng)終止自己;</p><p> (3)function為非0、非1類整數(shù)時,function的值即作為信號處理程序的指針。</p><p><b> 三、參考程序
18、</b></p><p> #include <stdio.h></p><p> #include <signal.h></p><p> #include <unistd.h></p><p> void waiting( ),stop( );</p><p>
19、; int wait_mark;</p><p><b> main( )</b></p><p><b> {</b></p><p> int p1,p2,stdout;</p><p> while((p1=fork( ))= =-1); /*創(chuàng)建子進程p1*/</
20、p><p><b> if (p1>0)</b></p><p><b> {</b></p><p> while((p2=fork( ))= =-1); /*創(chuàng)建子進程p2*/</p><p><b> if(p2>0)</b></p>
21、<p><b> {</b></p><p> wait_mark=1;</p><p> signal(SIGINT,stop); /*接收到^c信號,轉(zhuǎn)stop*/</p><p> waiting( );</p><p> kill(p1,16); /*向p1發(fā)軟中斷信號16
22、*/</p><p> kill(p2,17); /*向p2發(fā)軟中斷信號17*/</p><p> wait(0); /*同步*/</p><p><b> wait(0);</b></p><p> printf("Parent process is killed!\
23、n");</p><p><b> exit(0);</b></p><p><b> }</b></p><p><b> else</b></p><p><b> {</b></p><p> wait_m
24、ark=1;</p><p> signal(17,stop); /*接收到軟中斷信號17,轉(zhuǎn)stop*/</p><p> waiting( );</p><p> lockf(stdout,1,0);</p><p> printf("Child process 2 is killed by parent!\n&qu
25、ot;);</p><p> lockf(stdout,0,0);</p><p><b> exit(0);</b></p><p><b> }</b></p><p><b> }</b></p><p><b> else&l
26、t;/b></p><p><b> {</b></p><p> wait_mark=1;</p><p> signal(16,stop); /*接收到軟中斷信號16,轉(zhuǎn)stop*/</p><p> waiting( );</p><p> lockf(stdo
27、ut,1,0);</p><p> printf("Child process 1 is killed by parent!\n");</p><p> lockf(stdout,0,0);</p><p><b> exit(0);</b></p><p><b> }
28、}</b></p><p> void waiting( )</p><p><b> {</b></p><p> while(wait_mark!=0);</p><p><b> }</b></p><p> void stop( )</p&
29、gt;<p><b> {</b></p><p> wait_mark=0;</p><p><b> }</b></p><p><b> 四、運行結(jié)果</b></p><p> 屏幕上無反應(yīng),按下^C后,顯示 Parent process i
30、s killed!</p><p><b> 五、分析原因</b></p><p> 上述程序中,signal( )都放在一段程序的前面部位,而不是在其他接收信號處。這是因為signal( )的執(zhí)行只是為進程指定信號值16或17的作用,以及分配相應(yīng)的與stop( )過程鏈接的指針。因而,signal( )函數(shù)必須在程序前面部分執(zhí)行。</p><
31、;p> 本方法通信效率低,當(dāng)通信數(shù)據(jù)量較大時一般不用此法。</p><p><b> 六、思考</b></p><p> 1、該程序段前面部分用了兩個wait(0),它們起什么作用?</p><p> 2、該程序段中每個進程退出時都用了語句exit(0),為什么?</p><p> 3、為何預(yù)期的結(jié)果并未
32、顯示出?</p><p> 4、(重點)程序該如何修改才能得到正確結(jié)果?(實驗報告中寫出完整程序)</p><p> 5、*不修改程序如何得到期望的輸出?(給出合理的思路即可)</p><p> 以下為實驗報告部分:</p><p><b> 實驗 信號機制</b></p><p>
33、姓名 Lee QQ 615824191</p><p><b> 實驗?zāi)康?lt;/b></p><p><b> 1、了解什么是信號</b></p><p> 2、熟悉LINUX系統(tǒng)中進程之間軟中斷通信的基本原理</p><p><b> 實驗內(nèi)容</b></p&g
34、t;<p> 1、編寫程序:用fork( )創(chuàng)建兩個子進程,再用系統(tǒng)調(diào)用signal( )讓父進程捕捉鍵盤上來的中斷信號(即按^c鍵);捕捉到中斷信號后,父進程用系統(tǒng)調(diào)用kill( )向兩個子進程發(fā)出信號,子進程捕捉到信號后分別輸出下列信息后終止:</p><p> Child process1 is killed by parent!</p><p> Child p
35、rocess2 is killed by parent!</p><p> 父進程等待兩個子進程終止后,輸出如下的信息后終止:</p><p> Parent process is killed!</p><p> 2、分析利用軟中斷通信實現(xiàn)進程同步的機理</p><p><b> 實驗步驟</b></p&
36、gt;<p> 將參考程序用vi編輯器錄入,然后編譯執(zhí)行</p><p> #include <stdio.h></p><p> #include <signal.h></p><p> #include <unistd.h></p><p> void waiting( ),st
37、op( );</p><p> int wait_mark;</p><p><b> main( )</b></p><p><b> {</b></p><p> int p1,p2,stdout;</p><p> while((p1=fork( ))= =-
38、1); /*創(chuàng)建子進程p1*/</p><p><b> if (p1>0)</b></p><p><b> {</b></p><p> while((p2=fork( ))= =-1); /*創(chuàng)建子進程p2*/</p><p><b> if(p2&
39、gt;0)</b></p><p><b> {</b></p><p> wait_mark=1;</p><p> signal(SIGINT,stop); /*接收到^c信號,轉(zhuǎn)stop*/</p><p> waiting( );</p><p> kill(p1
40、,16); /*向p1發(fā)軟中斷信號16*/</p><p> kill(p2,17); /*向p2發(fā)軟中斷信號17*/</p><p> wait(0); /*同步*/</p><p><b> wait(0);</b></p><p> printf("
41、Parent process is killed!\n");</p><p><b> exit(0);</b></p><p><b> }</b></p><p><b> else</b></p><p><b> {</b><
42、;/p><p> wait_mark=1;</p><p> signal(17,stop); /*接收到軟中斷信號17,轉(zhuǎn)stop*/</p><p> waiting( );</p><p> lockf(stdout,1,0);</p><p> printf("Child process 2
43、 is killed by parent!\n");</p><p> lockf(stdout,0,0);</p><p><b> exit(0);</b></p><p><b> }</b></p><p><b> }</b></p>
44、<p><b> else</b></p><p><b> {</b></p><p> wait_mark=1;</p><p> signal(16,stop); /*接收到軟中斷信號16,轉(zhuǎn)stop*/</p><p> waiting( );</p&
45、gt;<p> lockf(stdout,1,0);</p><p> printf("Child process 1 is killed by parent!\n");</p><p> lockf(stdout,0,0);</p><p><b> exit(0);</b></p>&
46、lt;p><b> } }</b></p><p> void waiting( )</p><p><b> {</b></p><p> while(wait_mark!=0);</p><p><b> }</b></p><
47、p> void stop( )</p><p><b> {</b></p><p> wait_mark=0;</p><p><b> }</b></p><p><b> 運行結(jié)果</b></p><p> 屏幕上無反應(yīng),按下^C
48、后,顯示 Parent process is killed!</p><p><b> 分析原因</b></p><p> 上述程序中,signal( )都放在一段程序的前面部位,而不是在其他接收信號處。這是因為signal( )的執(zhí)行只是為進程指定信號值16或17的作用,以及分配相應(yīng)的與stop( )過程鏈接的指針。因而,signal( )函數(shù)必須在程序
49、前面部分執(zhí)行。</p><p><b> 思考</b></p><p> 1. 該程序段前面部分用了兩個wait(0),它們起什么作用?</p><p> 該程序段前面部分用的兩個 wait(0) 是為了讓父進程等待子進程結(jié)束后再結(jié)束自己,在此過程中,父進程處于掛起狀態(tài)。</p><p> 2. 該程序段中每個進
50、程退出時都用了語句exit(0),為什么?</p><p> 用 exit(0) 是為了讓子進程自我終止,正常退出。</p><p> 3. 為何預(yù)期的結(jié)果并未顯示出?</p><p> p1、p2 都會捕捉該中斷信號。對于父進程,當(dāng)它捕捉到中斷信號后就會就會轉(zhuǎn)向程序中指定的函數(shù)“stop()”,當(dāng)“stop()”執(zhí)行完畢后,父進程被喚醒,從中斷處繼續(xù)運行。對
51、于子進程,由于沒有給它們指定收到中斷信號后的動作,它們會在捕捉到中斷信號后執(zhí)行默認操作,即結(jié)束自己。所以當(dāng)我們發(fā)出中斷信號后,父進程按預(yù)計方式正常執(zhí)行,而 p1、p2 就被自己結(jié)束了,從而也就不會有預(yù)計的結(jié)果了。</p><p> 4. 程序該如何修改才能得到正確結(jié)果?</p><p> 為了使程序運行得到正確的結(jié)果,可以在每個子進程程序段開頭加上忽略“^C”中斷信號的語句,即:sig
52、nal(SIGINT,SIG_IGN) 。</p><p> #include <stdio.h></p><p> #include <signal.h></p><p> #include <unistd.h></p><p> #include <stdlib.h></p&g
53、t;<p> void waiting() ;</p><p> void stop() ;</p><p> int wait_mark ;</p><p><b> main() {</b></p><p> int p1,p2,stdout ;</p><p> w
54、hile((p1 = fork()) == -1) ;</p><p> if (p1 > 0) {</p><p> while((p2 = fork()) == -1) ;</p><p> if (p2 > 0) {</p><p> wait_mark = 1 ;</p><p> sig
55、nal(SIGINT,stop) ;</p><p> waiting() ;</p><p> kill(p1,16) ;</p><p> kill(p2,17) ;</p><p><b> wait(0) ;</b></p><p><b> wait(0) ;<
56、/b></p><p> printf("Parent process is killed !\n") ;</p><p><b> exit(0) ;</b></p><p><b> } else {</b></p><p> signal(SIGINT,SIG
57、_IGN) ;</p><p> wait_mark = 1 ;</p><p> signal(17,stop) ;</p><p> waiting() ;</p><p> lockf(stdout,1,0) ;</p><p> printf("Child process 2 is kill
58、ed by parent !\n") ;</p><p> lockf(stdout,0,0) ;</p><p><b> exit(0) ;</b></p><p><b> }</b></p><p><b> } else {</b></p>
59、;<p> signal(SIGINT,SIG_IGN) ;</p><p> wait_mark = 1 ;</p><p> signal(16,stop) ;</p><p> waiting() ;</p><p> lockf(stdout,1,0) ;</p><p> print
60、f("Child process 1 is killed by parent !\n") ;</p><p> lockf(stdout,0,0) ;</p><p><b> exit(0) ;</b></p><p><b> }</b></p><p><b&g
61、t; }</b></p><p> void waiting() {</p><p> while(wait_mark != 0) ;</p><p><b> }</b></p><p> void stop() {</p><p> wait_mark = 0 ;<
62、;/p><p><b> }</b></p><p> 不修改程序如何得到期望的輸出?</p><p> 在不修改程序的情況下要輸出期望的結(jié)果,可以單獨向父進程發(fā)送SIGINT信號,這樣即可避免子進程由于收到SIGINT信號執(zhí)行默認操作而自我終止,具體實現(xiàn)方法:</p><p> ?。ㄔ搶嶒炛谐绦蛎麨椋篸emo2)&l
63、t;/p><p> 首先讓程序在后臺運行,命令:./demo2&</p><p> 執(zhí)行該命令后,會在后臺生成3個進程,使用ps命令可以查看到它們的PID (相對小的PID應(yīng)該為父進程的PID,原因是創(chuàng)建時間相對早)。</p><p> 然后向后臺的父進程發(fā)送SIGINT信號,命令:kill –SIGINT 28664 (其中28664為父進程的PID)&
64、lt;/p><p> 具體實驗結(jié)果見下圖:</p><p><b> 心得與體會</b></p><p> 通過該實驗,我對 UNIX/LINUX 下軟中斷的實現(xiàn)原理與機制有了一個初步的認識,可以用kill() 函數(shù)和signal() 函數(shù)實現(xiàn)簡單的軟中斷程序,并且領(lǐng)會到了程序中wait_mark 所起的作用。在研究第五個思考題時,學(xué)習(xí)了進程
溫馨提示
- 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
- 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
- 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁內(nèi)容里面會有圖紙預(yù)覽,若沒有圖紙預(yù)覽就沒有圖紙。
- 4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
- 5. 眾賞文庫僅提供信息存儲空間,僅對用戶上傳內(nèi)容的表現(xiàn)方式做保護處理,對用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對任何下載內(nèi)容負責(zé)。
- 6. 下載文件中如有侵權(quán)或不適當(dāng)內(nèi)容,請與我們聯(lián)系,我們立即糾正。
- 7. 本站不保證下載資源的準(zhǔn)確性、安全性和完整性, 同時也不承擔(dān)用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。
最新文檔
- 操作系統(tǒng)課程設(shè)計——操作系統(tǒng)課程設(shè)計模擬操作系統(tǒng)
- 操作系統(tǒng)課程設(shè)計-- 操作系統(tǒng)
- 操作系統(tǒng)課程設(shè)計---信號量的操作
- 操作系統(tǒng)課程設(shè)計實驗報告
- 操作系統(tǒng)課程設(shè)計實驗報告
- 操作系統(tǒng)課程設(shè)計
- 操作系統(tǒng)課程設(shè)計
- 操作系統(tǒng)課程設(shè)計
- 操作系統(tǒng)課程設(shè)計
- 操作系統(tǒng)課程設(shè)計
- 操作系統(tǒng)課程設(shè)計
- 內(nèi)存管理(操作系統(tǒng))操作系統(tǒng)課程設(shè)計
- 操作系統(tǒng)課程設(shè)計題目
- 操作系統(tǒng)課程設(shè)計報告
- 操作系統(tǒng)課程設(shè)計論文
- 操作系統(tǒng)課程設(shè)計 (4)
- 操作系統(tǒng)課程設(shè)計1
- 課程設(shè)計報告--操作系統(tǒng)
- linux操作系統(tǒng)課程設(shè)計
- 操作系統(tǒng)課程設(shè)計報告
評論
0/150
提交評論