日韩av黄I国产麻豆传媒I国产91av视频在线观看I日韩一区二区三区在线看I美女国产在线I麻豆视频国产在线观看I成人黄色短片

歡迎訪問(wèn) 生活随笔!

生活随笔

當(dāng)前位置: 首頁(yè) >

Linux多任务编程——进程

發(fā)布時(shí)間:2025/3/20 33 豆豆
生活随笔 收集整理的這篇文章主要介紹了 Linux多任务编程——进程 小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.

進(jìn)程編程常用函數(shù)

1--- fork

  pitd_t fork(void);
  創(chuàng)建一個(gè)新的子進(jìn)程,其父進(jìn)程為調(diào)用 fork() 函數(shù)的進(jìn)程;
  返回值:成功:子進(jìn)程返回 0,父進(jìn)程返回 子進(jìn)程 PID;失敗 返回 -1;
  *1>新創(chuàng)建的子進(jìn)程PID,與父進(jìn)程PID不同;
  *2>子進(jìn)程 從 fork() 返回值開(kāi)始運(yùn)行,返回值為 0;父進(jìn)程 fork() 返回新創(chuàng)建的子線程 PID

1 int main() 2 { 3 pid_t pid; 4 if ((pid = fork()) == -1) { 5 perror("fork"); 6 return 0; 7 } 8 else if (pid == 0) { //返回 0 代表子進(jìn)程 9 printf("The return value is %d In child process! My PID is %d, My PPID is %d\n", pid, getpid(), getppid()); 10 } 11 return 0; 12 }

?

2--- exec函數(shù)族???

?????? exec函數(shù)族的作用是根據(jù)指定的文件名找到可執(zhí)行文件,并用它來(lái)取代調(diào)用進(jìn)程的內(nèi)容,換句話說(shuō),就是在調(diào)用進(jìn)程內(nèi)部執(zhí)行一個(gè)可執(zhí)行文件。這里的可執(zhí)行文件既可以是二進(jìn)制文件,也可以是任何Linux下可執(zhí)行的腳本文件。

?????? 與一般情況不同,exec函數(shù)族的函數(shù)執(zhí)行成功后不會(huì)返回,因?yàn)檎{(diào)用進(jìn)程的實(shí)體,包括代碼段,數(shù)據(jù)段和堆棧等都已經(jīng)被新的內(nèi)容取代,只留下進(jìn)程ID等一些表面上的信息仍保持原樣,頗有些神似"三十六計(jì)"中的"金蟬脫殼"。看上去還是舊的軀殼,卻已經(jīng)注入了新的靈魂。只有調(diào)用失敗了,它們才會(huì)返回一個(gè)-1,從原程序的調(diào)用點(diǎn)接著往下執(zhí)行。

  可以使用 fork 創(chuàng)建一個(gè)子進(jìn)程,在子進(jìn)程中進(jìn)行 exec 函數(shù)的調(diào)用 去完成某些比較危險(xiǎn)的操作。使用時(shí)一定要注意這一點(diǎn)。

  exec家族一共有六個(gè)函數(shù),分別是: 

  (1)int execl(const char *path, const char *arg, ......);

  (2)int execle(const char *path, const char *arg, ...... , char * const envp[]);

  (3)int execv(const char *path, char *const argv[]);

  (4)int execve(const char *filename, char *const argv[], char *const envp[]); 

  (5)int execvp(const char *file, char * const argv[]);

  (6)int execlp(const char *file, const char *arg, ......);  

  其中只有execve是真正意義上的系統(tǒng)調(diào)用,其它都是在此基礎(chǔ)上經(jīng)過(guò)包裝的庫(kù)函數(shù)。

1 #include <stdio.h> 2 #include <unistd.h> 3 4 int main() 5 { 6 /*調(diào)用execlp函數(shù),相當(dāng)于調(diào)用了 “ps -ef”命令*/ 7 if(execlp("ps", "ps", "-ef", NULL) < 0 8 { 9 perror("ececlp error!"); 10 } 11 return 0; 12 }

它們之間的區(qū)別:

  第一個(gè)區(qū)別是:
?????? 前四個(gè)取路徑名做為參數(shù),后兩個(gè)取文件名做為參數(shù),如果文件名中不包含 “/” 則從PATH環(huán)境變量中搜尋可執(zhí)行文件, 如果找到了一個(gè)可執(zhí)行文件,但是該文件不是連接編輯程序產(chǎn)生的可執(zhí)行代碼文件,則當(dāng)做shell腳本處理。

  第二個(gè)區(qū)別:
?????? 前兩個(gè)和最后一個(gè)函數(shù)中都包括“ l ”這個(gè)字母 ,而另三個(gè)都包括“ v ”, " l "代表 list即表 ,而" v "代表 vector即矢量,也是是前三個(gè)函數(shù)的參數(shù)都是以list的形式給出的,但最后要加一個(gè)空指針,如果用常數(shù)0來(lái)表示空指針,則必須將它強(qiáng)行轉(zhuǎn)換成字符指針,否則有可能出錯(cuò)。,而后三個(gè)都是以矢量的形式給出,即數(shù)組。

  最后一個(gè)區(qū)別:
????? 與向新程序傳遞環(huán)境變量有關(guān),如第二個(gè)和第四個(gè)以e結(jié)尾的函數(shù),可以向函數(shù)傳遞一個(gè)指向環(huán)境字符串指針數(shù)組的指針。即自個(gè)定義各個(gè)環(huán)境變量,而其它四個(gè)則使用進(jìn)程中的環(huán)境變量。

?

3--- exit( ) 和 _exit( )

  exit( )是標(biāo)準(zhǔn)庫(kù)函數(shù)(Standard library)

  _exit( ) 時(shí)系統(tǒng)調(diào)用函數(shù)(system call)

  exit( ) 和 _exit( ) 都是用來(lái)終止進(jìn)程的。當(dāng)程序執(zhí)行到 exit( )或 _exit( )時(shí),進(jìn)程會(huì)無(wú)條件地停止剩下的所有操作,清除各種數(shù)據(jù)結(jié)構(gòu),并終止本進(jìn)程的運(yùn)行。但是這連個(gè)函數(shù)還是有區(qū)別的:

?

4--- wait( ) 和 waitpid( )

  wait( )函數(shù)用于父進(jìn)程(也就是調(diào)用它的進(jìn)程)阻塞,直到一個(gè)子進(jìn)程結(jié)束,或者接到一個(gè)指定信號(hào)為止,如果父進(jìn)程沒(méi)有子進(jìn)程或者其他進(jìn)程的子進(jìn)程已經(jīng)結(jié)束,則wait( )會(huì)立即返回 -1;

  waitpid( )的作用和wait( )一樣,但并不一定等待第一個(gè)終止的子進(jìn)程。waitpid( )有若干個(gè)選項(xiàng),可以提供一個(gè)非阻塞版本的wait()功能。

函數(shù)原型:

  pid_t wait(int *status);  status 指向的整型對(duì)象用來(lái)保存進(jìn)程結(jié)束時(shí)的狀態(tài)。另外,子進(jìn)程的結(jié)束狀態(tài)可由linux中一些特定的宏來(lái)測(cè)定。

  返回值   成功:已回收子進(jìn)程的進(jìn)程號(hào)。    失敗: -1

  pid_t waitpid(pid_t pid, int *status, int options);

  pid: pid > 0: 回收進(jìn)程 ID 為 pid 的子進(jìn)程

     pid = -1:回收任何一個(gè)子進(jìn)程,此時(shí)和 wait()功能一樣

    ?? pid = 0:回收其組 ID 等于調(diào)用進(jìn)程的 ID 的任一子進(jìn)程

     pid?< -1:回收其組 ID 等于 pid 的絕對(duì)值的任一子進(jìn)程

  status:同wait()

  options:WNOHANG:若指定的子進(jìn)程沒(méi)有結(jié)束,則 waitpid()不阻塞而立即返回,此時(shí)返回值為 0

      ? WUNRTACED:為了實(shí)現(xiàn)某種操作,由pid 指定的任一子進(jìn)程已被暫停,但其狀態(tài)自暫停依賴還未報(bào)告過(guò),則返回其狀態(tài)

  返回值:>0:已結(jié)束運(yùn)行的子進(jìn)程的進(jìn)程號(hào)

      0:使用 WNOHANG 且沒(méi)有子進(jìn)程退出

      -1:出錯(cuò)

?

5--- 守護(hù)進(jìn)程 

  守護(hù)進(jìn)程也就是通常所說(shuō)的Daemon進(jìn)程,他是 Linux 中的后臺(tái)服務(wù)進(jìn)程。 通常在系統(tǒng)啟動(dòng)時(shí)開(kāi)始執(zhí)行, 在系統(tǒng)關(guān)閉時(shí)終止。

  編寫(xiě)守護(hù)進(jìn)程的步驟(5步):

   (1) 創(chuàng)建子進(jìn)程,父進(jìn)程退出。

    1 if0 < pid = fork()) {2 exit(0);      /*父進(jìn)程退出*/3 }

?

   (2) 在子進(jìn)程中創(chuàng)建新會(huì)話  (兩個(gè)新的概念:進(jìn)程組、會(huì)話期)

     進(jìn)程組:一個(gè)或多個(gè)進(jìn)程的集合。有進(jìn)程組由進(jìn)程組 ID 來(lái)唯一標(biāo)識(shí)。除了進(jìn)程號(hào)(PID)之外,進(jìn)程組 ID 也是一個(gè)進(jìn)程的必備屬性。

     會(huì)話:會(huì)話是一個(gè)或多個(gè)進(jìn)程組的集合。

     pit_t setsid(void);?     成功:返回該進(jìn)程組 ID    出錯(cuò):返回 -1

     用于創(chuàng)建一個(gè)新的會(huì)話,并擔(dān)任該會(huì)話組的組長(zhǎng)。調(diào)用 setsid() 有下面三個(gè)作用。

     ① 讓進(jìn)程擺脫原會(huì)話的控制  ② 讓進(jìn)程擺脫原進(jìn)程組的控制  ③ 讓進(jìn)程擺脫原控制終端的控制

   (3) 改變當(dāng)前目錄

     通常做法是讓 “/” (根目錄)作為守護(hù)進(jìn)程的工作目錄

   (4) 重設(shè)文件權(quán)限掩碼

     umask(); 是設(shè)置文件權(quán)限掩碼的函數(shù),通常的使用方法是 umask(0);

   (5) 關(guān)閉文件描述符

    1 int num;2 num = getdtablesize(); // 獲取當(dāng)前進(jìn)程文件描述表大小3 for (i = 0; i < num; i++)4 {5 close(i);6 }

?

轉(zhuǎn)載于:https://www.cnblogs.com/chen-farsight/p/6020795.html

總結(jié)

以上是生活随笔為你收集整理的Linux多任务编程——进程的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。

如果覺(jué)得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。