C程序fork进程导致PHP执行不退出

/*********************************************************************
 *                C程序fork进程导致PHP执行不退出
 * 说明:
 *     由于测试的GPIO程序需要持续运行,而主进程需要处理其他事务但退出时
 * 由于子线程未结束导致PHP系统调用函数不退出,解决办法是双重fork(第一次
 * fork产生子进程用于kill掉让第二次fork出的子进程变成孤儿进程),并将最终
 * 的子进程转换为守护进程,从而不影响PHP获取主进程数据。
 *
 *                                   2017-8-16 深圳 龙华樟坑村 曾剑锋
 ********************************************************************/

一、参考文档:
    1. Linux 守护进程的实现
        http://alfred-sun.github.io/blog/2015/06/18/daemon-implementation/

二、测试daemon Demo:
    #include <stdio.h>
    #include <stdlib.h>
    #include <string.h>
    #include <time.h>
    #include <unistd.h>
    #include <sys/param.h>
    #include <sys/types.h>
    #include <sys/stat.h>
    #include <fcntl.h>

    // 守护进程初始化函数
    void init_daemon()
    {
        pid_t pid;
        int i = 0;

        if ((pid = fork()) == -1) {
            printf("Fork error !\n");
            exit(1);
        }
        if (pid != 0) {
            exit(0);        // 父进程退出
        }

        setsid();           // 子进程开启新会话,并成为会话首进程和组长进程
        if ((pid = fork()) == -1) {
            printf("Fork error !\n");
            exit(-1);
        }
        if (pid != 0) {
            exit(0);        // 结束第一子进程,第二子进程不再是会话首进程
        }
        chdir("/tmp");      // 改变工作目录
        umask(0);           // 重设文件掩码
        for (; i < getdtablesize(); ++i) {
           close(i);        // 关闭打开的文件描述符
        }

        return;
    }

    int main(int argc, char *argv[])
    {
        int fp;
        time_t t;
        char buf[] = {"This is a daemon:  "};
        char *datetime;
        int len = 0;
        //printf("The NOFILE is: %d\n", NOFILE);
        //printf("The tablesize is: %d\n", getdtablesize());
        //printf("The pid is: %d\n", getpid());

        // 初始化 Daemon 进程
        init_daemon();

        // 每隔一分钟记录运行状态
        while (1) {
            if (-1 == (fp = open("/tmp/daemon.log", O_CREAT|O_WRONLY|O_APPEND, 0600))) {
              printf("Open file error !\n");
              exit(1);
            }
            len = strlen(buf);
            write(fp, buf, len);
            t = time(0);
            datetime = asctime(localtime(&t));
            len = strlen(datetime);
            write(fp, datetime, len);
            close(fp);
            sleep(60);
        }

        return 0;
    }
时间: 2024-08-11 07:37:21

C程序fork进程导致PHP执行不退出的相关文章

fork进程与Threading之超时退出

将任务放置在子进程或其他线程中执行,在子进程或其他线程执行超时,则父进程或主线程程序并退出 fork进程 import os import time import signal # 信号数和stack框架 def chldhandler(signum, stackframe): """ signal handler.Runs on the parent and is called whenever a child terminates.""" w

从程序到进程

该文出自:http://www.civilnet.cn/bbs/browse.php?topicno=78426 本文以<从代码到可执行文件>为基础,阅读本文前确保你熟悉了<从代码到可执行文件>中提到的概念,本文中的示例程序仍是<从代码到可执行文件>中的gemfield.c.代码如下: **************************** int main(int argc,char *argv[]) { int a = 0; char gemfield[32];

Linux从程序到进程

Linux从程序到进程 作者:Vamei 出处:http://www.cnblogs.com/vamei 欢迎转载,也请保留这段声明.谢谢! 计算机如何执行进程呢?这是计算机运行的核心问题.即使已经编写好程序,但程序是死的.只有活的进程才能产出.我们已经从Linux进程基础中了解了进程.现在我们看一下从程序到进程的漫漫征程. 一段程序 下面是一个简单的C程序,假设该程序已经编译好,生成可执行文件vamei.exe. #include <stdio.h> int glob=0; /*global

程序的进程

接上回的接着说 #一 操作系统的作用: 1:隐藏丑陋复杂的硬件接口,提供良好的抽象接口 2:管理.调度进程,并且将多个进程对硬件的竞争变得有序 #二 多道技术: 1.产生背景:针对单核,实现并发 ps: 现在的主机一般是多核,那么每个核都会利用多道技术 有4个cpu,运行于cpu1的某个程序遇到io阻塞,会等到io结束再重新调度,会被调度到4个 cpu中的任意一个,具体由操作系统调度算法决定. 2.空间上的复用:如内存中同时有多道程序 3.时间上的复用:复用一个cpu的时间片 强调:遇到io切,

程序、进程与线程

一.程序 程序是存储在磁盘上, 包含可执行机器指令和数据的静态实体. 即进程或者任务是处于活动状态的计算机程序. 二.进程 进程就是运行中的程序. 一个运行着的程序,可能有多个进程.进程在操作系统中执行特定的任务. 1.分类:进程一般分为交互进程.批处理进程和守护进程三类.守护进程总是活跃的,一般是后台运行. 守护进程一般是由系统在开机时通过脚本自动激活启动, 或者由超级用户root来启动. 2.查看进程  :ps /  ps axu /  ps  -efl 3.获取进程号:getpid 4.创

Linux0.11内核--fork进程分析

[版权所有,转载请注明出处.出处:http://www.cnblogs.com/joey-hua/p/5597818.html ] 据说安卓应用里通过fork子进程的方式可以防止应用被杀,大概原理就是子进程被杀会向父进程发送信号什么的,就不深究了. 首先fork()函数它是一个系统调用,在sys.h中: extern int sys_fork (); // 创建进程. (kernel/system_call.s, 208) // 系统调用函数指针表.用于系统调用中断处理程序(int 0x80),

linux之多线程fork:进程通信

++++++++++++++++++信号机制+++++++++++++++++++ 接收信号 int signal(int sig,__sighandler_t handler); int func(int sig); sig 指明了所要处理的信号类型,handler是SIG_IGN,SIG_DFL或者返回值为整数的函数地址. 当执行了signal函数后,进程只要接收到类型为sig 的信号,就立即执行 func()函数,不管其正在执行程序的哪一部分.当func()函数执行结束后,程序返回到进程被

Android Init进程命令的执行和服务的启动

这里开始分析init进程中配置文件的解析,在配置文件中的命令的执行和服务的启动. 首先init是一个可执行文件,它的对应的Makfile是init/Android.mk. Android.mk定义了init程序在编译的时候,使用了哪些源码,以及生成方式.当init程序生成之后,最终会放到/init,即根目录的init文件.通常所说的init进程就是执行这个init程序. 执行这个init程序的代码是在KERNEL/init/main.c文件中的kernel_init()函数里,当kernel把一

进程管理顺序执行和并发执行

一.引言 在传统的操作系统中,程序并不能独立运行,作为资源分配和独立运行的基本单位都是进程.操作系统所具有的四大特征也都是基于进程而形成的,并可从进程的观点来研究操作系统.显然,在操作系统中,进程是一个极其重要的概念. 二.程序的顺序执行及其特征 顺序执行:通常可以把一个应用程序分成若干个程序段,在各程序段之间,必须按照某种先后次序顺序执行,仅当前一操作(程序段)执行完后,才能执行后继操作. 2. 1 程序顺序执行时的特征 (1) 顺序性:处理机的操作严格按照程序所规定的顺序执行,即每一操作必须