2012-03-10 69 views
37

TCP具有元組對(IP Addr/port/type)來告訴另一個客戶端。 UDP傳遞客戶端IP和端口。 unix域如何跟蹤不同的客戶端?Unix域套接字如何區分多個客戶端?

換句話說,服務器創建一個綁定到某個路徑say/tmp/socket的套接字。 2個或更多客戶端連接到/ tmp/socket。底下發生了什麼,跟蹤客戶端1和客戶端2的數據?我認爲網絡堆棧在域套接字中不起作用,所以內核在這裏做所有的工作?

是否有像Unix協議格式和TCP/UDP格式的unix域協議格式?域套接字數據報協議的格式是否在某處發佈?每個unix都不同或者像POSIX那樣標準化它嗎?

感謝您的任何照明。我找不到任何解釋這一點的信息。每個來源只是掩飾如何使用域套接字。

+0

談論unix域協議基本上只是文件I/O。除非通過套接字傳遞的數據包含源標識,否則無法確定哪個進程發送了特定的字符串。 – 2012-03-10 05:51:52

+0

@MarcB應該是一個答案 – 2012-03-10 05:59:17

+3

這是真的嗎?如果服務器寫入數據,則第一個讀取的客戶端獲取數據,而不管該數據是否適用於該客戶端?這使他們幾乎無用。 – 2012-03-10 06:03:12

回答

62

如果您創建了一個PF_UNIX類型爲SOCK_STREAM的套接字並接受其上的連接,則每次接受連接時,都會得到一個新的文件描述符(作爲系統調用的返回值)。此文件描述符從客戶機進程中的文件描述符讀取數據並將數據寫入文件描述符。因此它就像TCP/IP連接一樣工作。

沒有「unix域協議格式」。這不需要,因爲Unix域套接字不能通過網絡連接連接到對等體。在內核中,表示您的Unix域套接字末尾的文件描述符指向一個數據結構,該數據結構告訴內核哪個文件描述符位於連接的另一端。將數據寫入文件描述符時,內核將在連接的另一端查找文件描述符,並將數據追加到其他文件描述符的讀取緩衝區。內核不需要將數據放入包含描述其目標的標頭的數據包中。

對於SOCK_DGRAM套接字,必須告訴內核應該接收數據的套接字的路徑,並使用它來查找該接收套接字的文件描述符。

如果您連接到服務器套接字之前綁定到你的客戶端套接字的路徑(或你,如果你使用SOCK_DGRAM發送數據之前),則該服務器進程可以得到使用getpeername(爲SOCK_STREAM)這條道路。對於SOCK_DGRAM,接收方可以使用recvfrom來獲取發送套接字的路徑。

如果你沒有綁定路徑,那麼接收過程不能獲得唯一標識對等體的id。至少,不是我正在運行的Linux內核(2.6.18-238.19.1.el5)。

+0

感謝您提供了一個非常好的完整答案。 – 2012-03-11 05:38:33

+0

很好的回答。謝謝@rob – nic 2015-04-09 05:06:57

+0

Linux中也有用於AF_UNIX的SOCK_SEQPACKET,它允許像SOCK_STREAM這樣的連接,但也保留了像SOCK_DGRAM中的消息邊界。 – 2015-09-07 16:10:58

相關問題