C++中的信号处理
信号是由操作系统传递给进程的中断,它可能提前终止程序。您可以在UNIX、LINUX、Mac OS X或Windows系统上按Ctrl+C来生成中断。
有些信号程序无法捕获,但以下列出了一些可在程序中捕获的信号,并可根据信号采取相应的操作。这些信号在C++头文件中定义。
信号 | 描述 |
---|---|
SIGABRT | 程序异常终止,例如调用abort。 |
SIGFPE | 算术运算错误,例如除以零或导致溢出的运算。 |
SIGILL | 检测到非法指令。 |
SIGINT | 收到交互式中断信号。 |
SIGSEGV | 无效的存储器访问。 |
SIGTERM | 发送到程序的终止请求。 |
signal() 函数
C++信号处理库提供signal函数来捕获意外事件。以下是signal()函数的语法:
void (*signal (int sig, void (*func)(int)))(int);
简单来说,此函数接收两个参数:第一个参数是一个整数,表示信号编号;第二个参数是指向信号处理函数的指针。
让我们编写一个简单的C++程序,其中我们将使用signal()函数捕获SIGINT信号。无论您想在程序中捕获哪个信号,都必须使用signal函数注册该信号并将其与信号处理程序关联。请查看以下示例:
示例
#include <iostream> #include <csignal> using namespace std; void signalHandler( int signum ) { cout << "Interrupt signal (" << signum << ") received.\n"; // cleanup and close up stuff here // terminate program exit(signum); } int main () { // register signal SIGINT and signal handler signal(SIGINT, signalHandler); while(1) { cout << "Going to sleep...." << endl; sleep(1); } return 0; }
输出
Going to sleep.... Going to sleep.... Going to sleep....
按下Ctrl + C后,将显示:
输出
Going to sleep.... Going to sleep.... Going to sleep.... Interrupt signal (2) received.
raise() 函数
您可以通过raise()函数生成信号,该函数接收一个整数信号编号作为参数,并具有以下语法。
int raise (signal sig);
这里,sig是要发送任何信号的信号编号:SIGINT、SIGABRT、SIGFPE、SIGILL、SIGSEGV、SIGTERM、SIGHUP。以下是在使用raise()函数内部引发信号的示例:
示例
#include <iostream> #include <csignal> using namespace std; void signalHandler( int signum ) { cout << "Interrupt signal (" << signum << ") received.\n"; // cleanup and close up stuff here // terminate program exit(signum); } int main () { int i = 0; // register signal SIGINT and signal handler signal(SIGINT, signalHandler); while(++i) { cout << "Going to sleep...." << endl; if( i == 3 ) { raise( SIGINT); } sleep(1); } return 0; }
输出
Going to sleep.... Going to sleep.... Going to sleep.... Interrupt signal (2) received.
广告