日韩av黄I国产麻豆传媒I国产91av视频在线观看I日韩一区二区三区在线看I美女国产在线I麻豆视频国产在线观看I成人黄色短片

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 >

UNIX环境编程学习笔记(25)——信号处理进阶学习之 sigaction 函数

發布時間:2024/8/24 47 豆豆
生活随笔 收集整理的這篇文章主要介紹了 UNIX环境编程学习笔记(25)——信号处理进阶学习之 sigaction 函数 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

lienhua34
2014-11-05

sigaction 函數跟 signal 函數一樣,用于設置信號處理函數。此函數是用于取代 UNIX 早期版本使用的 signal 函數。UNIX 早期版本的 signal 函數在捕獲到一個信號之后,就會自動將該信號的處理動作恢復為默認處理動作。于是,如果我們希望注冊的信號處理函數長期生效,則需要在信號處理程序中再次調用 signal 函數注冊一次。這樣的操作太麻煩,而且在信號處理函數中再次調用 signal 注冊信號處理函數之前可能又會產生該信號,而這個信號就會觸發默認處理動作。

另外,signal 函數還有一個限制:不修改信號的處理方式就不能確定該信號的當前處理方式。這個限制在 sigaction 函數中不存在。

sigaction 函數的聲明如下,

#include <signal.h>

int sigaction(int signo, const struct sigaction *restrict act, struct sigaction *restrict oact);

返回值:若成功則返回0,若出錯則返回-1

其中,signo 參數即要檢測或修改其處理動作的信號編號。如果 act 指針非空,則要修改該信號的處理動作。如果 oact 指針非空,則由 oact 指針返回該信號的上一個動作。
sigaction 函數的參數中使用的結構體 struct sigaction 的聲明如下,

struct sigaction {void (*sa_handler)(int);sigset_t sa_mask;int sa_flags;void (*sa_sigaction)(int, siginfo_t *, void *); };

該結構體各個字段的說明如下:

  • sa_handler:信號處理函數的指針。
  • sa_mask:在調用該信號的處理函數期間進程要阻塞的信號集。
  • sa_flags:指定信號進行處理的各個選項,關于具體的選項,可以參考sigaction 函數的手冊。
  • sa_sigaction:替代的信號處理函數,如果sa_flags 設置了SA_SIGINFO,則會調用該信號處理函數;否則調用sa_handler。

我們來看一個例子,

#include <stdlib.h> #include <stdio.h> #include <unistd.h> #include <string.h> #include <errno.h> #include <signal.h>void print_mask(const char *str) {sigset_t sigset;int errno_save;errno_save = errno;if (sigprocmask(0, NULL, &sigset) < 0) {printf("sigprocmask error: %s\n", strerror(errno));exit(-1);}printf("%s", str);if (sigismember(&sigset, SIGALRM)) {printf("SIGALRM ");}if (sigismember(&sigset, SIGINT)) {printf("SIGINT ");}printf("\n");errno = errno_save; }static void sig_alrm(int signo) {printf("received SIGALRM\n");print_mask("in sig_alrm: "); }int main(void) {struct sigaction sact;sact.sa_handler = sig_alrm;sact.sa_flags = 0;sigemptyset(&sact.sa_mask);sigaddset(&sact.sa_mask, SIGINT);if (sigaction(SIGALRM, &sact, NULL) < 0) {printf("sigaction error: %s\n", strerror(errno));exit(-1);}print_mask("in main before alarm: ");alarm(3);pause();print_mask("in main after alarm: ");exit(0); }

在上面的 sigactiondemo.c 程序中,我們調用 sigaction 函數設置了信號 SIGALRM 的處理函數,而在 sigaction 函數的參數 act 的sa_mask 字段中添加了信號 SIGINT,表示調用信號 SIGALRM 的處理函數期間,進程阻塞信號 SIGINT。編譯該程序,生成并執行可執行文件 sigactiondemo,

lienhua34:demo$ gcc -o sigactiondemo sigactiondemo.c lienhua34:demo$ ./sigactiondemo in main before alarm: received SIGALRM in sig_alrm: SIGALRM SIGINT in main after alarm:

從上面的運行結果,我們看到在 SIGALRM 信號產生之前,進程沒有屏蔽信號 SIGINT 和 SIGALRM,而在信號 SIGALRM 的處理函數中,進程的信號屏蔽字中包含了 SIGINT 和 SIGALRM,而在調用 SIGALRM 的信號處理函數之后,進程的信號屏蔽字復原為調用信號處理屏蔽字之前。(說明:在調用 sigaction 函數注冊的信號處理函數期間,系統會自動將該信號也加入信號屏蔽字中,除非設置 sigaction 函數的 act 參數的sa_flags為SA_NODEFER。)

(done)

轉載于:https://www.cnblogs.com/lienhua34/p/4077595.html

總結

以上是生活随笔為你收集整理的UNIX环境编程学习笔记(25)——信号处理进阶学习之 sigaction 函数的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。