Deamon有名的守护进程

#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>

#include <sys/types.h>
#include <sys/stat.h>

void deamon_mode()
{
	pid_t pid;

	//创建子进程,父进程退出
	if((pid = fork()) < 0)
	{
		perror("Fail fork");
		exit(EXIT_FAILURE);
	}

	if(pid > 0)
	{
		exit(EXIT_SUCCESS);
	}

	//创建新会话期
	if(setsid() < 0)
	{
		perror("Fail to setsid");
		exit(EXIT_FAILURE);
	}

	//改变工作目录为"/"
	chdir("/");

	//重设文件掩码
	umask(0);

	//关闭不需要的文件描述符
	close(0);
	close(1);
	close(2);

	return ;
}

//守护进程写日志

//./a.out -d 进程守护进程模式
//./a.out 非守护进程模式
int main(int argc, char * const argv[])
{
	int ch;
	int flag = 0;

	while((ch = getopt(argc,argv,"d")) != -1)
	{
		switch(ch)
		{
		case 'd':
			flag = 1;
			break;
		}
	}
	
	if(flag)
	{
		deamon_mode();
	}

	printf("hello word.\n");
	
	while(1);

	exit(EXIT_SUCCESS);
}

后台打印log

#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <errno.h>
#include <time.h>
#include <string.h>

void deamon_mode()
{
	pid_t pid;

	//创建子进程,父进程退出
	if((pid = fork()) < 0)
	{
		perror("Fail fork");
		exit(EXIT_FAILURE);
	}

	if(pid > 0)
	{
		exit(EXIT_SUCCESS);
	}

	//创建新会话期
	if(setsid() < 0)
	{
		perror("Fail to setsid");
		exit(EXIT_FAILURE);
	}

	//改变工作目录为"/"
	chdir("/");

	//重设文件掩码
	umask(0);

	//关闭不需要的文件描述符
	close(0);
	close(1);
	close(2);

	return ;
}

int get_line(FILE *fp)
{
	int line = 0;
	char buf[1024];
	
	//buf:....\n\0
	while(fgets(buf,sizeof(buf),fp) != NULL)
	{
		if(buf[strlen(buf) - 1] == '\n')
			line ++;
	}
	
	return line;
}

void do_log(char *name)
{
	FILE *fp;
	time_t tim;
	struct tm *ptm;
	int line = 0;

	if((fp = fopen(name,"a+")) == NULL)
	{
		fprintf(stderr,"Fail to fopen %s : %s.\n",name,strerror(errno));
		return;
	}

	line = get_line(fp);
	
	while(1)
	{
		tim = time(NULL);
		ptm = localtime(&tim);
		
		fprintf(fp,"%d,%d-%d-%d  %d:%d:%d.\n",++line,ptm->tm_year + 1900,ptm->tm_mon + 1,\
				ptm->tm_mday,ptm->tm_hour,ptm->tm_min,ptm->tm_sec);
		
		fflush(fp);
		sleep(1);
	}

	return ;
}

//练习:守护进程写日志

//./a.out -d 进程守护进程模式
//./a.out 非守护进程模式
//./a.out -d file
//./a.out file
int main(int argc, char * const argv[])
{
	int ch;
	int flag = 0;

	while((ch = getopt(argc,argv,"d")) != -1)
	{
		switch(ch)
		{
		case 'd':
			flag = 1;
			break;
		}
	}
	
	if(flag)
	{
		deamon_mode();
	}

	do_log(argv[optind]);
	
	exit(EXIT_SUCCESS);
}

经验证后台打印日志代码有bug,修复如下:

#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <errno.h>
#include <time.h>
#include <string.h>
#include <sys/types.h>
#include <sys/stat.h>

void deamon_mode()
{
	pid_t pid;

	//创建子进程,父进程退出
	if((pid = fork()) < 0)
	{
		perror("Fail fork");
		exit(EXIT_FAILURE);
	}

	if(pid > 0)
	{
		exit(EXIT_SUCCESS);
	}

	//创建新会话期
	if(setsid() < 0)
	{
		perror("Fail to setsid");
		exit(EXIT_FAILURE);
	}

	//改变工作目录为"/"
	chdir("/");

	//重设文件掩码
	umask(0);

	//关闭不需要的文件描述符
	close(0);
	close(1);
	close(2);

	return ;
}

int get_line(FILE *fp)
{
	int line = 0;
	char buf[1024];
	
	//buf:....\n\0
	while(fgets(buf,sizeof(buf),fp) != NULL)
	{
		if(buf[strlen(buf) - 1] == '\n')
			line ++;
	}
	
	return line;
}

void do_log(char *name, FILE *fp)
{
	time_t tim;
	struct tm *ptm;
	int line = 0;

	line = get_line(fp);
	
	while(1)
	{
		tim = time(NULL);
		ptm = localtime(&tim);
		
		fprintf(fp,"%d,%d-%d-%d  %d:%d:%d.\n",++line,ptm->tm_year + 1900,ptm->tm_mon + 1,\
				ptm->tm_mday,ptm->tm_hour,ptm->tm_min,ptm->tm_sec);
		
		fflush(fp);
		sleep(1);
	}

	return ;
}

//练习:守护进程写日志

//./a.out -d 进程守护进程模式
//./a.out 非守护进程模式
//./a.out -d file
//./a.out file
int main(int argc, char * const argv[])
{
	int ch;
	int flag = 0;

	while((ch = getopt(argc,argv,"d")) != -1)
	{
		switch(ch)
		{
		case 'd':
			flag = 1;
			break;
		}
	}
	
	FILE *fp;
	if((fp = fopen(argv[optind],"a+")) == NULL)
	{
		fprintf(stderr,"Fail to fopen %s : %s.\n",argv[optind],strerror(errno));
		return -1;
	}
	
	if(flag)
	{
		deamon_mode();
	}

	do_log(argv[optind], fp);
	
	exit(EXIT_SUCCESS);
}

部分参考

liumengyang1992 本文链接:https://blog.csdn.net/liumengyang1992/article/details/99430671

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

静思心远

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值