淺談以太網中的UDP編程

關於Internet上傳輸的、udp數據的大小問題,在論壇找到的帖子

http://bbs.csdn.net/topics/20299532#new_post

轉Delphi大富翁上的帖子的一部分,具體的帖子見

http://www.delphibbs.com/delphibbs/dispq.asp?lid=726166

輪子學習筆記一:淺談以太網中的UDP編程 

1.在進行UDP編程的時候,我們最容易想到的問題就是,一次發送多少bytes好? 
當然,這個沒有唯一答案,相對於不同的系統,不同的要求,其得到的答案是不一樣的,我這裏僅對 
像ICQ一類的發送聊天消息的情況作分析,對於其他情況,你或許也能得到一點幫助: 
首先,我們知道,TCP/IP通常被認爲是一個四層協議系統,包括鏈路層,網絡層,運輸層,應用層. 
UDP屬於運輸層,下面我們由下至上一步一步來看: 
以太網(Ethernet)數據幀的長度必須在46-1500字節之間,這是由以太網的物理特性決定的. 
這個1500字節被稱爲鏈路層的MTU(最大傳輸單元). 
但這並不是指鏈路層的長度被限制在1500字節,其實這這個MTU指的是鏈路層的數據區. 
並不包括鏈路層的首部和尾部的18個字節. 
所以,事實上,這個1500字節就是網絡層IP數據報的長度限制. 
因爲IP數據報的首部爲20字節,所以IP數據報的數據區長度最大爲1480字節. 
而這個1480字節就是用來放TCP傳來的TCP報文段或UDP傳來的UDP數據報的. 
又因爲UDP數據報的首部8字節,所以UDP數據報的數據區最大長度爲1472字節. 
這個1472字節就是我們可以使用的字節數。:) 

當我們發送的UDP數據大於1472的時候會怎樣呢? 
這也就是說IP數據報大於1500字節,大於MTU.這個時候發送方IP層就需要分片(fragmentation). 
把數據報分成若干片,使每一片都小於MTU.而接收方IP層則需要進行數據報的重組. 
這樣就會多做許多事情,而更嚴重的是,由於UDP的特性,當某一片數據傳送中丟失時,接收方便 
無法重組數據報.將導致丟棄整個UDP數據報。 

因此,在普通的局域網環境下,我建議將UDP的數據控制在1472字節以下爲好. 

進行Internet編程時則不同,因爲Internet上的路由器可能會將MTU設爲不同的值. 
如果我們假定MTU爲1500來發送數據的,而途經的某個網絡的MTU值小於1500字節,那麼系統將會使用一系列的機 
制來調整MTU值,使數據報能夠順利到達目的地,這樣就會做許多不必要的操作. 

鑑於Internet上的標準MTU值爲576字節,所以我建議在進行Internet的UDP編程時. 
最好將UDP的數據長度控件在548字節(576-8-20)以內. 

2.UDP數據報的覆蓋和重疊問題? 
有的兄弟說使用UDP編程時會出現數據的覆蓋和重疊問題, 
所謂覆蓋,即發送第一條消息爲"第一條",第二條消息爲"第二條". 
而接收到的兩條消息皆爲"第一條". 
而重疊,即指當發送"第一條","第二條"兩條消息後. 
收到的第一條消息可能是不固定的,比如"第一條第二","第一條第二條"等. 
這種重疊的情況在TCP編程中是常見的. 
但是在我的編程經驗中,從來沒有遇到過這兩種情況. 

我在局域網中在機器A用使死循環連續不斷的向機器B發送UDP數據報. 
但一直沒有出現上面的兩個問題. 

因此我認爲,根據UDP協議的特性,不會象基於字節流連接的TCP一樣出現重疊問題. 
有兄弟說,他在局域網試也沒有問題,但在Internet上會.是不是路由器對數據進行組合, 
或者說兩條消息同時到達? 

我想兩條消息到達的時延無論如何不會比在局域網中的時延短吧?即時有,那種機率也是很少的. 
而對於路由數據進行了重組,我認爲,即使假定路由器對數據進行了重組,這也對導致UDP數據報 
在接收時發現數據報中的校驗和與數據不一致而丟棄該數據報。 

暫定寫到這裏吧,歡迎兄弟們指正,討論。:P 

Email:[email protected] 

輪子 

2001.9.25 
發佈了36 篇原創文章 · 獲贊 7 · 訪問量 20萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章