最近使用Cdrouer測試產品時
有個NAT 名詞 hairpin
查了一下
這個網站解釋了很多NAT P2P的技術,值得一看
P2P最簡單的作法是有一台 server 有中間當橋
1. relay
2. connection reversal
但這2個作法,那台server需要大量的頻寬, 因為2個endpoint所有的流量都會從這個 server 進去
所以有了另一個方法
UDP holepunching
這個方法就是為了不讓中間的server 太忙,讓2個endpoint直接連線
但是還要需要一台 Rendezvous Server,
記錄2個endpoint各自的 public ip+port , private ip+port
之後這兩個endpoint 要連線, 這個server 便會傳給各自的public+private ip+port
讓他們直接連線
但這個又分成3種網路階層
1. endpoint在同一個NAT
2. endpoint在不同NAT
3. endpoint 在不同NAT,而且是2層NAT的網路架構
這3種的技術又不太一樣
1. 同個NAT
第一個比較簡單,在連線之前, A,B都跟S留下各自的 private+public ip/port (左邊的圖)
之後 A想連到B時, 會通知S , S會傳給A 有關B的 private+public ip/port (中間的圖)
S也會同時傳給B 有關A private+public ip/port, 叫B準備連線
A這時會先送出主動連線的UDP packet 到 B的public 和 private ip
理論上 送到 B 的private ip 會先成立,因為都在同個NAT,
所以連線建立了
2. 不同NAT
第二個複雜了點,在連線之前, A,B都跟S留下各自的 private+public ip/port (左邊的圖)
之後 A想連到B時, 會通知S , S會傳給A 有關B的 private+public ip/port (中間的圖)
S也會同時傳給B 有關A private+public ip/port, 叫B準備連線
A這時會先送出主動連線的UDP packet 到 B的public 和 private ip
理論上 送到 B 的private ip 是送不出去的,
而送到B 的public ip 會被DROP,但這時A 的NAT開了一個洞是 A->B的 udp session
這時, B會發出去主動連線到A 的 public IP , 這個也會在B的NAT開了一個洞是 B->A的 udp session
這個 B->A的UDP 封包就可以穿過A的NAT, 這時, A<->B的連線也建立了
3. multi level NAT
第三個有點複雜,左邊的圖跟上面2個都一樣
但是到了中間時,當A發出主動連線到B , 實際上到了NAT C
NAT C 會發現這個連線是要到自己的domain,
如果NAT C 有支援hairpin (loopback) NAT translation ,
會把這個連線的
source and destination ip 同時轉換
10.0.1.1:45000->155.99.25.11:62005 這個組轉換成155.99.25.11:62000->10.0.1.2:55000,
所以NAT A也開了洞,再等到 NAT B 也送來連線, 這個p2p連線就建立了
但有個疑問是NAT C 要怎麼知道,要將source/destination 同時轉呢?
我猜是原本在A,B 跟S連線留下的session ,
10.0.1.2:55000<->155.99.25.11:62005
10.0.1.1:45000<->155.99.25.11:62000
但什麼條件下會同時轉呢?