2011-11-23 53 views
1

我在尝试在c中编写一个smallshell时遇到了一些问题。Unix编程 - 信号处理器

问题是:假设我为信号处理程序编写了一些代码,在这种情况下,它被修改为捕获SIGCHLD信号,我怎么能通知我的程序信号已被捕获?
如果我使用全局变量,问题很简单,但这不是我想要去做的。所以任何建议/提示将不胜感激!

这就是我现在要解决的问题。

volatile sig_atomic_t exit_status; /* <--global variabel */ 

void sigchld_handler(int signal) { 
    switch (signal) { 
    case SIGCHLD: 
     exit_status = 1; /* SIGCHLD was caught, notify program.. */ 
     break; 
    default: 
     fprintf(stderr, "Some signal catched\n"); /* not a signal of intrest */ 
     break; 
    } 
} 

//感谢

+0

绝对使用全局变量。另外,在使用'volatile'之前,请确保您阅读[this](http://www.cs.utah.edu/~regehr/papers/emsoft08-preprint.pdf),它基本上表明(至少)普通编译器混乱打开优化时使用'volatile'。或[内核文档中的这一点](http://www.mjmwired.net/kernel/Documentation/volatile-considered-harmful.txt)。更何况丹尼斯里奇也反对'挥发性' – Shahbaz

+0

谢谢,我会看看它:) –

回答

2

标准解决方案是使用unix self-pipe trick。好处是管道的读取端可以与select()epoll()一起使用,因此可以与event loops很好地集成,而无需定期轮询原子变量的值。

1

signal(7)包含的是安全的信号处理程序来执行的功能列表; fprintf(3)不是其中之一。如果在您的外壳正在打印提示或状态消息时孩子死亡会发生什么?损坏的数据结构是通常的结果。 (对玩具来说这很好 - 但我不想要这样的外壳。)

设置全局变量对信号处理程序来说是非常典型的。这是一个简单的方法来指示进程的主要事件循环或主要处理循环,以便完成其他事情。