Linux 守护进程

守护进程(Daemon)是Linux系统中的后台服务进程,它们独立于控制终端,常用于提供持续服务,如FTP、NFS等。创建守护进程涉及setsid函数,用于创建新会话并脱离控制终端。在创建过程中,需要改变工作目录、重设文件权限掩码、关闭不必要的文件描述符。本文还提供了一个简单的守护进程创建示例代码,包括创建子进程、调用setsid、改变目录、重设umask、关闭文件描述符等步骤。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

什么是守护进程

Daemon(精灵)进程,是Linux中后台服务进程,通常独立于控制终端并且周期性地执行某种任务货等待处理某些发生的事件。一般采用d结尾的名字。

Linux后台的一些系统服务进程,没有控制终端,不能直接和用户交互。不受用户登录、注销的影响,一直在运行着,他们都是守护进程。如:预读入缓输出机制的实现;ftp服务器;nfs服务器等

创建守护进程,最关键的一步是调用setsid函数创建一个新的Session,并成为Session Leader。

相关函数

setsid 函数

创建一个会话,并以自己的ID设置进程组ID,同时也是新会话的ID。pid_t setsid(void);成功:返回调用进程的会话ID;失败:-1,设置errno,

调用setsid函数的进程,既是新的会长,也是新的组长

getsid 函数

获取进程所属的会话 ID;  pid_t getsid(pid_t pid); 成功:返回调用进程的会话 ID;失败:-1,设置 errno

pid 为 0 表示察看当前进程 session ID

ps ajx 命令查看系统中的进程。参数 a 表示不仅列当前用户的进程,也列出所有其他用户的进程,参数 x 表示不仅列有控制终端的进程,也列出所有无控制终端的进程,参数 j 表示列出与作业控制相关的信息。

组长进程不能成为新会话首进程,新会话首进程必定会成为组长进程。

创建会话
创建一个会话需要注意以下 6 点注意事项:
1. 调用进程不能是进程组组长,该进程变成新会话首进程(session header)
2. 该进程成为一个新进程组的组长进程。
3. 需有 root 权限 (ubuntu 不需要)
4. 新会话丢弃原有的控制终端,该会话没有控制终端
5. 该调用进程是组长进程,则出错返回
6. 建立新会话时,先调用 fork, 父进程终止,子进程调用 setsid()

创建守护进程模型

1. 创建子进程,父进程退出
  所有工作在子进程中进行形式上脱离了控制终端
2. 在子进程中创建新会话
  setsid()函数
  使子进程完全独立出来,脱离控制
3. 改变当前目录位置
  chdir()函数
  防止占用可卸载的文件系统
  也可以换成其它路径
4. 重设文件权限掩码
  umask()函数
  防止继承的文件创建屏蔽字拒绝某些权限
  增加守护进程灵活性
5. 关闭文件描述符
  继承的打开文件不会用到,浪费系统资源,无法卸载
6. 开始执行守护进程核心工作守护进程退出处理程序模型

#include<stdio.h>
#include<sys/stat.h>
#include<fcntl.h>
#include<stdlib.h>
#include<string.h>
#include<unistd.h>
#include<errno.h>
#include<pthread.h>

void sys_err(const char *str) {
    perror(str);
    exit(1);
}

int main(int argc,char *argv[])
{
    pid_t pid;
    int ret,fd;

    //Step1:创建子进程,父进程终止
    pid=fork();
    if (pid>0) exit(0);

    //Step2:子进程中创建新会话
    pid=setsid();
    if (pid==-1)
        sys_err("setsid error");

    //Step3:改变当前目录位置,防止目录在可卸载的文件内
    ret=chdir("./");
    if (ret==-1)
        sys_err("chdir error");

    //Step4:重设文件权限掩码umask,防止权限被拒绝
    umask(0023);

    //Step5:
    //关闭文件描述符0,没有标准输入
    //重定向 标准输出和错误输出 到指定文件
    close(STDIN_FILENO);
    fd=open("/dev/null",O_RDWR);        //此时fd应为0,因为open寻找最小的文件描述符
    if (fd==-1)
        sys_err("open error");
    dup2(fd,STDOUT_FILENO);
    dup2(fd,STDERR_FILENO);

    //Step6:守护进程逻辑
    while(1);

    return 0;
}

 

 

 

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值