python之signal操作


1 信號的意義

在linux系統中信號是與進程通信的一種手段。假設沒有信號,linux中的進程一旦運行起來將不再受控,這種局面對於進程的管理來說是一種災難。kill、ctrl+c等操作本質上就是我們向linux發出的信號,進程接收到信號后根據相應的策略做出反饋。

 

 

2 信號的來源

A) 通過終端(組合鍵)產生信號

最典型的ctrl+c終止當前進程

B) 硬件異常產生信號

例如進程運行中內存的尋址出現異常,就會發出信號。

C) 顯式的調用linux命令產生信號

最典型的kill命令,通過linux命令發出信號干預進程運行

D) 軟件代碼發送信號

Java本地方法、Python signal類包等,通過程序發出信號。

 

 

3 有哪些信號

執行命令$kill -l可以看到信號列表

 

 

 

可以看到有62種信號,32、33輪空;1-31號為不可靠信號,是linux自帶的與進程通信的信號;34-64是可靠信號,是為了彌補linux不可靠信號太少而擴展的。不可靠信號多次發出最終只響應1次;而可靠信號每次都有響應。

執行命令$man 7 signal可以更詳細的查看每一種信號的意義:

 

 

 

例如我們前面說過的ctrl+c,對應的是2號sigint;kill對應的是9號sigkill;內存錯誤對應的11號sigsegv。

 

 

4 進程會如何處理這些信號

並不是每種信號進程都要給出反饋的,進程對待信號會有3種策略:

A) 忽略此信號

好理解,就是假裝沒看見,不鳥它。

B) 執行默認動作

例如終止進程等

C) 提供一個信號處理函數,要求內核執行該函數

通過某種形式在發送信號時同時給定處理信號的函數,相當於回調函數

 

 

5 python對信號的支持

Python對信號的操作在importsignal這個包里,有了前面知識的積累,我們很好理解signal包調用的側重點:哪種信號?如何處理?如何發送?

A) 哪種信號?

Linux的62種信號,signal包已經都搬到python中來了,需要開發人員自己選擇一種

B) 如何處理?

Signal默認提供了Ignal和Default2種策略,同時支持開發人員自定義回調函數

C) 如何發送?

Signal對信號的發送做了簡易的封裝,例如alarm()函數發起sigalrm信號

 

6 案例,做一個timeout的自定義annotation:

import signal
 
def timeout(seconds=10, error_message="connect to server timeout"):
    def decorator(func):
        def _handle_timeout(signum, frame):
            raise TimeoutError(error_message)
 
        def wrapper(*args, **kwargs):
            signal.signal(signal.SIGALRM, _handle_timeout)
            signal.alarm(seconds)
            try:
                result = func(*args, **kwargs)
            finally:
                signal.alarm(0)
            return result
 
        return wraps(func)(wrapper)
 
    return decorator

 


先定制了一個回調函數decorator,超時后直接拋異常;

然后通過signal.signal()方法決定了信號種類和處理方式,第一個參數可以替換成62種信號的其中一種,第二個參數還可以傳入SIG_DFL或SIG_IGN;

最后通過signal.alarm()函數發起信號。

這樣我就自己開發了一個超時處理機制。

@timeout(1200)
def ready_host(**not_connected):
    while True:
        if not any(not_connected):
            break
        for h in not_connected.keys():
            if check_port_is_open(h):
                del not_connected[h]
 
    return True
————————————————
版權聲明:本文為CSDN博主「牛麥康納」的原創文章,遵循CC 4.0 BY-SA版權協議,轉載請附上原文出處鏈接及本聲明。
原文鏈接:https://blog.csdn.net/yejingtao703/article/details/80659458

 

原文鏈接:https://blog.csdn.net/yejingtao703/article/details/80659458


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM