使用forkexit和exec系統調用編寫多進程程序_第1頁
使用forkexit和exec系統調用編寫多進程程序_第2頁
使用forkexit和exec系統調用編寫多進程程序_第3頁
使用forkexit和exec系統調用編寫多進程程序_第4頁
使用forkexit和exec系統調用編寫多進程程序_第5頁
全文預覽已結束

下載本文檔

版權說明:本文檔由用戶提供并上傳,收益歸屬內容提供方,若內容存在侵權,請進行舉報或認領

文檔簡介

本文格式為Word版,下載可任意編輯——使用forkexit和exec系統調用編寫多進程程序4.3使用fork、exit和exec系統調用編寫多進程程序

本試驗將通過編寫fork等系統調用的程序,加深對系統進程及其控制的了解。fork后父子進程會同步運行,但父子進程的返回順序是不確定的。設兩個變量global和test來檢測父子進程共享資源的狀況。同時在進程退出時對exit和_exit的區別進行測試和說明。

1.fork

#include#include#include#include#include#include//#includeintglobal=22;

charbuf[]=\

intmain(void){

inttest=0,stat;pid_tpid;

if(write(STDOUT_FILENO,buf,sizeof(buf)-1)!=sizeof(buf)-1)

perror(\printf(\/*fork*/

pid=fork();/*weshouldchecktheerror*/if(pid==-1){

perror(\exit;}

/*ifthepid=0thenitisthechild*/elseif(pid==0){global++;test++;

printf(\exit(0);}

/*elsebetheparent*/global+=2;test+=2;

printf(\exit(0);

//printf(\//_exit(0);}

編譯執行,并分析結果:[root@localhostroot]#./testthetestcontent!forktest!

global=23test=1Child,myPIDis2751global=24test=2Parent,myPIDis2750

可以看出父子進程打印出了各自的進程號和對應變量的值,顯然global和test在父子進程間是獨立的,其各自的操作不會對對方的值有影響。將上述代碼最終的兩行代碼替換為解釋掉的_exit(0)行,重新編譯,查看結果,解釋原因:

[root@localhostroot]#./testthetestcontent!forktest!

global=23test=1Child,myPIDis2771

父進程的信息沒有打印出來,其原因是:_exit()函數直接使進程中止運行,清除其使用的內存空間,并銷毀其在內核中的各種數據結構;而exit()函數則在這些基礎上作了一些包裝,在執行退出之前加了若干道工序。exit()函數在調用exit系統調用之前要檢查文件的開啟狀況,把文件緩沖區中的內容寫回文件,即會\清理I/O緩沖\。若將上述_exit(0)改為exit(0),則確定會有打印。另外,需要注意換行符\\n會引起IO的清理操作,若下面的語句printf(\Parent,myPIDis%d\加上\\n,則調用_exit(0)的結果和調用exit(0)的結果是一樣的。

2.vfork的特點

將上述代碼的pid=fork();改為pid=vfork();編譯后運行結果如下:[root@localhostroot]#./testthetestcontent!forktest!

global=23test=1Child,myPIDis2849global=25test=3Parent,myPIDis2848

可以看出,vfork與fork區別在于共享的資源不一樣,vfork調用后,子進程先對global和test加1,父進程運行時,在其基礎之上再加2,得到上述運行結果。即vfork的特點是:在調用execv或者exit前子進程對變量的修改會影響到父進程,即他們是共享的;

特別注意:父進程等待子進程調用execv或exit才繼續執行。則若子進程依靠父進程的進一步動作時,父進程又必需阻塞到子進程調用execv或者exit才會往下執行,此時就會造成“死鎖〞。讀者可自己設計測試一下這種“死鎖〞狀態。

4.4使用fork和exec系統調用編寫執行命令的程序

本試驗將通過編寫fork和exec等系統調用的程序,加深對系統進程及其控制的了解。fork后調用exec族函數來調用系統命令或者程序來實現系統shell功能。

execv函數族的使用

注意點:調用execv后,程序不再返回!在上述代碼基礎上,在子進程的退出代碼前參與如下代碼:

printf(\if(execl(\

perror(\

printf(\exit(0);

編譯運行后結果為:[root@localhostroot]#./testthetestcontent!forktest!

global=23test=1Child,myPIDis2909

USERPID%CPU%MEMVSZRSSTTYSTATSTARTTIMECOMMANDroot27190.00.643601032pts/1S23:140:00/bin/bashroot29080.00.11340276pts/1R23:380:00./testroot29090.00.42684736pts/1R23:380:00ps-auglobal=25test=3Parent,myPIDis2908

4.waitpid的作用是等待子進程退出并回收其資源,同時可以通過WIFEXITED等宏調用可以檢測子進程退出的狀態。在第一個例如fork使用的代碼基礎上進行修改,添加檢測進程退出狀態的子函數,參考代碼如下:

voidexit_check(intstat){if(WIFEXITED(stat))

printf(\elseif(WIFSIGNALED(stat))

printf(\\\n\#ifdefWCOREDUMP/

WCOREDUMP(stat)?\#else\\

#endif//條件編譯,如WIFSIGNALED(stat)為非0,

//且此進程產生一個內存映射文件(coredump)則返回非0elseif(WIFSTOPPED(stat))//假使子進程暫停(stopped)則返回非0printf(\}

在父進程處理global和test變量前參與如下代碼:

if(waitpid(pid,//thestatusofexitcheck編譯運行后結果為:[root@localhostroot]#./testthetestcontent!forktest!

溫馨提示

  • 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
  • 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯系上傳者。文件的所有權益歸上傳用戶所有。
  • 3. 本站RAR壓縮包中若帶圖紙,網頁內容里面會有圖紙預覽,若沒有圖紙預覽就沒有圖紙。
  • 4. 未經權益所有人同意不得將文件中的內容挪作商業或盈利用途。
  • 5. 人人文庫網僅提供信息存儲空間,僅對用戶上傳內容的表現方式做保護處理,對用戶上傳分享的文檔內容本身不做任何修改或編輯,并不能對任何下載內容負責。
  • 6. 下載文件中如有侵權或不適當內容,請與我們聯系,我們立即糾正。
  • 7. 本站不保證下載資源的準確性、安全性和完整性, 同時也不承擔用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。

評論

0/150

提交評論