📜  信号 (1)

📅  最后修改于: 2023-12-03 15:36:43.070000             🧑  作者: Mango

信号

简介

信号是 UNIX 操作系统的重要特性之一,是一种软件中断。它是由操作系统传递给进程的中断通知,用于通知进程发生了某些事件。

在 Unix 系统中,信号可分为以下两类:

  • 标准信号:Unix 系统中预定义了一些常用的信号,如 SIGKILLSIGTERMSIGINT 等。
  • 实时信号:在 POSIX 标准中定义的一类新型信号。它们的行为比标准信号更加可预测。
信号处理方式

当进程接收到信号时,可以采取如下几种处理方式:

  • 忽略信号
  • 执行默认操作
  • 自定义信号处理函数
忽略信号

可以通过调用 signal() 函数来忽略某些信号。如下所示:

#include <signal.h>

// 忽略信号不做任何处理
signal(SIGINT, SIG_IGN); 

在上面的代码中,我们将 SIGINT 信号忽略,当进程收到 SIGINT 信号时,不做任何处理。

默认操作

每个信号都有一个默认的行为,当进程接收到信号时,将自动执行该行为。比如,当进程接收到 SIGTERM 信号时,默认将终止进程。

自定义信号处理函数

我们可以自定义信号处理函数来处理接收到的信号。如下所示:

#include <signal.h>

void sigint_handler(int signo) 
{
    printf("Received SIGINT signal\n");
}

int main(int argc, char *argv[]) 
{
    signal(SIGINT, sigint_handler);
    while(1) {}
    return 0;
}

在上面的代码中,当进程接收到 SIGINT 信号时,将执行 sigint_handler() 函数。

信号相关函数

下面是一些常用的信号相关函数。

signal()

用于设置信号处理函数。函数定义如下:

#include <signal.h>

typedef void (*sighandler_t)(int);

sighandler_t signal(int signum, sighandler_t handler);

其中,signum 表示信号的编号,handler 表示信号处理函数。

kill()

用于向指定进程或进程组发送信号。函数定义如下:

#include <signal.h>

int kill(pid_t pid, int sig);

其中,pid 表示进程标识符,sig 表示信号的编号。

raise()

用于向当前进程发送信号,等同于调用 kill(getpid(), sig)。函数定义如下:

#include <signal.h>

int raise(int sig);

其中,sig 表示信号的编号。

sigaction()

用于设置信号处理函数和信号屏蔽字。函数定义如下:

#include <signal.h>

int sigaction(int signum, const struct sigaction *act, struct sigaction *oldact);

其中,signum 表示信号的编号,act 表示新的信号处理函数和信号屏蔽字,oldact 表示原来的信号处理函数和信号屏蔽字。

总结

信号是 Unix 操作系统的重要特性之一,可以用于进程之间的通信和事件处理。在编写程序时,需要注意信号的处理方式和相关函数的使用。