2012-01-01 91 views
0

我正在編寫一個服務器應用程序,它將本地串行端口簡單地連接到多個網絡連接的客戶端。我使用linux和C作爲服務器應用程序,因爲程序的設備是內存有限的路由器。發送相同的信息到多個線程/套接字?

我有一切設置爲多個客戶端連接和發送數據到串行端口使用每個連接的fork()過程。

我的問題在於將串行端口上的數據傳入多個客戶端連接(varing number)。我的問題在於爲每個活動套接字設計一種方法來獲取所有傳入數據,並且只獲取一次。任何幫助?

+0

你是說多個網絡客戶端正在讀寫一個單一的通用串行接口?這聽起來很像,但這也是一種奇怪的模式。 – purpleamy 2012-01-01 03:25:37

+0

就是這樣。如果它不奇怪,那肯定會更容易。可惜的是,串聯輸入網絡是重要的方向。另一個方向更容易,因爲每個線程都會根據需要直接寫入串行端口。 – scoutjoe 2012-01-01 03:34:28

+0

我不確定你的設計或要求是否正確。你應該非常小心串行端口。您可以使用多路複用系統調用,如'poll'或'select'而不是幾個線程。 – 2012-01-01 07:04:58

回答

0

假設你保留一個或連接到客戶端的列表或其他參考,爲什麼不只是循環這些信息的每一位並將它發送給所有人?

+0

謝謝,這就是我正在嘗試的方法,我希望有一些「內置管道或類似」的方式,我有大量的循環運行。 – scoutjoe 2012-01-01 04:01:44

1

聽起來像你需要每個連接的客戶端的數據隊列(緩衝區)。每次數據進入端口時,都會將其發送到每個客戶端隊列的後面。然後客戶端從各自隊列的前面讀取數據。由於所有的客戶端可能會以不同的速率讀取數據,這將確保他們所有的數據都只能得到一次數據副本,而且當有更多的數據進入時,您不會掛斷等待任何一個客戶端。當然,您需要爲每個連接的客戶端隊列分配一定數量的內存(我不確定您期望的客戶端數量,並且您確實表示您的可用內存有限),並且您需要考慮如何處理在客戶端讀取所有內容之前,隊列會變滿。

0

每個套接字設計的線程可能不是解決此問題的最佳方法。事件驅動的異步方法應該更適合。但是,如果您必須使用線程來完成此操作,並且串行端口速度很慢,那麼在監聽串行端口的線程和所有與網絡客戶端交談的線程之間建立管道是最實際的。你可以使用rwlocks來移動數據,但是你仍然需要一種方法讓網絡線程在套接字和串口數據上等待,所以你需要爲這兩個文件使用文件描述符輪詢。

但嚴重的是,這可能會更容易,沒有線程會更好。把它看作一個主循環,等待正在觀察網絡和串口的輪詢,確定發生了哪個事件,並相應地分配數據。一旦你明白了,這應該會更容易。

+0

只需重讀並給定環境,您可能沒有標準的POSIX設施,因此管道可能不是一個選項。另一種選擇是中斷網絡套接字讀取等待的信號。但假設你有某種形式的民意調查,這應該是一個相對安全的假設,我仍然試着完全放棄這些話題,因爲我沒有看到他們添加的內容。 – purpleamy 2012-01-01 04:20:02

+0

謝謝。這種類型的服務器編程對我來說是新的,所以我試圖抓住我的方式,線程/ fork是我發現處理多重連接的第一種方式,我試着讓我的頭繞過你談論的另一種方法,所以而不是fork()'ing我會將新套接字的fd添加到數組的某個時間,然後回過頭來處理數組中的每個成員(讀/寫)? – scoutjoe 2012-01-01 04:29:22

+0

您需要一個連接數組,您需要了解輪詢界面。一旦你得到了這些,你的事件循環只需要使用提供的函數來測試哪些FD被提出並處理事件(這取決於你如何使用這些工具創建邏輯來將事件路由到處理程序),其中我認爲你有四個:連接,斷開連接,從串行接收和從網絡客戶端接收。 – purpleamy 2012-01-01 15:56:52