我创build了一个linux c ++服务(它基本上是一个应用程序,但它经常通过TCP / IP处理请求)。
我想知道是否有任何简单的方法让它“自动重启”,如果出现问题(如崩溃),或者如果服务器重新启动?
我不知道如何甚至是应该设置它作为服务或设置一个rc.d脚本,我不是100%熟悉w /如何在Linux上执行此操作(我的服务器正在运行ubuntu,如果它很重要)。
任何build议将不胜感激!
〜乔希
在我的产品中,我创建了看门狗进程,它在单独的进程中分叉和执行服务进程,并等待其终止。 如果出于某种原因,进程终止,看门狗进程将创建另一个线程,它将再次启动进程。
正如评论中指出的,你应该检查它为什么崩溃。 首先,您可以阅读程序退出值。
这里是简单的程序,让你开始:
#include <stdio.h> #include <unistd.h> #include <sys/wait.h> int main() { create_process(); return 0; } void create_process() { int exit_code; if(fork() == 0) { exec("./your_service"); } else { wait(&exit_code); if(WIFEXITED(exit_code)) { /* Program terminated with exit */ /* If you want, you could decode exit code here using WEXITSTATUS and you can start program again. */ return; } else ` { /* Program didn't terminated with exit, restart */ create_process(); } } }
为了在系统启动时启动服务,只需编辑/etc/rc.local
脚本并附加运行看门狗进程的命令即可。
这里有很多答案建议有一个“父应用程序”这样做,但你最终与父应用程序相同的问题 – 这是乌龟一直下降。
在许多unix类型系统中(特别是历史上),init进程是第一个执行进程的进程,它将执行(并自动重启)/ etc / inittab中定义的进程。
所以,不要写你自己的看门狗或进程来自动重启 – 你可以使用这个为你自动完成这项工作的进程,因为它是初始化进程,所以如果它死了,系统比你的服务有更多的担心。
@doron提出了另一种好方法,如果你的服务应该为每个传入的连接产生一个新的进程,并且只有当它有一个传入的连接时才能工作。
最后,现在init进程(和/ etc / inittab)已经在Ubuntu系统上被upstart – http://upstart.ubuntu.com/取代 – 这是一个更灵活的系统。
你可能想看看使用Inet守护进程 。 每次有新的请求进入时,inet守护进程都会启动一个新进程。因此,如果服务器发生崩溃,那么在下一个请求进入时它会重新启动。
在* NIX上编写一个自动重启子进程的父应用程序最简单的方法就是使用一个shell脚本:
#!/bin/sh while true; do run_my_program; done
你可以有选择地使用这个重定向输出,在后台运行,等等。这并没有解决首先启动进程的问题,但是与用C ++编写父进程相比,它的工作量更少(与结果完全相同)。