2023年8月2日发(作者:)
在Linux中简单实现回收⼦进程学习到wait函数了,这个函数的作⽤是⽤来回收进程。⼀般来说,正常退出的进程是不需要我们来专门回收的。但是进程有这两种:孤⼉进程和僵⼫进程。孤⼉进程:通俗点说就是⽗进程先于⼦进程死亡。此时⼦进程就成为孤⼉进程。这时候⼦进程的⽗进程就是init进程了。这个过程(⽗进程死亡后⼦进程的⽗进程变为init)称为init进程领养孤⼉进程。僵⼫进程进程终⽌,但是⽗进程并未进⾏回收操作。⼦进程的残留资源(PCB)存在于内核中,成为僵⼫进程。就是⼉⼦死了,但是⽗亲不收⼫。这⾥要注重理解的是:僵⼫进程实际上是结束的进程。所以,我们能⽤kill命令结束它么?不能!结束⼀个已经结束的进程。怎么能⾏呢?请看下列代码:#include
int main(){ int status; int i = 0; pid_t pid_1, pid_2;
for (; i != 1; i++) { pid_1 = fork(); if (!pid_1) { break; } } if (i < 1) { sleep(5); printf("I am the %d ID is %d .n", i + 1, getpid()); } else { pid_2 = wait(&status); if (-1 == pid_2) { perror("wait precess "); exit(1); } printf("Recovery of the %d process is is ID %d .n", i, pid_2); if (WIFEXITED(status)) { printf("Normal exit of process, Exit status : %d .n", WEXITSTATUS(status)); } else if (WIFSIGNALED(status)) { printf("The program exits with abnormal signal, signal value : %d.n", WTERMSIG(status)); }
printf("I am is father.n"); }
//printf("hello from Recycle_child_process!n"); return 0;}我fork了⼀个⼦进程,并让它休眠5s。注意我的wait函数是在⽗进程分⽀中调⽤的,这⾥涉及到⼏个宏函数:WIFEXITED(status) 为⾮0 → 进程正常结束WEXITSTATUS(status) 如上宏为真,使⽤此宏 → 获取进程退出状态 (exit的参数)WIFSIGNALED(status) 为⾮0 → 进程异常终⽌WTERMSIG(status) 如上宏为真,使⽤此宏 → 取得使进程终⽌的那个信号的编号。这样,程序会输出:I am the 1 ID is 6024 .Recovery of the 1 process is is ID 6024 .Normal exit of process,Exit status:0 .I am is 应该是不会⼀样的。程序显⽰该⼦进程是正常退出的,返回值为0;我们可以改动这个返回值:⽤return 语句if (i < 1){ sleep(5); printf("I am the %d ID is %d .n", i + 1, getpid()); return 1314520;}那么程序的输出就应该是:I am the 1 ID is 6024 .Recovery of the 1 process is is ID 6024 .Normal exit of process,Exit status:1314520 .I am is father.那我们怎么让⼦进程异常退出?毕竟平常也很少遇到。我们可以⼈为的营造环境,段错误知道吧?浮点异常知道吧?不知道可以百度或⾕歌。我们来编写⼀个程序:#include
编译并命名为。然后我们修改程序为:if (i < 1){ execl(" / home / lovedan / projects / Recycle_child_process / bin / x64 / Debug / ", "", NULL);//第⼀个参数⼀定是绝对路径。相信你知道execl函数 /*sleep(5); printf("I am the %d ID is %d .n", i + 1, getpid());*/}这时候,程序的输出。。。。输出结果我丢失了,也不想在去重新弄了。反正吧,他会输出⼦进程被成功回收,但是⼦进程是异常退出。提⽰浮点异常,value值是8(即:SIGFPE)。将in i=5/0;注释掉之后在编译它,重新运⾏另外⼀个程序输出结果⼜会不⼀样。会提⽰我们⼦进程因为段错误⽽退出。⼤概就这些吧,后⾯还有⼀个waitpid函数。后⾯在来介绍吧。
来更新⼀下:循环回收多个⼦进程:上⾯的⽰例是指创建回收⼀个⼦进程,若是我们创建多个,该如何回收呢?⽤循环!for (; i != 10; i++){ pid_1 = fork(); if (!pid_1) { break; }}if (i < 10){ sleep(i); printf("I am the %d ID is %d .n", i + 1, getpid());}else{ sleep(i); while (pid_2 = wait(&status) != -1)//循环回收进程 { printf("Recovery of the %d process is is ID %d .n", i, pid_2);
if (WIFEXITED(status)) { printf("Normal exit of process, Exit status : %d .n", WEXITSTATUS(status)); } else if (WIFSIGNALED(status)) { printf("The program exits with abnormal signal, signal value : %d.n", WTERMSIG(status)); }
printf("I am is father.n"); }
if (-1 == pid_2) { perror("wait precess "); exit(1); }}我就只是贴了我修改的代码。其实变动很少,就是加个循环控制⽽已,这个程序的输出是:I am the 1 ID is 1225 .I am the 2 ID is 1226 .I am the 3 ID is 1227 .I am the 4 ID is 1228 .I am the 5 ID is 1229 .I am the 6 ID is 1230 .I am the 7 ID is 1231 .I am the 8 ID is 1232 .I am the 9 ID is 1233 .I am the 10 ID is 1234 .Recovery of the 10 process is is ID 1 .Normal exit of process,Exit status:0 .I am is ry of the 10 process is is ID 1 .Normal exit of process,Exit status:0 .I am is ry of the 10 process is is ID 1 .Normal exit of process,Exit status:0 .I am is ry of the 10 process is is ID 1 .Normal exit of process,Exit status:0 .I am is ry of the 10 process is is ID 1 .Normal exit of process,Exit status:0 .I am is ry of the 10 process is is ID 1 .Normal exit of process,Exit status:0 .I am is ry of the 10 process is is ID 1 .Normal exit of process,Exit status:0 .I am is ry of the 10 process is is ID 1 .Normal exit of process,Exit status:0 .I am is ry of the 10 process is is ID 1 .Normal exit of process,Exit status:0 .I am is ry of the 10 process is is ID 1 .Normal exit of process,Exit status:0 .I am is father.有没有发现回收的ID全为1?因为⼦进程先于⽗进程结束啊,是正常的结束,返回值为0;如果想要测试异常结束,请⾃⾏营造环境。
发布者:admin,转转请注明出处:http://www.yc00.com/web/1690955001a472269.html
评论列表(0条)