Unix環境高階程式設計 程序控制 二

2021-07-10 12:09:24 字數 3664 閱讀 6713

一、函式wait

和waitpid

今天我們繼續通過昨天那個死爹死兒子的故事來講(

便於記憶

),現在看看

wait

和waitpid

函式。

#include

pid_t wait(int *statloc); 

pid_t waitpid(pid_t pid , int *statloc , int options);  若成功,返回程序

id,若出錯,返回0或

-1 wait系列函式的作用就是通知父親兒子的死訊的,父程序一般接收到

sigchld

訊號而呼叫

wait

,(等待終止),可能有三種情況發生:

(1).子程序都在

running

,則阻塞

(2).如果乙個子程序終止,則父程序獲取其終止狀態

(statloc

指標指向的空間

),然後立即返回

(3).如果它沒有任何子程序,則立即出錯返回

wait可以返回的四個終止狀態的互斥的巨集,分別為:

wifexited(status)               正常終止

wifsignaled(status)             異常終止

wifstopped(status)              暫停子程序

wifcontinued(status)           暫停後已經繼續的子程序

例子:

#include "apue.h"

#include void pr_exit(int status)

intmain(void)

waitpid函式,顧名思義,其作用就在於可以等待特定的

pid的子程序終止。此外,

waitpid

的options

引數提供了

wnohang

(相當於不阻塞的

wait

)、wcontinued

、wuntraced(

支援作業控制

)三個常量選項。

下面是乙個非常經典的fork

子、孫程序的示例:(兩次fork,有效的避免僵死程序)

#include "apue.h"

#include int

main(void)

else if (pid == 0)

if (waitpid(pid, null, 0) != pid) /* wait for first child */

err_sys("waitpid error");

/** we're the parent (the original process); we continue executing,

* knowing that we're not the parent of the second child.

*/sleep(30);

exit(0);

}

為了便於測試效果明顯,我將父程序sleep了30秒,然後退出,將孫程序sleep了60秒,然後退出。在這段**中,最先退出的是子程序,為了防止孫程序僵死,我們讓它sleep的時間更長,而父程序執行完畢退出後,孫程序被init程序收養,孫程序執行自己的任務,執行完畢後正常退出,使得該過程有效的避免了僵死程序。

此外,waitid

類似於waitpid

,但更為靈活,

wait3

、wait4

的附加引數可以返回所有子程序使用的資源概況,不在此詳細說明。

二、函式exec

當我們fork

乙個程序後,新的程序往往要呼叫

exec

執行乙個啟動例程,如第七章所述圖:

因此,呼叫exec

並不建立新的程序,只是用磁碟上的乙個新程式替換了當前程序的正文段、資料段、堆段、棧段。

7個不同的

exec

函式:

#include 

int execl(const char *pathname, const char *arg0, ... /* (char *)0 */ );

int execv(const char *pathname, char *const argv);

int execle(const char *pathname, const char *arg0, ... /* (char *)0, char *const envp */ );

int execve(const char *pathname, char *const argv, char *const envp);

int execlp(const char *filename, const char *arg0, ... /* (char *)0 */ );

int execvp(const char *filename, char *const argv);

int fexecve(int fd, char *const argv, char *const envp);

返回值:成功不返回,出錯返回-1

七個exec

函式的區別:

(1).前四個取路徑名作為引數,後兩個取檔名作為引數,最後乙個以

fd作為引數

(2).參數列的傳遞不同(

l表示列表

list,v

表示向量

vector

)包含l

和包含v

(3).向新程式傳遞環境表不同。包含

e和不含e

七個exec

直接的關係如下圖,只有

execve

是核心的系統呼叫,另外

6個只是庫函式,它們最終都要呼叫該

execve

系統呼叫。

exec函式使用例程:

#include "apue.h"

#include char *env_init = ;

intmain(void)

else if (pid == 0)

if (waitpid(pid, null, 0) < 0)

err_sys("wait error");

if ((pid = fork()) < 0) else if (pid == 0)

exit(0);

}

echoall.c檔案**如下:

#include "apue.h"

intmain(int argc, char *argv)

這裡同樣是為了測試,我們sleep了100秒,模擬子程序的工作時間。

注意,需要預先把echoall.c

檔案程式設計,

gcc echoall.c -o echoall 

,否則,當我們

exec

找到該檔案後無法執行。這樣,我們就完成了啟動子程序的一整個流程

unix環境高階程式設計 程序環境與程序控制

a 終止 i.程序終止 1.正常終止 return exit exit 系a exit與 exit 的區別 exit退出時按 atexit 註冊的相反順序呼叫註冊過的函式,對開啟的流呼叫 fclose 將緩衝區的資料寫到檔案上 重新整理緩衝區 exit 沒有 b exit與自然返回 return 的...

《unix高階環境程式設計》程序控制 程序ID

在unix系統中,每個程序都有乙個非負整型表示的唯一程序id。當乙個程序終止時,程序id可以重新被其他程序使用,為了防止誤判,unix系統實現延遲重用演算法,即新建的程序id不同於最近終止程序所使用的id。程序id為0的是排程程序,也稱為交換程序,是核心的一部分,不執行磁碟上的程式,因此也稱為系統程...

《unix高階環境程式設計》程序控制 程序時間

程序時間有牆上時鐘時間 使用者cpu時間和系統cpu時間。任一程序都可以呼叫 times 函式以獲得它自己以及終止子程序的上述值。cpp view plain copy 程序時間 返回值 若成功則返回流逝的牆上時鐘時間 單位 時鐘滴答數 若出錯則返回 1 函式原型 include clock t t...