如何在Linux上使用信号处理强制重启应用程序崩溃/挂起?

时间:2012-09-24 16:30:25

标签: c embedded-linux

我有一个在C上运行的应用程序在Linux设备服务器上运行。如果应用程序崩溃或挂起,我希望系统重新启动。设备服务器附带了一个示例应用程序,我认为它实现了这个功能,但我不确定。通过从中获取似乎实现此功能的内容,我有以下框架:

int terminate=0;

int main () {

  struct sigaction     sigact;

  sigact.sa_handler = sighandler;
  sigemptyset(&sigact.sa_mask);
  sigact.sa_flags = 0;
  sigaction(SIGTERM,&sigact,0); 

  while (terminate == 0) 
  {
    // my main application functions
  }

  SDK_reboot();  // reboots my device server

}

void sighandler(int sig)
{
  if (sig == SIGTERM)
    terminate = 1;
}

我基本上想要了解上述代码中发生了什么,并在必要时更改它以满足我的需求。是'sigaction(SIGTERM,& sigact,0);'导致SIGTERM被引发以响应我的应用程序挂起或崩溃的行?如果不是,那么正确的代码是什么?另外,上面一般来说,是一种在应用程序崩溃/挂起时实现重启的好方法吗?还是我偏离轨道?非常感谢提前。

2 个答案:

答案 0 :(得分:0)

不,不是SIGTERM,而是SIGCHLD。换句话说,当main的一个分叉子进程退出时,循环终止。

这看起来像应用程序的一部分,它会分叉实际的“工作进程”并在它退出时重新启动。注意:挂起不会退出。这不会检测到无限循环或其他挂起。

答案 1 :(得分:0)

重启电路板最可靠的方法是使用硬件看门狗定时器。 此解决方案将有效地检测应用程序崩溃和挂起。

嵌入式linux内核通常包含看门狗驱动程序(/ dev / watchdog)。在启用了看门狗支持的情况下重建内核。

在应用程序内部打开/ dev / watchdog,并经常写入它以防止内核重置,至少每分钟一次。每次写入都会延迟重启时间。一段时间不活动后,看门狗硬件将导致复位。 (见http://linux.die.net/man/8/watchdog

参考你的代码,你可以在应用程序启动后立即打开/ dev / watchog,然后在while循环中写入它。如果应用程序只有一个线程,则会出现这种情况。如果有更多线程,你需要提出一些更棘手的东西。

还有一种方法可以检测应用程序崩溃。主要思想与解决方案相同:https://superuser.com/questions/223449/auto-restart-process-on-crash。该脚本可以用C重写。它涉及使用fork(),execve()waitpid()。