亚洲香蕉成人av网站在线观看_欧美精品成人91久久久久久久_久久久久久久久久久亚洲_热久久视久久精品18亚洲精品_国产精自产拍久久久久久_亚洲色图国产精品_91精品国产网站_中文字幕欧美日韩精品_国产精品久久久久久亚洲调教_国产精品久久一区_性夜试看影院91社区_97在线观看视频国产_68精品久久久久久欧美_欧美精品在线观看_国产精品一区二区久久精品_欧美老女人bb

首頁 > 學院 > 開發設計 > 正文

Linux 下的多進程編程

2019-11-17 05:39:47
字體:
來源:轉載
供稿:網友

 ?。ㄒ唬?理解linux下進程的結構
   Linux下一個進程在內存里有三部份的數據,就是“數據段”,“堆棧段”和“代碼段”,其實學過匯編語言的人一定知道,一般的CPU象I386,都有上述三種段寄存器,以方便操作系統的運行?!按a段”,顧名思義,就是存放了程序代碼的數據,假如機器中有數個進程運行相同的一個程序,那么它們就可以使用同一個代碼段。
   堆棧段存放的就是子程序的返回地址、子程序的參數以及程序的局部變量。而數據段則存放程序的全局變量,常數以及動態數據分配的數據空間(比如用malloc之類的函數取得的空間)。這其中有許多細節問題,這里限于篇幅就不多介紹了。系統假如同時運行數個相同的程序,它們之間就不能使用同一個堆棧段和數據段。

(二) 如何使用fork
   在Linux下產生新的進程的系統調用就是fork函數,這個函數名是英文中“分叉”的意思。為什么取這個名字呢?因為一個進程在運行中,假如使用了fork,就產生了另一個進程,于是進程就“分叉”了,所以這個名字取得很形象。下面就看看如何具體使用fork,這段程序演示了使用fork的基本框架:

void main(){
int i;
if ( fork() == 0 ) {
/* 子進程程序 */
for ( i = 1; i <1000; i ++ )
}
else {
/* 父進程程序*/
for ( i = 1; i <1000; i ++ )
printf("This is process process/n");
}
}

   程序運行后,你就能看到屏幕上交替出現子進程與父進程各打印出的一千條信息了。假如程序還在運行中,你用ps命令就能看到系統中有兩個它在運行了。
   那么調用這個fork函數時發生了什么呢?一個程序一調用fork函數,系統就為一個新的進程預備了前述三個段,首先,系統讓新的進程與舊的進程使用同一個代碼段,因為它們的程序還是相同的,對于數據段和堆棧段,系統則復制一份給新的進程,這樣,父進程的所有數據都可以留給子進程,但是,子進程一旦開始運行,雖然它繼續了父進程的一切數據,但實際上數據卻已經分開,相互之間不再有影響了,也就是說,它們之間不再共享任何數據了。而假如兩個進程要共享什么數據的話,就要使用另一套函數(shmget,shmat,shmdt等)來操作。現在,已經是兩個進程了,對于父進程,fork函數返回了子程序的進程號,而對于子程序,fork函數則返回零,這樣,對于程序,只要判定fork函數的返回值,就知道自己是處于父進程還是子進程中。
   讀者也許會問,假如一個大程序在運行中,它的數據段和堆棧都很大,一次fork就要復制一次,那么fork的系統開銷不是很大嗎?其實UNIX自有其解決的辦法,大家知道,一般CPU都是以“頁”為單位分配空間的,象INTEL的CPU,其一頁在通常情況下是4K字節大小,而無論是數據段還是堆棧段都是由許多“頁”構成的,fork函數復制這兩個段,只是“邏輯”上的,并非“物理”上的,也就是說,實際執行fork時,物理空間上兩個進程的數據段和堆棧段都還是共享著的,當有一個進程寫了某個數據時,這時兩個進程之間的數據才有了區別,系統就將有區別的“頁”從物理上也分開。系統在空間上的開銷就可以達到最小。
   一個小幽默:下面演示一個足以"搞死"Linux的小程序,其源代碼非常簡單:

void main()
{
for(;;) fork();
}

   這個程序什么也不做,就是死循環地fork,其結果是程序不斷產生進程,而這些進程又不斷產生新的進程,很快,系統的進程就滿了,系統就被這么多不斷產生的進程"撐死了"。用不著是root,任何人運行上述程序都足以讓系統死掉。哈哈,但這不是Linux不安全的理由,因為只要系統治理員足夠聰明,他(或她)就可以預先給每個用戶設置可運行的最大進程數,這樣,只要不是root,任何能運行的進程數也許不足系統總的能運行和進程數的十分之一,這樣,系統治理員就能對付上述惡意的程序了。

(三) 如何啟動另一程序的執行
   下面我們來看看一個進程如何來啟動另一個程序的執行。在Linux中要使用exec類的函數,exec類的函數不止一個,但大致相同,在Linux中,它們分別是:execl,execlp,execle,execv,execve和execvp,下面我只以execlp為例,其它函數究竟與execlp有何區別,請通過manexec命令來了解它們的具體情況。
   一個進程一旦調用exec類函數,它本身就“死亡”了,系統把代碼段替換成新的程序的代碼,廢棄原有的數據段和堆棧段,并為新程序分配新的數據段與堆棧段,唯一留下的,就是進程號,也就是說,對系統而言,還是同一個進程,不過已經是另一個程序了。(不過exec類函數中有的還答應繼續環境變量之類的信息。)

   那么假如我的程序想啟動另一程序的執行但自己仍想繼續運行的話,怎么辦呢?那就是結合fork與exec的使用。下面一段代碼顯示如何啟動運行其它程序:

char command[256];
void main()
{
int rtn; /*子進程的返回數值*/
while(1) {
/* 從終端讀取要執行的命令 */
printf( ">" );
fgets( command, 256, stdin );
command[strlen(command)-1] = 0;
if ( fork() == 0 ) {
/* 子進程執行此命令 */
execlp( command, command );
/* 假如exec函數返回,表明沒有正常執行命令,打印錯誤信息*/
perror( command );
exit( errorno );
}
else {
/* 父進程, 等待子進程結束,并打印子進程的返回值 */
wait ( &rtn );
printf( " child process return %d/n",. rtn );
}
}
}

   此程序從終端讀入命令并執行之,執行完成后,父進程繼續等待從終端讀入命令。熟悉DOS和WINDOWS系統調用的朋友一定知道DOS/WINDOWS也有exec類函數,其使用方法是類似的,但DOS/WINDOWS還有spawn類函數,因為DOS是單任務的系統,它只能將“父進程”駐留在機器內再執行“子進程”,這就是spawn類的函數。WIN32已經是多任務的系統了,但還保留了spawn類函數,WIN32中實現spawn函數的方法同前述UNIX中的方法差不多,開設子進程后父進程等待子進程結束后才繼續運行。UNIX在其一開始就是多任務的系統,所以從核心角度上講不需要spawn類函數。
   另外,有一個更簡單的執行其它程序的函數system,它是一個較高層的函數,實際上相當于在SHELL環境下執行一條命令,而exec類函數則是低層的系統調用。

(四) Linux的進程與Win32的進程/線程有何區別
   熟悉WIN32編程的人一定知道,WIN32的進程治理方式與UNIX上有著很大區別,在UNIX里,只有進程的概念,但在WIN32里卻還有一個“線程”的概念,那么UNIX和WIN32在這里究竟有著什么區別呢?
   UNIX里的fork是七十年代UNIX早期的開發者經過長期在理論和實踐上的艱苦探索后取得的成果,一方面,它使操作系統在進程治理上付出了最小的代價,另一方面,又為程序員提供了一個簡潔明了的多進程方法。
   WIN32里的進程/線程是繼續自OS/2的。在WIN32里,“進程”是指一個程序,而“線程”是一個“進程”里的一個執行“線索”。從核心上講,WIN32的多進程與UNIX并無多大的區別,在WIN32里的線程才相當于UNIX的進程,是一個實際正在執行的代碼。但是,WIN32里同一個進程里各個線程之間是共享數據段的。這才是與UNIX的進程最大的不同。
   下面這段程序顯示了WIN32下一個進程如何啟動一個線程:(請注重,這是個終端方式程序,沒有圖形界面)

int g;
D
Word WINAPI ChildProcess( LPVOID lpParameter ){
int i;
for ( i = 1; i <1000; i ++) {
g ++;
printf( "This is Child Thread: %d/n", g );
}
ExitThread( 0 );
};

void main()
{
int threadID;
int i;
g = 0;
CreateThread( NULL, 0, ChildProcess, NULL, 0, &threadID );
for ( i = 1; i <1000; i ++) {
g ++;
printf( "This is Parent Thread: %d/n", g );
}
}

   在WIN32下,使用CreateThread函數創建線程,與UNIX不同,線程不是從創建處開始運行的,而是由CreateThread指定一個函數,線程就從那個函數處開始運行。此程序同前面的UNIX程序一樣,由兩個線程各打印1000條信息。threadID是子線程的線程號,另外,全局變量g是子線程與父線程共享的,這就是與UNIX最大的不同之處。大家可以看出,WIN32的進程/線程要比UNIX復雜,在UNIX里要實現類似WIN32的線程并不難,只要fork以后,讓子進程調用ThreadProc函數,并且為全局變量開設共享數據區就行了,但在WIN32下就無法實現類似fork的功能了。所以現在WIN32下的C語言編譯器所提供的庫函數雖然已經能兼容大多數UNIX的庫函數,但卻仍無法實現fork。
   對于多任務系統,共享數據區是必要的,但也是一個輕易引起混亂的問題,在WIN32下,一個程序員很輕易忘記線程之間的數據是共享的這一情況,一個線程修改過一個變量后,另一個線程卻又修改了它

發表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發表
亚洲香蕉成人av网站在线观看_欧美精品成人91久久久久久久_久久久久久久久久久亚洲_热久久视久久精品18亚洲精品_国产精自产拍久久久久久_亚洲色图国产精品_91精品国产网站_中文字幕欧美日韩精品_国产精品久久久久久亚洲调教_国产精品久久一区_性夜试看影院91社区_97在线观看视频国产_68精品久久久久久欧美_欧美精品在线观看_国产精品一区二区久久精品_欧美老女人bb
国产亚洲精品久久| 国产亚洲精品美女久久久| 在线日韩第一页| 午夜精品一区二区三区在线视频| 亚洲国产成人精品久久久国产成人一区| 日av在线播放中文不卡| 亚洲国产精品成人精品| 国产精品免费一区二区三区都可以| 亚洲第一天堂av| 亚洲国产99精品国自产| 亚洲综合最新在线| 国产精品久久久久久久久久尿| 国产成人久久精品| 欧美夫妻性视频| 亚洲精品少妇网址| 国产精品免费看久久久香蕉| 日韩电影中文 亚洲精品乱码| 精品国产户外野外| 海角国产乱辈乱精品视频| 国产精品视频不卡| 精品国偷自产在线视频99| 伊人伊成久久人综合网小说| 国产精品免费看久久久香蕉| 91欧美视频网站| 国产999在线观看| 欧美剧在线观看| 国产国语videosex另类| 欧美日韩国产黄| 欧美乱妇高清无乱码| 丝袜情趣国产精品| 欧美激情精品久久久久久久变态| 日本国产高清不卡| 在线观看久久av| 日韩日本欧美亚洲| 欧美在线影院在线视频| 高潮白浆女日韩av免费看| 国产美女91呻吟求| 亚洲国产精品成人av| 亚洲天堂网站在线观看视频| 久久久久久999| 在线成人激情视频| 国产视频久久网| 久久久久久久久中文字幕| 欧美成人免费小视频| 欧美成人激情视频免费观看| 欧美精品久久久久久久久| 国产日韩中文字幕在线| 中文字幕成人在线| 午夜精品久久久久久久久久久久| 精品国产91久久久| 亚洲午夜国产成人av电影男同| 久久久视频免费观看| 国产精品亚洲视频在线观看| 欧美xxxx做受欧美| 欧美日韩亚洲视频一区| 国产一区二区三区免费视频| 成人黄色免费在线观看| 日韩**中文字幕毛片| 大胆欧美人体视频| 成人精品网站在线观看| 欧美刺激性大交免费视频| 亚洲欧美第一页| 亚洲最新av在线网站| 少妇高潮久久久久久潘金莲| 欧美成人免费一级人片100| 国产精品自拍偷拍| 欧美日韩高清区| 91九色国产在线| 亚洲护士老师的毛茸茸最新章节| 91久久在线播放| 国产精品xxx视频| 成人情趣片在线观看免费| 国产精品美女久久久久av超清| 色悠久久久久综合先锋影音下载| 亚洲免费精彩视频| 亚洲毛片在线免费观看| 国产成人啪精品视频免费网| 成人精品aaaa网站| 成人免费网站在线观看| 欧美性黄网官网| 成人精品在线观看| 国产日本欧美一区二区三区| 久久成人这里只有精品| 国产精品欧美一区二区三区奶水| 国产成人激情小视频| 国产色综合天天综合网| 欧美午夜激情视频| 久久视频在线直播| 国产91精品久久久久久| 九色91av视频| 国产激情综合五月久久| 国产午夜精品美女视频明星a级| 欧美大片在线免费观看| 国产精品久久久999| 国内外成人免费激情在线视频| 国产美女精品免费电影| 亚洲精品久久在线| 日韩av在线高清| 久久黄色av网站| 国产精品久久久久9999| 午夜精品福利电影| 欧美精品久久久久| 日韩美女免费观看| 日韩精品中文字| 日韩欧美一区二区三区久久| 人人爽久久涩噜噜噜网站| 国产精品成人一区二区| 成人av.网址在线网站| 日韩成人在线视频观看| 日本精品久久久| 欧美性猛交xxx| 国产精品旅馆在线| 亚洲自拍高清视频网站| 91免费看视频.| 影音先锋欧美精品| 亚洲国产日韩欧美在线99| 亚洲丝袜av一区| 91精品国产综合久久久久久久久| 国产精品国模在线| 欧美日韩国产精品| 日韩男女性生活视频| 亚洲一区二区在线| 97视频人免费观看| 欧美亚洲免费电影| 中日韩午夜理伦电影免费| 亚洲人成在线播放| 亚洲精品影视在线观看| 黑人精品xxx一区一二区| 国产精品专区一| 国产精品视频久| 97人洗澡人人免费公开视频碰碰碰| 亚洲第一av网| 高清欧美性猛交xxxx| 91av网站在线播放| 欧美一区二区三区免费观看| 久久国产色av| 日韩av免费看网站| 神马国产精品影院av| 亚洲精品美女免费| 亚洲精品av在线| 国产精品久久99久久| 亚洲午夜精品久久久久久久久久久久| 国产精品露脸av在线| 日本一区二区三区四区视频| 中文字幕在线视频日韩| 精品中文字幕视频| 久久久亚洲精选| 国产女人18毛片水18精品| 亚洲最大av在线| 亚洲性无码av在线| 欧美中文字幕视频| 国模私拍视频一区| 久久在线精品视频| 青青a在线精品免费观看| 亚洲视屏在线播放| 亚洲人成网站色ww在线| 欧美老少配视频| 国产成人免费91av在线| 久久久免费精品视频| 久久久久久这里只有精品| 亚洲偷熟乱区亚洲香蕉av| 亚洲成人av在线播放| 成人一区二区电影| 91九色视频在线|