2017-05-03 34 views
0

我有一個特定的問題。Python通過帶多線程概念的dbus信號引發異常

  1. 程序的主要內容從創建使用dbus循環的過程開始,在這裏我監聽信號。
  2. 我存儲在隊列中的信號內容。在主要的下一部分,我有一個線程池。
  3. 當某個線程從隊列中取項時,它使用特定的函數(檢測)來處理請求 - 基於隊列中項目的內容。 (對數據庫有操作,從中取數據並根據請求進行一些操作)
  4. 線程池中的每個線程都會啓動一個線程,它應該處理信號(當前狀態和中斷)。

例如:我收到信號,這意味着我必須處理一些數字。線程池中的任何線程都會從隊列中獲取此項並啓動處理數字內容的函數 - 這可能需要很長時間。所以在任何時候之後,我都會收到當前狀態的信號,並且需要發送當前的檢測狀態 - 這就是爲什麼我使用線程(用於共享內存)的原因。我也可以接收來自D-Bus的中斷信號(「需要很長的時間,因此停止檢測並免費提供另一個請求」)。和中斷的主要問題是...

所以我的主要問題是:

  1. 有什麼辦法,我可以提高對中斷信號異常並停止功能(檢測)? (我只是發現解決方案,但只爲主要捕獲...但我需要抓住它在線程池中的線程,並提升線程中線程中的線程)
  2. 第二個問題是關於GIL ...做我的信號接收線程接收所有信號?我認爲它不...(是的,我用threads_init()

程序:

SERVICE = multiprocessing.Process(target=dbus_signal_receiver, args=(...)) 
SERVICE.daemon = True 
SERVICE.start() 

class worker(threading.Thread): 
    def __init__(self,...): 
     threading.Thread.__init__(self) 

    def run(self): 
     while True: 
      #get item from queue 
      s = threading.Thread(target=curr_and_interr_signal_handle, args=(ID of item from queue,...)) 
      s.daemon = True 
      s.start() 
      #start specific detection based on request 

for i in range(number of threads): 
    t = worker(...) 
    t.daemon = True 
    t.start() 

,我希望,這樣的事情會工作...(但事實並非如此)

... 

class worker(threading.Thread): 
    def __init__(self,...): 
     threading.Thread.__init__(self) 

    def run(self): 
     while True: 
      try: 
       #get item from queue 
       s = threading.Thread(target=curr_and_interr_signal_handle, args=(ID of item from queue,...)) 
       s.daemon = True 
       s.start() 
       #start specific detection based on request 
      except raised_interrupt_exception: 
       #continue - wait for another request from queue 


... 
+0

也許這與[ASYNCIO]更容易完成(https://github.com/ldo/dbussy)... –

回答

0

閱讀18.8.1.2. Signals and threads
Python的信號處理器是始終在主Python的線程中執行,甚至 如果信號在另一個線程中被接收到。
這意味着信號不能用作線程間通信的手段。
您可以改用線程模塊的同步原語。
此外,只允許主線程設置新的信號處理程序。

閱讀有關17.1.7. Event Objects
這是線程間通信最簡單的機制之一:一個線程信號的事件和其他線程等待它


目前尚不清楚爲什麼你必須使用thread in thread
爲什麼您的worker thread不能處理檢測?

例如,下面應該做到這一點:

def run(self): 
    while self.running.is_set(): 
     #get item from queue 
     #start specific detection based on request 
+0

螺紋螺紋我因爲隊列中的每個項目(請求)都是使用的,而我在線程池中使用它有它自己的唯一ID。因此,線程池中的每個線程都會啓動線程來處理來自D-Bus的關於檢測和中斷的當前狀態的處理信號,以停止帶ID的處理請求。當中斷時,在處理這個ID的線程中停止函數並繼續從隊列中獲取另一個項(請求) –

+0

例如:我得到了D-Bus信號,這意味着ID爲55的中斷請求。並且因爲這個線程 - 線程。線程(target = curr_and_interr_signal_handle,args =(...)) - 開始從隊列中獲取項目的ID,如果隊列中的實際處理項目的ID與信號中斷請求ID相同,則會引發任何異常。但是這引起了異常,我無法正確捕捉。 –

+0

你有更好的方式來處理它嗎? –