1、
僵尸进程和孤儿进程。
进程消亡pcb块未释放称僵尸状态,父进程消亡,子进程悬空为孤儿状态。
exit()库函数:进程退出,刷新缓冲区,参数1错误退出,0正常退出。文件关闭,堆空间释放,缓冲区清理。
_exti 系统调用,只退出进程。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 | #include <stdio.h> #include <stdlib.h> int main(int argc, char **argv) { printf("hello"); exit(1);// 全面回收工作。文件关闭,堆释放。,缓冲区清理 printf("aaaaaaaaaaa"); //system("pause"); return 0; } |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 | #include <stdio.h> #include <stdlib.h> #include <unistd.h> int main(int argc, char **argv) { printf("hello"); _exit(1);// 关闭打开的文件 printf("aaaaaaaaaaa"); //system("pause"); return 0; } |
回调函数:作为另一个函数参数传递的函数,作用:解耦合。
int atexit(void(*func)(void))。注册清理函数,只能调用exit(1)退出。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 | #include <stdio.h> #include <stdlib.h> #include <string.h> #include <unistd.h> char* p; void clean(void) { printf("this clean fun, %s\n", p); free(p); } int main() { p = malloc(50); atexit(clean); strcpy(p, "aaa"); printf("befor exit\n"); exit(1); //如果有注册有清理函数,只能调用exit, } |
进程回收:pid_t wait(int *status);
阻塞状态等待子进程结束,并回收该进程的状态,一般用于父进程收回子进程状态。
1 2 3
5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 | #include <stdio.h> #include <string.h> #include <sys/types.h> #include <sys/wait.h> #include <unistd.h> int main(int argc, char **argv) { pid_t pid = fork(); if (pid > 0) { printf("father %d\n", getpid()); pid_t ret = wait(NULL);//阻塞 block printf("pid :%d ret %d\n",pid,ret); } else if (0 == pid) { int i = 3; while (i--) { printf("pid:%d child\n", getpid()); sleep(1); } } else { perror("fork"); return 1; } //system("pause"); return 0; } |
pcb里的退出状态:man wait查看wstatus,正常结束传exit的值,随意写,被信号关闭,传信号值,64个信号。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 | #include <stdio.h> #include <string.h> #include <sys/types.h> #include <sys/wait.h> #include <unistd.h> #include <stdlib.h> int main(int argc, char **argv) { pid_t pid = fork(); if (pid > 0) { printf("father %d\n", getpid()); int status; pid_t ret = wait(&status);//阻塞 block if(WIFEXITED(status)) //子进程正常结束 { printf("child terminal normally, exit value %d\n ",WEXITSTATUS(status)); } else if(WIFSIGNALED(status)) //异常结束 { printf("child terminal by signal , signal value %d\n ",WTERMSIG(status)); } printf("pid :%d ret %d\n",pid,ret); } else if (0 == pid) { int i = 10; while (i--) { printf("pid:%d child\n", getpid()); sleep(1); } exit(20); } else { perror("fork"); return 1; } //system("pause"); return 0; } |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 | #include <stdio.h> #include <stdlib.h> #include <string.h> #include <sys/types.h> #include <sys/wait.h> #include <unistd.h> int main(int argc, char **argv) { pid_t pid = fork(); if (pid > 0) { printf("father %d\n", getpid()); int status; while (1) { pid_t ret = waitpid(pid, &status, WNOHANG); //阻塞 block if (ret == pid) //回收成功 { if (WIFEXITED(status)) //子进程正常结束 { printf("child terminal normally, exit value %d\n ", WEXITSTATUS(status)); } else if (WIFSIGNALED(status)) //异常结束 { printf("child terminal by signal , signal value %d\n ", WTERMSIG(status)); } printf("pid :%d ret %d\n", pid, ret); break; } else if (0 == ret) { printf("回收失败,稍后在试\n"); } else // ret == - 1 { printf("回收错误\n"); return 1; } } } else if (0 == pid) { int i = 10; while (i--) { printf("pid:%d child\n", getpid()); sleep(1); } exit(20); } else { perror("fork"); return 1; } // system("pause"); return 0; } |
execute执行外部可执行程序,当执行后原代码被可执行程序替换,当执行完后程序就结束了。
excel(路径,参数,,NULL)
execlp(程序名,参数,,NULL)
execv
whereis 命令 查看系统程序是否装上
echo $PATH
echo $PATH 是 Shell 命令,用于显示当前用户的 PATH 环境变量,即系统在哪些目录中查找可执行程序。
env 获取系统环境变量
sentinel哨兵
system(const char *command); fork +exec
写一个程序,选几走几。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 | #include <stdio.h> #include <unistd.h> // ls -l -a --color=auto int main(int argc, char **argv) { //execl("/bin/ls","ls","-l","-a", "--color=auto",NULL); //list // firefox www.baidu.com //execl("/usr/bin/firefox","firefox","www.baidu.com",NULL); //echo $PATH //execlp("ls","ls","-l","-a", "--color=auto",NULL); // list path //execlp("cat","cat","./01fork.c",NULL); //execl("b.out","b.out",NULL); //execlp("./b.out","b.out",NULL); char *args[]={"ls","-l","-a", "--color=auto",NULL}; //execv("/bin/ls",args); //vector execvp(args[0],args); printf("看见就错了"); //system("pause"); return 0; } |