c - 将自定义函数设置为所有信号的处理程序

标签 c unix signals

我有这个任务要做:

编写一个函数 void myfunct(void(*f)(int sig))f 设置为所有可能信号的处理程序。

我有两个问题:

  1. a 如何获得所有可能的信号?有这个功能吗?我可以通过某种方式遍历它们吗?
  2. 将函数 f 设置为接受参数的处理程序真的有效吗?它不应该没有任何参数吗?

谢谢。

最佳答案

我个人会迭代一个静态的信号编号列表,并使用预处理器指令来检测支持哪些信号(在编译时)。例如:

#include <signal.h>

static const all_signals[] = {
#ifdef SIGHUP
    SIGHUP,  /* POSIX.1 */
#endif
#ifdef SIGQUIT
    SIGQUIT, /* POSIX.1 */
#endif
#ifdef SIGTRAP
    SIGTRAP, /* POSIX.1 */
#endif
#ifdef SIGIO
    SIGIO,   /* BSD/Linux */
#endif

/*
 * Other signal names omitted for brevity
*/

/* C89/C99/C11 standard signals: */
    SIGABRT,
    SIGFPE,
    SIGILL,
    SIGINT,
    SIGSEGV,
/* SIGTERM (C89/C99/C11) is also the terminating signal number */
    SIGTERM
};

SIGTERM 是数组中安装了信号处理程序的最后一个条目:

    struct sigaction  act;
    int               i = 0;

    memset(&act, 0, sizeof act);
    sigemptyset(&act.sa_mask);
    act.sa_handler = your_signal_handler;
    act.sa_flags = 0;

    do {
        if (sigaction(all_signals[i], &act, NULL)) {
            fprintf(stderr, "Cannot install signal %d handler: %s.\n", all_signals[i], strerror(errno));
            exit(EXIT_FAILURE);
        }
    } while (all_signals[i++] != SIGTERM);

这样您的代码就不需要 POSIX 等支持即可工作,但如果在编译时可用,则支持 POSIX 信号。

可以查维基百科Unix signal文章和man 7 signal对于已知的信号名称。

您还可以使用安装 POSIX 实时信号的信号处理程序

#if SIGRTMAX-0 > SIGRTMIN-0
    for (i = SIGRTMIN; i <= SIGRTMAX; i++)
        if (sigaction(i, &act, NULL)) {
            fprintf(stderr, "Cannot install realtime signal %d handler: %s.\n", i, strerror(errno));
            exit(EXIT_FAILURE);
        }
#endif

关于c - 将自定义函数设置为所有信号的处理程序,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/41909348/

相关文章:

c - K&R 中的 getline 函数定义

c - 如何处理字符串连接中尺寸较小的情况?

c++ - MinGW 可以毫不费力地复制大多数 unix 系统调用吗?

unix - awk 比较两个文件并打印格式化输出

erlang - 进程正常退出

c - 信号处理程序在到达双 SIGINT 时终止主程序和所有分支

c - Matlab 抽取( vector ,阶数, 'fir')内部工作原理

c - 将文件重命名为回收站

c - 在 C 程序中使用 system ("clear") 命令时出现奇怪的输出

synchronization - "S->value <= 0"signal() 在没有忙等待的信号量中实现