【发布时间】:2013-07-30 07:19:41
【问题描述】:
我有一个程序可以创建许多线程并运行直到嵌入式计算机关闭电源,或者用户使用 kill 或 ctrlc 来终止过程。
这是一些代码以及 main() 的外观。
static int terminate = 0; // does this need to be volatile?
static void sighandler(int signum) { terminate = 1; }
int main() {
signal(SIGINT, sighandler);
// ...
// create objects, spawn threads + allocate dynamic memory
// ...
while (!terminate) sleep(2);
// ...
// clean up memory, close threads, etc.
// ...
signal(SIGINT, SIG_DFL); // is this necessary?
}
我想知道一些事情:
是否需要任何信号处理?
我在这个线程"Linux C catching kill signal for graceful termination" 中读到,显然操作系统将为我处理清理工作。 因此,我可以只用一个无限循环替换信号处理程序,让操作系统优雅地退出线程、取消分配内存等吗?关于干净终止,我是否需要关注其他任何信号?这个线程"How does SIGINT relate to the other termination signals?",对于列出我可能关心的所有信号很有用,但实际需要处理的信号有多少?
我的示例中的终止变量是否必须是可变的?我见过很多例子,这个变量是 volatile 的,还有一些不是。
我了解到
signal()现在已弃用,可以使用sigaction()。有没有很好的例子来展示如何从之前的signal()调用转换?我对必须创建/传递的新结构以及它们如何组合在一起遇到了问题。是否需要第二次致电
signal()?
对于sigaction(),我需要关注类似的事情吗?
明确地说,我要完成的所有工作就是让我的主循环运行,直到 ctrlc 或电源断开或发生非常糟糕的事情。
【问题讨论】:
-
关于清理,系统无法进行一些清理。一个例子是,如果您通过串行端口进行通信,那么您可能需要发送一个特殊的“再见”消息来告诉另一端您要离开了。
-
是的,但这不是告诉对方我已经离开的一种不可靠的方法吗?例如,如果 SIGKILL 命中进程,则我无能为力,或者没有可以放置的处理程序,因为没有处理程序可以映射到 SIGKILL... 对于某些应用程序,尽管我可以看到为什么这是有用的。对于我来说,我只需要进行内存释放并关闭一些线程。
-
您没有义务进行信号处理,但是如果您有一个 5 步每步 10 分钟的计算程序,这可能会很烦人。用户可能会意外杀死该程序。当它被杀死时,适当的信号处理可以保存步骤 1 到 4 的中间结果。
-
@It'sPete 谁建议你在 main() 中调用
signal(SIGINT, SIG_DFL);?参考?