环境:Vmware Workstation;CentOS-6.4-x86_64
程序实现的效果:
通过管道向管道中写入一个字符串“exit”,使守护进程退出。
步骤:
1、创建管道并记录所在的完整路径:
[negivup@negivup mycode]$ mkfifo fifo
[negivup@negivup mycode]$ ls
fifo
[negivup@negivup mycode]$ pwd
/home/negivup/mycode
2、书写makefile文件:
.SUFFIXES:.c .o
CC=gcc
SRCS=main.c
OBJS=$(SRCS:.c=.o)
EXEC=main
start: $(OBJS)
$(CC) -o $(EXEC) $(OBJS)
@echo "--------------------------OK------------------------"
.c.o:
$(CC) -Wall -o $@ -c $<
clean:
rm -rf $(OBJS) $(EXEC)
3、编写源文件main.c:
#include <stdio.h>
#include <unistd.h>
#include <string.h>
#include <errno.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
int main(int argc, char *args[])
{
// 使用fork创建进程
pid_t pid = fork();
// 判断fork是否成功
if (pid == -1)
{
printf("Message : %s\n", strerror(errno));
return -1;
}
if (pid > 0)
{
// 1、父进程退出,使子进程成为孤儿进程
exit(0);
}
else
{
// 2、取消进程和任何控制终端的关联
setsid();
// 下面的一下步骤是根据自己需要选择的,即使不选择,这个进程也是守护进程
/
// 3、让根目录成为当前执行的目录
chdir("/");
// 4、设置进程的启动权限
// 不继承启动程序用户的权限
// 这样做的目的是保证这个进程能够被其他用户正常使用
umask(0);
// 5、关闭不需要的文件描述符
close(STDIN_FILENO);
close(STDOUT_FILENO);
close(STDERR_FILENO);
/
// 创建文件缓冲区
char buf[1024];
// 以只读的方式打开管道
int fd = open("/home/negivup/mycode/fifo", O_RDONLY);
// 判断管道是否打开成功
if (fd == -1)
{
printf("Message : %s\n", strerror(errno));
return -1;
}
while (1)
{
// 清空缓冲区内存
memset(buf, 0, sizeof(buf));
// 从管道中读取数据放到缓冲区中
read(fd, buf, sizeof(buf));
// 比较字符串,如果输入的是exit,那么退出循环
if (strncmp(buf, "exit", 4) == 0)
break;
}
// 关闭管道
close(fd);
}
return 0;
}
4、编译并执行程序:
[negivup@negivup mycode]$ make 编译程序
gcc -Wall -o main.o -c main.c
gcc -o main main.o
--------------------------OK------------------------
[negivup@negivup mycode]$ main 运行程序
[negivup@negivup mycode]$ ps -u negivup 查看进程信息,此时存在进程main
PID TTY TIME CMD
4887 ? 00:00:03 sshd
4888 pts/0 00:00:01 bash
17662 ? 00:00:00 main
17663 pts/0 00:00:00 ps
[negivup@negivup mycode]$ echo "exit" > fifo 向管道中写入字符串“exit”
[negivup@negivup mycode]$ ps -u negivup 查看进程信息,此时不存在进程main
PID TTY TIME CMD
4887 ? 00:00:03 sshd
4888 pts/0 00:00:01 bash
17670 pts/0 00:00:00 ps
成功实现了通过管道关闭一个守护进程。
PS:根据传智播客视频学习整理得出。