linux操作系统之信号
(1)信號的概念
? ? ? ? ? ?信號的特點:簡單,不能攜帶大量信息,滿足某種特定條件才觸發(fā)。
? ? ? ? ? ?信號的機制;“軟中斷”,通過軟件方式實現(xiàn),具有很強的延時性。每個進程收到的信號,都由內(nèi)核負責發(fā)送,內(nèi)核處理。
? ? ? ? ? ?信號的產(chǎn)生:1)按鍵產(chǎn)生(ctrl+c,ctrl+z,ctrl+\)
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?2) 系統(tǒng)調(diào)用產(chǎn)生(kill,abort,raise)
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?3)軟件條件產(chǎn)生(定時器alarm)
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?4)硬件異常產(chǎn)生((非法訪問內(nèi)存)段錯誤,(除0)浮點數(shù)例外,內(nèi)存對齊出錯(總線錯誤))
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?5)命令產(chǎn)生(kill)
? ? ? ? ?信號的處理方式:1)執(zhí)行默認動作
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 1>Term :終止進程? 2>lgn:忽略信號3>core:終止進程(查驗死亡原因,gdb調(diào)試)
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 4>Stop:停止(暫停)進程5>Cont:繼續(xù)進程
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?2)忽略(舍棄)
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?3)捕捉(掉用戶處理函數(shù))
? ? ? ? ?信號的四要素:編號? 名稱? 事件 默認處理動作
? ? ? ? Linux內(nèi)核中有一個PCB進程控制塊,是一個結構體,task_struct,里面保存了進程id,狀態(tài),工作目錄,用戶id,用戶組id,文件描述符和阻塞信號集及未決信號集。
? ? ? ?信號的編號:由kill -i查看當前系統(tǒng)可使用的命令,其中1~31為常規(guī)信號,34~64為實時信號。
? ? ? ?在31個常規(guī)信號中,9)SIGKILL和19)SIGSTOP信號不能被忽略和捕捉,智能執(zhí)行默認動作,不能設置其為阻塞。
(2)信號的產(chǎn)生
? ? ?1)終端按鍵產(chǎn)生信號:ctrl+c? -->2)SIGINT(終止、中斷)ctrl+z --->20)SIGTSTP(暫時、停止)? ctrl+\--->3)SIGQUIT(退出)
? ? ?2) 硬件產(chǎn)生信號:除零操作-->8)SIGFPE(浮點數(shù)例外)? ? ?非法訪問內(nèi)存-->11)SIGSEGV(段錯誤)? ?總線錯誤 --->7)SIGBUS
? ? ?3)?kill函數(shù)或命令產(chǎn)生信號: kill -SIGKILL pid
? ? ? ? ? ? ? int kill(pid_t pid,int sig);? ? ? 成功:0 失敗-1
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?sig:不推薦直接使用數(shù)字,應使用宏名。因為不同的操作系統(tǒng)可能編號不一樣,但名稱一致。
? ? ? ? ? ? ? ? pid>0? ?發(fā)送信號給指定進程
? ? ? ? ? ? ? ? pid<0? ? 發(fā)送信號給調(diào)用kill函數(shù)同一進程組的所有進程。
? ? ? ? ? ? ? ?pid<0? ? ?取|pid|發(fā)給對應進程組
? ? ? ? ? ? ? ?pid=-1? ? 發(fā)送給當前用戶組的所有進程? ? ? ? ? ? ? ? ?
? ? ? ? ? ?raise函數(shù):給自己發(fā)指定信號? int raise(int sig)==kill(getpid(),sig)
? ? ? ? ? abort函數(shù):給自己發(fā)送異常終止信號? 6)SIGABRT信號,終止并產(chǎn)生core文件,void abort(void)
? ? 4)軟件產(chǎn)生信號
? ? ? ? ? ? ?alarm函數(shù):定時固定秒數(shù)之后,內(nèi)核給當前進程發(fā)送14)SIGALRM信號,終止進程(每個進程只有一個鬧鐘)? ?
? ? ? ? ? ? ?unsigned int alarm(unsigned int seconds);? 返回0或剩余的秒數(shù)(上一次定時剩余的秒數(shù))?alarm(0)取消定時
? ? ? ? ? ? ? ? ? ? ? ? 采用自然定時發(fā),與進程狀態(tài)無關
? ? ? ? ? ? setitimer函數(shù):定時可以達到微秒,可實現(xiàn)循環(huán)定時。
? ? ? ? ? ? int setitimer(int which,const struct itimerval*new_value,struct itimerval*old_value);
? ? ? ? ? ? ? ? ? ? ?參數(shù)which(定時方式):ITIMER_REAL(自然定時法-)-->14)SIGLARM
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?ITIMER_VIRTUAL(虛擬空間計時,用戶時間)---->26)SIGVTALRM
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ITMER_PROF(運行時間計時,用戶+內(nèi)核)------>27)SIGPROF
? ? ? ? ? ? ? ? ? ?程序實際執(zhí)行的時間=系統(tǒng)時間+用戶時間+等待時間
? ? ? ? ? ? ? ? ??
? ? ? ? ? ? 其中it_interval為周期定時的時間,it_value為當前定時的時間。
(3)信號集操作函數(shù)
? ? ? 內(nèi)核通過讀取未決信號集來判斷信號是否被處理,信號屏蔽字(阻塞信號集)mask可以影響未決信號集。? ? ? ? ? ??
? ? ? ? ? ?1 )信號集設定
? ? ? ? ? ? ? ?
? ? ? ? 2)sigprocmask函數(shù):屏蔽信號,接觸屏蔽,設置信號集
? ? ? ? ? ? ?int sigprocmask(int how,const sigset_t*set,sigset_t*oldset);
? ? ? ? ? ? ? ? ? ? ? ? ? how:SIG_BLOCK,set表示需要屏蔽的信號
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?SIG_UNBLOCK,set表示需要解屏蔽的信號
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?SIG_SETMASK:set表示需要替代原始的新屏蔽集。
? ? ? ? 3)sigpending函數(shù):獲取當前的未決信號集
? ? ? ? ? ? ? ? ? int sigpending(sigset_t*set);? ? //使用sigsimember來判斷某個信號是否在其中
(4)信號捕捉
? ? ? ? ? ?1)signal函數(shù):注冊一個信號捕捉函數(shù),抓信號由內(nèi)核進行
? ? ? ? ? ? ? ? ? ? ? typedef void(*sighandler_t)(int);
? ? ? ? ? ? ? ? ? ? ?sighandler_t signal(int signum,sighandler_t handler);
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?參數(shù):signum(捕捉的信號)? handle(處理的函數(shù))
? ? ? ? ?2)sigaction函數(shù):修改信號處理動作
? ? ? ? ? ? ? ? ? ? int sigaction(int signum,const struct sigaction*act,struct sigaction*oldact)
? ? ? ? ? ? ??
? ? ? ? ? ? ? 重點掌握:1>sa_handler:指定的信號捕捉后的處理函數(shù)名,可以賦值為SIG_IGN(表示忽略)SIG_DFL(表示執(zhí)行默認)
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 2>sa_mask:調(diào)用信號處理函數(shù)時使用的屏蔽信號集(臨時設置,執(zhí)行完函數(shù)即失效)(如果有信號為非屏蔽? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?信號集中的信號,會先處理該信號)
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?3>sa_flags:設置為0,表默認屬性(信號捕捉函數(shù)期間,默認屏蔽本信號)
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?阻塞的常規(guī)信號不支持排隊,產(chǎn)生多次只記錄一次,捕捉函數(shù)執(zhí)行完之后再執(zhí)行該阻塞信號。
? ? ? ? ? ? ?其他:第五個信號舍棄不用
? ? ? ? ? ? ? ? ? ? ? ? 當sa_flags==SA_SIGINFO時,使用第二個參數(shù)處理程序。
? ? ? ? ? ? 3)內(nèi)核實現(xiàn)信號捕獲過程
? ? ? ? ? ? ? ? ? ??
?
總結
以上是生活随笔為你收集整理的linux操作系统之信号的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: linux操作系统进程间通信IPC之共享
- 下一篇: linux操作系统信号捕捉函数之siga