【C语言】【unix c】进程资源的回收

来源:互联网 发布:代言宝无水印版源码 编辑:程序博客网 时间:2024/06/05 19:43
四、进程资源的回收    1、进程结束后还会有残留的资源空间,所以需要清理    2、进程终止的时候会向父进程发送SIGCHLD信号,父进程收到这个信号后,会调用wait2)家族的函数,去回收子进程的资源    3、在父进程还没有回收子进程的资源的时候,这时候,子进程处于僵尸状态,这时候的子进程为僵尸进程    举例:僵尸进程 (zomble.c)        #include <stdio.h>        #include <unistd.h>        #include <sys/types.h>        int main() {            pid_t pid;            pid = fork();            if(pid == -1) {            perror("fork");            return -1;            }            if(pid == 0) {            printf("pid:%d\n", getpid());            }            else {            sleep(10);            }            return 0;        }    命令: tarena@ubuntu:~/day/day30$ a.out     结果: pid:4363    命令: tarena@ubuntu:~/day/day29$ ps -aux    结果: tarena    4363  0.0  0.0      0     0 pts/0    Z+(这个表示僵尸)   15:11   0:00 [a.out] <defunct>    10s后        结果: tarena@ubuntu:~/day/day30$    命令: tarena@ubuntu:~/day/day29$ ps -aux    结果: 没有了,被清理了    wait(2)        #include <sys/types.h>        #include <sys/wait.h>        pid_t wait(int *status);             功能:等待进程状态的改变(也就是终止)            参数:status:如果不为空,存储子进程的信息,这个整数可以使用宏来监测                WIFEXITED(status):如果子进程正常终止,返回ture                WEXITSTATUS(status):返回子进程的退出状态码,只有上边的宏返回真的时候,被使用                WIFSIGNALED(status):如果子进程被信号终止,返回ture                WTERMSIG(status):这个宏只有在上面的宏为真的情况下使用,返回的是使子进程终止的信号编号            返回值:返回终止的子进程的pid                返回 -1 错误            举例:使用wait回收子进程的资源(wait.c)            进程正常终止:                #include <stdio.h>                #include <sys/types.h>                #include <sys/wait.h>                #include <unistd.h>                #include <stdlib.h>                int main(void) {                    //创建子进程                    pid_t pid = fork();                    int s;                    if(pid == -1) {                    perror("fork");                    return -1;                    }                    if(pid == 0) {                    printf("child...%d\n",getpid());                    sleep(5);                    getchar();                    exit(1);                    }                    else {                    //阻塞等待子进程结束                    wait(&s);                    printf("prant...\n");                    //监测子进程是否正常终止,如果正常终止,返回子进程状态码                    if(WIFEXITED(s)) {                        printf("exit code...%d\n",WEXITSTATUS(s));                    }                    }                    return 0;                }                tarena@ubuntu:~/day/day29$ a.out                 child...                (等待5S)                prant...            用信号来终止:                             #include <stdio.h>                #include <sys/types.h>                #include <sys/wait.h>                #include <unistd.h>                #include <stdlib.h>                int main(void) {                    //创建子进程                    pid_t pid = fork();                    int s;                    if(pid == -1) {                    perror("fork");                    return -1;                    }                    if(pid == 0) {                    printf("child...%d\n",getpid());                    getchar();                    exit(1);                    }                    else {                    //阻塞等待子进程结束                    wait(&s);                    printf("prant...\n");                    //监测子进程是否被信号终止                    if(WIFSIGNALED(s)) {                        printf("signum...%d\n", WTERMSIG(s));                    }                    }                    return 0;                }            终端1:    tarena@ubuntu:~/day/day29$ a.out                 child...4638            终端2:    tarena@ubuntu:~/day/day30$ kill -9 4638            终端1:    prant...                signum...9    waitpid(2)        pid_t waitpid(pid_t pid, int *status, int options);            功能:等待指定进程状态的改变(也就是终止)            参数:                pid:指定了要等待的子进程的pid,默认的话只等待                    <-1:等待任意子进程,子进程的组id等于pid的绝对值                    -1:等待任意子进程的终止                     0:等待任意子进程,这些子进程的组id等于当前进程组id                    >0:pid指定了要等待的子进程pid                status:如果不为空,存储子进程的信息,这个整数可以使用宏来监测                    WIFEXITED(status):如果子进程正常终止,返回ture                    WEXITSTATUS(status):返回子进程的退出状态码,只有上边的宏返回真的时候,被使用                    WIFSIGNALED(status):如果子进程被信号终止,返回ture                    WTERMSIG(status):这个宏只有在上面的宏为真的情况下使用,返回的是使子进程终止的信号编号                options:可以改变是否等待子进程的终止                    WNOHANG:如果没有子进程退出,立即返回                    0:如果没有子进程退出,阻塞等待子进程的退出            返回值:成功 返回子进程的pid                错误 返回-1                如果WNOHANG被指定 返回0 代表等待的所有子进程都没有终止            waitpid(-1, &status, 0); == wait(&status)                #include <stdio.h>                #include <sys/types.h>                #include <sys/wait.h>                #include <unistd.h>                #include <stdlib.h>                int main(void) {                    //创建子进程                    pid_t pid = fork();                    int s;                    if(pid == -1) {                    perror("fork");                    return -1;                    }                    if(pid == 0) { //子进程                    printf("child...%d\n",getpid());                    //sleep(5);                    getchar();                    exit(1);                    }                    else {                    //阻塞等待子进程结束                    //wait(&s);                    //如果没有子进程退出,非阻塞                    int w = waitpid(-1, &s, WNOHANG);                        if(w > 0) {                        printf("prant...\n");                        //监测子进程是否正常终止,如果正常终止,返回子进程状态码                        if(WIFEXITED(s)) {                            printf("exit code...%d\n",WEXITSTATUS(s));                        }                        //监测子进程是否被信号终止                        if(WIFSIGNALED(s)) {                            printf("signum...%d\n", WTERMSIG(s));                        }                        }                    }                    return 0;                }            命令: tarena@ubuntu:~/day/day29$ a.out             结果: child...5231            分析:父进程在执行的时候不论子进程结束没有都不会阻塞,在没有进程结束时,父进程不会输出任何东西,当有进程结束时会打印结束号补充:     如何给进程发送信号,终止进程:        kill -信号编号(239) pid    进程组中有1个或多个进程,一般情况下子进程和父进程属于同进程组
原创粉丝点击