知識前提:STUN 代表UDP數據包簡單地穿過NAT(Simple Traversal of UDP over NAT)。這是一個協議,當一個IP電話機在NAT后面時,IP電話機可以使用這個協議檢測到NAT的存在,并判斷NAT的類型。一個IP電話機如果支持 STUN協議,它就可以發送一系列的STUN查詢,到公共的因特網上的STUN服務器,這樣就可以得到NAT上映射到話機的公網IP地址和端口。IP電話機就可以智能地修改SIP/SDP消息中的私有IP地址。這樣SIP信令和RTP多媒體數據就可以成功地穿過NAT,而不需要修改NAT的任何配置。
STUN代表了對大多數NAT的解決方法,但是不適合于對稱的NAT。也就是說,絕大多數的SOHO路由器都是非對稱的NAT,在這種情況下,使用STUN是成功的。但是STUN協議不能穿過對稱的NAT。如果你的路由器是對稱的NAT,則不要使用STUN。
問題:公網終端正常,NAT后的終端無法看到和聽到公網終端圖像與聲音。
解決方法之一是使用STUN技術:
http://bgp.potaroo.net/ietf/rfc-pdf/rfc3489.pdf
簡單來說,STUN解決的過程如下:
1、將STUN Client放在NAT后的終端中。
2、該終端在發送OLC之前調用STUN Client,去連接位于公網的任一臺STUN Server.
3、STUN Server與STUN Client進行STUN Messgae交互(STUN Server將對應的RTP/RTCP經NAT轉換后的地址告之STUN Client)。
4、該終端在打開本地邏輯通道時,使用STUN Client已經發送過的地址作為RTP/RTCP地址。并且在填寫OLC時將STUN Client得到的NAT轉換后的地址填寫到OLC報文中。比如:STUN Client使用192.168.1.4:40000與192.168.1.4:40001 與STUN Server通訊;得到的經NAT轉換后的地址為:221.12.27.14:2000與221.12.27.14:2039;那么終端在打開本地的RTP/RTCP就指定為40000與40001,同時OLC中地址替換為221.12.27.14:2000與221.12.27.14:2039。
5、這樣公網的終端將會把數據發到221.12.27.14:2000與221.12.27.14:2039上,NAT會送到192.168.1.4:40000與192.168.1.4:40001上。
在這里,提及了4種NAT類型,上面使用STUN的結果會有不同:
● 如果STUN Server和被叫不是同一主機,那么只有Full Cone類型的NAT才能成功。
● 如果STUN Server和被叫是同一主機(也就是被叫終端安裝STUN Server),但STUN Server使用的端口與本地OLC的端口不同,那么Restricted Cone NAT類型的也能成功。
● 如果STUN Server和被叫是同一主機,而且STUN Server使用的端口與本地OLC的端口相同,那么都能成功。
OpenH323 在其class H323EndPoint/class H323_RTP_UDP/class RTP_UDP中已經加入了STUN Client支持,你只需要調用H323EndPoint ::SetSTUNServer(…),就可以完成Client的功能。其STUN Client的代碼在PWLIB中:http://cvs.sourceforge.net/viewcvs.py/openh323/pwlib/src/ptclib/pstun.cxx
雖然OpenH323沒有提供STUN Server的支持,但是找到一個成熟的STUN Server/Client并添加到OpenH323中并不是一件難事:http://sourceforge.net/projects/stun/ 是不錯的選擇。
將http://sourceforge.net/projects/stun/的代碼放入PWLIB中編譯,并相應的修改OpenH323,以支持STUN Server。