linux创建进程和等待进程退出
在WIN32下,在一个进程里我们可以使用CreateProcess()创建一个进程,然后通过调用WaitForSingleObect(), WaitForMultipleObject()等待进程退出。那么在linux下该如何实现呢?
以下的代码实现了一个daemon程序, daemon程序负责系统启动其它所有App,当其它应用出现异常退出的时候,daemon程序会重新启动它们。
/********************************************************************
filename: daemon.c
created: 2013-07-17
author: firehood
purpose: daemon implement
*********************************************************************/
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/wait.h>
#include <stdio.h>
#include <stdlib.h>
#include <fcntl.h>
#include <errno.h>
#include <unistd.h>
#include <syslog.h>
#include <string.h> typedef enum APP_ID_
{
APP_ID_MIN,
APP_ID_RTMP = APP_ID_MIN,
APP_ID_VIDTRANSFILT,
APP_ID_SOS, //////////////////////
APP_ID_MAX,
}APP_ID; typedef struct APP_INFO_
{
APP_ID id; // app id
const char* app_path; // app file path
const char* cmdline; // app cmdline
int start_interval; // waitting time before starting the app. (unit:ms)
}APP_INFO; static APP_INFO APP_INFO_Array[] =
{
{APP_ID_RTMP, "/opt/exe/crtmpserver/sbin/crtmpserver", "/opt/exe/crtmpserver/etc/crtmpserver.lua" ,0},
{APP_ID_VIDTRANSFILT, "./VidTransFilt", NULL, 2000},
{APP_ID_SOS, "/opt/exe/sos", NULL, 5000},
}; pid_t APP_pid[APP_ID_MAX]; int ExecuteApp(const char *app_path,const char *argv[]);
int GetAppIdByPid(pid_t pid); int main(void)
{
/* Our process ID and Session ID */
pid_t pid, sid; /* Fork off the parent process */
pid = fork();
if (pid < 0) {
exit(EXIT_FAILURE);
}
/* If we got a good PID, then
we can exit the parent process. */
if (pid > 0) {
exit(EXIT_SUCCESS);
}
#if 0
/* Change the file mode mask */
umask(0); /* Open any logs here */ /* Create a new SID for the child process */
sid = setsid();
if (sid < 0) {
/* Log the failure */
exit(EXIT_FAILURE);
} /* Change the current working directory */
if ((chdir("/")) < 0) {
/* Log the failure */
exit(EXIT_FAILURE);
} /* Close out the standard file descriptors */
close(STDIN_FILENO);
close(STDOUT_FILENO);
close(STDERR_FILENO);
#endif /* Daemon-specific initialization goes here */
printf("Daemon is running..\n"); int nAppCount = sizeof(APP_INFO_Array)/sizeof(APP_INFO);
printf("Daemon: AppCount is [%d]\n",nAppCount); int i = 0;
for(i =0; i<nAppCount;i++)
{
usleep(APP_INFO_Array[i].start_interval*1000);
if(APP_INFO_Array[i].cmdline)
{
char* argv[3] ={0};
argv[0] = strrchr(APP_INFO_Array[i].app_path,'/')+1;
argv[1] = APP_INFO_Array[i].cmdline;
argv[2] = NULL;
APP_pid[APP_INFO_Array[i].id] = ExecuteApp(APP_INFO_Array[i].app_path,argv);
}
else
{
APP_pid[APP_INFO_Array[i].id] = ExecuteApp(APP_INFO_Array[i].app_path,NULL);
}
printf("Daemon: %s is running pid = [%d]\n",APP_INFO_Array[i].app_path,APP_pid[APP_INFO_Array[i].id]);
} int status;
while(1)
{
pid_t ret_pid = wait(&status);
if(ret_pid == -1)
{
printf("Daemon: all app are exited!\n");
break;
}
printf("Daemon: app [%d] returns\n",ret_pid);
if(!WIFEXITED(status))
{
printf("Daemon: app [%d] terminated abnormally\n",ret_pid);
}
else
{
printf("Daemon: app [%d] exited with code[%d]\n",ret_pid,WEXITSTATUS(status));
}
int app_id = GetAppIdByPid(ret_pid);
if(app_id>=0 && app_id!=APP_ID_RTMP)
{
// restart the app
APP_pid[app_id] = ExecuteApp(APP_INFO_Array[app_id].app_path,APP_INFO_Array[app_id].cmdline);
}
} exit(EXIT_SUCCESS);
} int GetAppIdByPid(pid_t pid)
{
int i = 0;
for(i = 0; i<APP_ID_MAX;i++)
{
if(pid == APP_pid[i] & i != APP_ID_RTMP)
{
return i;
}
}
return -1;
} int ExecuteApp(const char *app_path,const char *argv[])
{
if(app_path == NULL)
{
return 0;
} pid_t pid = fork(); int ret;
switch(pid)
{
case -1:
perror("fork failed");
exit(-1);
case 0 :
ret = execv(app_path,argv);
printf("start app[%s] failed, ret= [%d]\n",app_path,ret);
break;
default:
break;
} return pid;
}
linux创建进程和等待进程退出的更多相关文章
- Linux系统编程——特殊进程之僵尸进程
僵尸进程(Zombie Process) 进程已执行结束,但进程的占用的资源未被回收.这种进程称为僵尸进程. 在每一个进程退出的时候,内核释放该进程全部的资源.包含打开的文件.占用的内存等. 可是仍然 ...
- python开发进程:共享数据&进程池
一,共享数据 展望未来,基于消息传递的并发编程是大势所趋 即便是使用线程,推荐做法也是将程序设计为大量独立的线程集合 通过消息队列交换数据.这样极大地减少了对使用锁定和其他同步手段的需求, 还可以扩展 ...
- Linux系统编程之进程控制(进程创建、终止、等待及替换)
进程创建 在上一节讲解进程概念时,我们提到fork函数是从已经存在的进程中创建一个新进程.那么,系统是如何创建一个新进程的呢?这就需要我们更深入的剖析fork函数. 1.1 fork函数的返回值 调用 ...
- LINUX编程学习笔记(十四) 创建进程与 父子进程内存空间
1什么是进程:进程是一个执行中的程序 执行的程序: 代码->资源->CPU 进程有很多数据维护:进程状态/进程属性 所有进程属性采用的一个树形结构体维护 ps -a//所有进程 ps - ...
- linux进程管理之进程创建
所谓进程就是程序执行时的一个实例. 它是现代操作系统中一个很重要的抽象,我们从进程的生命周期:创建,执行,消亡来分析一下Linux上的进程管理实现. 一:前言 进程管理结构; 在内核中,每一个进程对应 ...
- Linux系统编程之--守护进程的创建和详解【转】
本文转载自:http://www.cnblogs.com/mickole/p/3188321.html 一,守护进程概述 Linux Daemon(守护进程)是运行在后台的一种特殊进程.它独立于控制终 ...
- linux系统编程:守护进程详解及创建,daemon()使用
一,守护进程概述 Linux Daemon(守护进程)是运行在后台的一种特殊进程.它独立于控制终端并且周期性地执行某种任务或等待处理某些发生的事件.它不需要用户输入就能运行而且提供某种服务,不是对整个 ...
- Linux之进程的等待与其内核实现解析
进程通过fork产生子进程,进程也会死亡,进程退出的时候将会进行内核清理,释放所有进程的资源,资源包括:内存资源,文件资源,信号量资源,共享内存资源,或者引用计数减一,或者彻底释放. 不过进程 ...
- linux进程管理之进程创建(三)
在linux系统中,许多进程在诞生之初都与其父进程共同用一个存储空间.但是子进程又可以建立自己的存储空间,并与父进程“分道扬镳”,成为与父进程一样真正意义上的进程. linux系统运行的第一个进程是在 ...
随机推荐
- 【C++】智能指针auto_ptr简单的实现
//[C++]智能指针auto_ptr简单的实现 #include <iostream> using namespace std; template <class _Ty> c ...
- Java设计模式(七)策略模式 模板模式
(十三)策略模式 策略图案限定了多个封装算法,该算法可以相互替换包.法的客户.借用还有一位大神的样例. interface ICalculator{ public int calculate(Stri ...
- hdu1297 Children’s Queue
再加上男人:dp[i-1]: 加2一个女人:dp[i-2]+x. 上述的另一种情况下dp[i-2]它不仅包括加2女人对法律状况.和x是一个加号ff原违法的法律案后加入,这最后是mf案例,然后,x=dp ...
- javascript中数组常用方法总结
原文:javascript中数组常用方法总结 在javascript的基础编程中,数组是我们最常遇到的,那么数组的一些常用方法也是我们必须要掌握的,下面我们总结一下数组中常用的方法. toString ...
- 基于ip san的iscsi操作执行过程
SAN它是storage area network(存储区域网络)速记,早期san光纤通道技术被用于.当迟到iscsi协议后出现,为了在这两者之间区分.它分IP SAN和FC SAN.FC SAN由于 ...
- 速度 Github
首先需要了解.git 是版本号的管理工具,为了能够把任意代码托管执照:github 其中一个是. 应用 github 什么不该说的帐户. 那么,申请后,在需求 github 并建立了独特的本地机器上的 ...
- 网上收集的WebBrowser的Cookie操作
原文:网上收集的WebBrowser的Cookie操作 1.WebBrowser设置Cookie Code highlighting produced by Actipro CodeHighlight ...
- 小记NodeJS两项小技巧(与HTTP相关)
1,兼容HTTP1.1和HTTP1.0 区别在content-length,1.0接受定长,不接受变长,导致transfer-encodeing的chunked模式无法识别,最终导致无法识别BODY. ...
- SQL表连接
背景 在上次的自考科目<数据库系统原理>中.已经接触到了关于数据库表连接的一些知识,近期的学习过程中又用到了关于数据库表的连接问题,趁此再跟大家一起回想一下. 导图总结 首先用一张思维导图 ...
- UiAutomator源码分析之UiAutomatorBridge框架
上一篇文章<UIAutomator源码分析之启动和运行>我们描述了uitautomator从命令行运行到加载测试用例运行测试的整个流程,过程中我们也描述了UiAutomatorBridge ...