1尝胆、fork()系統(tǒng)調(diào)用:創(chuàng)建新的進程。
#include <stdio.h>
#include<stdilib.h>
#include<unistd.h>
int main(int args,char*argv[]){
? ? printf("hello world(pid:%d)\n",(int)getpid());
? ? int rc = fork();
? ? if(rc < 0){
? ????? fprintf(stderr,"fork failed\n");
? ????? exit(1);
? ? ?} else if(rc == 0){
? ? ? ? ?printf("hello, I am child(pid:%d)\n",(int)getpid());??
? ? ?}else{
? ? ? ? printf("hello, I am mother of %d(pid:%d)\n",rc (int)getpid());
? ? ?}
? ? return 0;
????}
2个盆、wait()系統(tǒng)調(diào)用:用于父進程等待子進程執(zhí)行完畢
#include<stdilib.h>
#include<unistd.h>
int main(int args,char*argv[]){
printf("hello world(pid:%d)\n",(int)getpid());
? ? int rc = fork();
? ? if(rc < 0){
fprintf(stderr,"fork failed\n");
exit(1);
? ? ?} else if(rc == 0){
? ? ? ? ?printf("hello, I am child(pid:%d)\n",(int)getpid());??
? ? ?}else{
? ? ? ? ? ? int wc = wait(NULL);
????????????printf("hello, I am mother of %d(wc:%d)(pid:%d)\n",rc (int)getpid());
? ? ?}
return 0;
????}
3、exec()系統(tǒng)調(diào)用:讓子進程執(zhí)行與父進程不同的程序
prompt> ./p3
hello world (pid:29383)
hello, I am child (pid:29384)
? ? ? 29? ? 107? 1030 p3.c
hello, I am parent of 29384 (wc:29384) (pid:29383)
prompt>
? ? #include <stdio.h>
? ? #include <stdlib.h>
? ? #include <unistd.h>
? ? #include <string.h>
? ? #include <sys/wait.h>
? ?int main(int argc, char *argv[]){
????? ?printf("hello world (pid:%d)\n", (int) getpid());
????? ?int rc = fork();
? ?????if (rc < 0) {? ? ? ? // fork failed; exit
? ? ? ? ? ? ? fprintf(stderr, "fork failed\n");
????????????? ?exit(1);
????????????} else if (rc == 0) { // child (new process)
? ? ? ? ? ? ? ?printf("hello, I am child (pid:%d)\n", (int) getpid());
????? ? ? ? ? ?char *myargs[3];
????????? ? ? ? myargs[0] = strdup("wc");? // program: "wc" (word count)
? ? ? ? ? ? ? ? ?myargs[1] = strdup("p3.c"); // argument: file to count
? ? ? ? ? ? ? ? ?myargs[2] = NULL;? ? ? ? ? // marks end of array
?????????????????execvp(myargs[0], myargs); // runs word count
? ? ? ? ? ? ? ? ?printf("this shouldn't print out");
?????????????} else {? ? // parent goes down this path (main)
????????????? ? ? int wc = wait(NULL);
? ? ? ? ? ? ? ? ? ?printf("hello, I am parent of %d (wc:%d) (pid:%d)\n",
? ? ? ? ? ? ? ? ? ?rc, wc, (int) getpid());
? ? ? ? ? ? }
? ? ????? ?return 0;
????}
????給定可執(zhí)行程序的名稱(如wc)及需要的參數(shù)后,exec()會從可執(zhí)行程序中加載代碼和靜態(tài)數(shù)據(jù)怜森,并用它覆寫自己的代碼段(以及靜態(tài)數(shù)據(jù))殿雪,堆暇咆、棧及其他內(nèi)存空間也會被重新初始化。然后操作系統(tǒng)就執(zhí)行該程序冠摄,將參數(shù)通過argv傳遞給該進程糯崎。它并沒有創(chuàng)建新進程,而是直接將當(dāng)前運行的程序替換為不同的運行程序(wc)河泳。
4沃呢、shell
????shell是一個用戶成簇,它首先顯示一個提示符(prompt),然后等待用戶輸入拆挥。用戶輸入一個可執(zhí)行程序的名稱以及需要的參數(shù)后薄霜,shell可以在文件系統(tǒng)中找到這個可執(zhí)行程序某抓,調(diào)用fork()創(chuàng)建新的進程,并調(diào)用exec()的某個變體來執(zhí)行這個可執(zhí)行程序惰瓜,調(diào)用wait()等待該命令完成否副,子進程結(jié)束后,shell從wait()返回并再次輸出一個提示符崎坊,等待用戶輸入嚇一跳命令备禀。
????prompt> wc p3.c > newfile.txt
????wc的輸出結(jié)果被重定向(redirect)到文件newfile.txt中(通過newfile.txt之前的大于號來指明重定向)。shell實現(xiàn)結(jié)果重定向的方式也很簡單奈揍,當(dāng)完成子進程的創(chuàng)建后曲尸,shell在調(diào)用exec()之前先關(guān)閉了標(biāo)準(zhǔn)輸出(standard output),打開了文件newfile.txt男翰。這樣另患,即將運行的程序wc的輸出結(jié)果就被發(fā)送到該文件,而不是打印在屏幕上蛾绎。
prompt> ./p4
prompt> cat p4.output
? ? ? 32? ? 109? ? 846 p4.c
prompt>
#include<stdio.h>
#include<stdlib.h>
#include<unistd.h>
#include<string.h>
#include<fcntl.h>
#include<sys/wait.h>
int main(int argc,char *argv[]){
? ? int rc = fork();
? ? if(rc<0){
? ? ? ? fprintf(stderr,"fork failed\n");
? ? ? ? exit(1);
? ? ?}else if(rc == 0){
? ? ? ? close(STDOUT_FILENO);
? ? ? ? open("./p4.output",O_CEREAT|O_WEONLY|O_TRUNC,S_IRWXU);
? ? ? ? char *myargs[3];
? ? ? ? myargs[0]=strdup("wc");
? ? ? ? myargs[1]=strdup("p4.c");
? ? ? ? myargs[2]=NULL;
? ? ? ? execvp(myargs[0],myargs);
? ? }else{
? ? int wc = wait(NULL);
????}
? ? return 0;
}
5昆箕、pipe()系統(tǒng)調(diào)用
? ? ? ? 一個進程的輸出被鏈接到了一個內(nèi)核管道(pipe)上(隊列),另一個進程的輸入也被連接到了同一個管道上租冠。前一個進程的輸出無縫地作為后一個進程的輸入鹏倘,許多命令可以用這種方式串聯(lián)在一起,共同完成某項任務(wù)肺稀。
grep -o foo file|wc -l? 將grep第股、wc命令用管道連接可以完成從一個文件中查找某個詞,并統(tǒng)計其出現(xiàn)次數(shù)的功能