守护进程
本文,主要讲解守护进程的定义和相关的原理,并通过一个用户实例来说明如何编写守护进程。
1.守护进程的撰写条件:
1)D要在系统中处于一直运转的状态,也就是说while循环,时刻在监听服务2)D不能在关闭终端的时候退出—— 为什么终端关闭将导致进程退出呢?
3)D要脱离控制终端,登录会话和进程组—— 注销的时候,为什么有的进程将被注销,而有的不会?
2.相关原理
Q:每个进程都属于一个进程组,就是进程组长的ID。一个登录会话可以包含多个进程组,这些进程组共享一个控制终端.他们的关系可以参考下图?
Q:为什么要设计进程组id?
A:(猜想)方便对作业进行管理,可能在某些时候我们需要对一组进程而不是一个进程进行管理;例如在一个终端发送信号,那么信号对所有属于这个终端的进程组都是有效的。
Q.tip:如何查看一个进程组的进程组id?如何查看控制终端?ps和top命令的每个字段是什么意思?
ps 按照用户的要求输出所有相关的信息:ps axo stat,euid,ruid,tty,tpgid,sess,pgrp,ppid,pid,pcpu,comm
仅仅查看进程组id:ps -C sshd -o pgrp
ps -p ID -o pgrp
Q:如何得到进程的组id和设置进程的组id?
A:pid_t getpgrp() ;
int setpgid(pid_t pid, pid_t pgid) :进程可以调用这个函数来设置自己或者子进程的pgid
3.守护进程的编写步骤
守护进程的编写中,有两个主要的部分:1)脱离控制 2)清理资源守护进程编程步骤
1. 创建子进程,父进程退出
?所有工作在子进程中进行
?形式上脱离了控制终端
2. 在子进程中创建新会话
?setsid()函数
?使子进程完全独立出来,脱离控制
3. 改变当前目录为根目录
?chdir()函数
?防止占用可卸载的文件系统
?也可以换成其它路径
4. 重设文件权限掩码
?umask()函数:将某些文件权限标记为设定为0
?防止继承的文件创建屏蔽字拒绝某些权限
?增加守护进程灵活性
5. 关闭文件描述符
?继承的打开文件不会用到,浪费系统资源,无法卸载
?getdtablesize()
?返回所在进程的文件描述符表的项数,即该进程打开的文件数目
code:
#include "stdio.h" /* #include "type.h" */ #include <unistd.h> #include <fcntl.h> /* #include < sys/wait.h> */ #include <sys/types.h> #include <string.h> int main(int argc, char *argv[]) { pid_t pid; int i, fd; char *buf = "This is a deamon program"; if( (pid = fork()) < 0){ printf("fork error!"); exit(1); } else if(pid >0){ exit(0); } /* setsid(); */ chdir("/"); umask(0); for (int i = 0; i < getdtablesize(); ++i){ close(i); } while(1){ if( ( fd=open("/tmp/daemon.log", O_CREAT| O_WRONLY | O_APPEND, 0600)) < 0){ } write(fd, buf, strlen(buf)+1); close(fd); sleep(10); printf("never"); } return 0; }
郑重声明:本站内容如果来自互联网及其他传播媒体,其版权均属原媒体及文章作者所有。转载目的在于传递更多信息及用于网络分享,并不代表本站赞同其观点和对其真实性负责,也不构成任何其他建议。