歡迎來到Linux教程網
Linux教程網
Linux教程網
Linux教程網
Linux教程網 >> Linux編程 >> Linux編程 >> Linux的信號處理和實際使用(結合Redis分析)

Linux的信號處理和實際使用(結合Redis分析)

日期:2017/3/1 9:46:51   编辑:Linux編程

最近比較多朋友問我常見的信號和一些Linux信號實際的應用。所以,我簡單總結一下,讓大家對信號有清晰的理解。

我自己寫的系統裡面,我是直接參考redis的信號處理機制的。

redis是這樣處理信號的:

如果系統支持 HAVE_BACKTRACK,即是:

#if defined(__APPLE__) || defined(__linux__) || defined(__sun)
#define HAVE_BACKTRACE 1
#endif

那麼redis會用sigsegvHandler函數處理SIGSEGV , SIGBUS , SIGFPE , SIGILL等信號。

否則只用sigtermHandler 處理 SIGTERM ,SIGQUIT 。

我自己系統是這樣實現的(分析如上):

void
setupSignalHandlers(void){
struct sigaction act;

sigemptyset(&act.sa_mask);
act.sa_flags = 0;
act.sa_handler = sigtermHandler;
sigaction(SIGTERM , &act , NULL);
sigaction(SIGQUIT , &act , NULL);

#ifdef HAVE_BACKTRACE
sigemptyset(&act.sa_mask);
act.sa_flags = SA_NODEFER|SA_RESETHAND|SA_SIGINFO;
act.sa_sigaction = sigsegvHandler;
sigaction(SIGSEGV ,&act , NULL);
sigaction(SIGBUS ,&act , NULL);
sigaction(SIGFPE ,&act , NULL);
sigaction(SIGILL ,&act , NULL);
#endif /* HAVE_BACKTRACE */
return;
}

SIGKILL : 用來立即結束程序的運行. 本信號不能被阻塞, 處理和忽略。

SIGTERM : 有兩個信號可以停止進程:SIGTERM和SIGKILL。 SIGTERM比較友好,進程能捕捉這個信號,根據您的需要來關閉程序。在關閉程序之前,您可以結束打開的記錄文件和完成正在做的任務。在某些情況下,假 如進程正在進行作業而且不能中斷,那麼進程可以忽略這個SIGTERM信號。

SIGINT : 程序終止(interrupt)信號, 在用戶鍵入INTR字符(通常是Ctrl-C)時發出。

SIGQUIT信號: SIGQUIT 和SIGINT類似, 但由QUIT字符(通常是Ctrl-)來控制. 進程在因收到 SIGQUIT退出時會產生core文件, 在這個意義上類似於一個程序錯誤信號。

SIGSEGV : 試圖訪問未分配給自己的內存, 或試圖往沒有寫權限的內存地址寫數據

SIGBUS :非法地址, 包括內存地址對齊(alignment)出錯. eg: 訪問一個四個字長的整數, 但其地址不是4的倍數.

SIGFPE : 在發生致命的算術運算錯誤時發出. 不僅包括浮點運算錯誤, 還包括溢出及除數為0等其它所有的算術的錯誤.

SIGILL : 執行了非法指令. 通常是因為可執行文件本身出現錯誤, 或者試圖執行數據段. 堆棧溢出時也有可能產生這個信號.

(不得不說的是,redis的信號處理機制。非常漂亮。在程序出現錯誤的時候,可以打印出和valgrind一樣有用的信息。不知道大家是怎樣想的。反正我的項目如果C代碼過3K。我都會加入這個機制的。)

Redis 的詳細介紹:請點這裡
Redis 的下載地址:請點這裡

Copyright © Linux教程網 All Rights Reserved