前幾天在做p2p TCP穿透的時候,發(fā)現(xiàn)了一個很嚴重的一個問題,由于需要做點對點穿透,無法預(yù)知IP和內(nèi)網(wǎng)IP哪個會被連接,所以 P點 機器上使用了 socket.bind(IPAddress.Any, port); 并且使用端口復(fù)用,socket.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.ReuseAddress, true); //設(shè)置端口可重用 。以下稱A機器,B機器,S服務(wù)器。A向B做穿透連接。
在B的同一個端口上,啟動了連接S服務(wù)器的socket 和一個監(jiān)聽另一個P機器連接的socket ,但是問題出現(xiàn)了,在服務(wù)器S幫忙穿透后,A向B連接時,出現(xiàn)了無法連接,服務(wù)器積極拒絕的情況。后來在局域網(wǎng)中測試,發(fā)現(xiàn)把B的 bind 的 IPAddress.Any, 改成 固定的內(nèi)網(wǎng)IP后,沒有出現(xiàn)那種情況。
剛開始很郁悶,不是IPAddress.Any 可以在任何IP接口上啟動監(jiān)聽嗎,怎么不行?
一想,可能是B的端口復(fù)用上出現(xiàn)了問題,因為在同一個端口上綁定了另外一個Socket , 當然,端口復(fù)用不是問題所在,而是在端口復(fù)用的另一個Socket 上 (與 S 做連接的Socket ) 綁定的是固定的內(nèi)網(wǎng)IP,而不是IPAddress.Any 。 具體也不知道原理,我猜想可能是綁定固定IP的SOCKET 比較優(yōu)先吧,所以導(dǎo)致另一個復(fù)用的端口不能正常在IPAddress.Any 監(jiān)聽。后來,把那個綁定固定IP的SOCKET 也改成IPAddress.Any 就沒有出現(xiàn)問題了。
情況復(fù)雜,說得比較亂,完全是自己備忘和給有心人提個醒。
為這個問題郁悶了半天,下班回家晚上快睡覺的時候,慢慢整理出一個頭緒,想到可能可以解決的辦法。
?
后來查了資料,才明白了原理:端口復(fù)用時,當連接到來時,按最明確及最近綁定的原則將連接交給某一個應(yīng)用處理