IP數據報的格式如圖3-1所示。普通的IP首部長為20個字節,除非含有選項字段。

分析圖3-1中的首部。最高位在左邊,記為0bit;最低位在右邊,記為31 bit。
4個字節的32 bit值以下面的次序傳輸:首先是0~7 bit,其次8~15 bit,然后1 6~23 bit,最后是24~31 bit。這種傳輸次序稱作big endian字節序。由于TCP/IP首部中所有的二進制整數在網絡中傳輸時都要求以這種次序,因此它又稱作網絡字節序。以其他形式存儲二進制整數的機器,如little endian格式,則必須在傳輸數據之前把首部轉換成網絡字節序。
目前的協議版本號是4,因此I P有時也稱作IPv4。3.10節將對一種新版的I P協議進行討論。
首部長度指的是首部占32bit字的數目,包括任何選項。由于它是一個4比特字段,因此首部最長為60個字節。在第8章中,我們將看到這種限制使某些選項如路由記錄選項在當今已沒有什么用處。普通IP數據報(沒有任何選擇項)字段的值是5。
服務類型(TOS)字段包括一個3bit的優先權子字段(現在已被忽略),4 bit的TOS子字段和1bit未用位但必須置0。4bit的TOS分別代表:最小時延、最大吞吐量、最高可靠性和最小費用。4 bit中只能置其中1 bit。如果所有4 bit均為0,那么就意味著是一般服務。RFC 1340
[Reynolds and Postel 1992]描述了所有的標準應用如何設置這些服務類型。RFC 1349[Almquist 1992]對該RFC進行了修正,更為詳細地描述了TOS的特性。
圖3-2列出了對不同應用建議的TOS值。在最后一列中給出的是十六進制值,因為這就是在后面將要看到的tcpdump命令輸出。

Telnet和Rlogin這兩個交互應用要求最小的傳輸時延,因為人們主要用它們來傳輸少量的交互數據。另一方面,FTP文件傳輸則要求有最大的吞吐量。最高可靠性被指明給網絡管理(SNMP)和路由選擇協議。用戶網絡新聞(Usenet news, NNTP)是唯一要求最小費用的應用。
現在大多數的TCP/IP實現都不支持TOS特性,但是自4.3BSDReno以后的新版系統都對它進行了設置。另外,新的路由協議如OSPF和IS-IS都能根據這些字段的值進行路由決策。
在2.10節中,我們提到SLIP一般提供基于服務類型的排隊方法,允許對交互通信數據在處理大塊數據之前進行處理。由于大多數的實現都不使用TOS字段,因此這種排隊機制由SLIP自己來判斷和處理,驅動程序先查看協議字段(確定是否是一個TCP段),然后檢查TCP信源和信宿的端口號,以判斷是否是一個交互服務。一個驅動程序的注釋這樣認為,這種“令人厭惡的處理方法”是必需的,因為大多數實現都不允許應用程序設置TOS字段。
總長度字段是指整個IP數據報的長度,以字節為單位。利用首部長度字段和總長度字段,就可以知道IP數據報中數據內容的起始位置和長度。由于該字段長16比特,所以IP數據報最長可達65535字節(回憶圖2-5,超級通道的MTU為65535。它的意思其實不是一個真正的MTU—它使用了最長的IP數據報)。當數據報被分片時,該字段的值也隨著變化,這一點將在11.5節中進一步描述。
盡管可以傳送一個長達65535字節的IP數據報,但是大多數的鏈路層都會對它進行分片。
而且,主機也要求不能接收超過576字節的數據報。由于TCP把用戶數據分成若干片,因此一般來說這個限制不會影響TCP。在后面的章節中將遇到大量使用UDP的應用(RIP,TFTP,BOOTP,DNS,以及SNMP),它們都限制用戶數據報長度為512字節,小于576字節。但是,事實上現在大多數的實現(特別是那些支持網絡文件系統NFS的實現)允許超過8192字節的IP數據報。總長度字段是IP首部中必要的內容,因為一些數據鏈路(如以太網)需要填充一些數據以達到最小長度。盡管以太網的最小幀長為46字節(見圖2-1),但是IP數據可能會更短。如果沒有總長度字段,那么IP層就不知道46字節中有多少是IP數據報的內容。
標識字段唯一地標識主機發送的每一份數據報。通常每發送一份報文它的值就會加1。在11.5節介紹分片和重組時再詳細討論它。同樣,在討論分片時再來分析標志字段和片偏移字段。
RFC 791 [Postel 1981a]認為標識字段應該由讓IP發送數據報的上層來選擇。假設有兩個連續的IP數據報,其中一個是由TCP生成的,而另一個是由UDP生成的,那么它們可能具有相同的標識字段。盡管這也可以照常工作(由重組算法來處理),但是在大多數從伯克利派生出來的系統中,每發送一個IP數據報,IP層都要把一個內核變量的值加1,不管交給IP的數據來自哪一層。內核變量的初始值根據系統引導時的時間來設置。
TTL(time-to-live)生存時間字段設置了數據報可以經過的最多路由器數。它指定了數據報的生存時間。TTL的初始值由源主機設置(通常為32或64),一旦經過一個處理它的路由器,它的值就減去1。當該字段的值為0時,數據報就被丟棄,并發送ICMP報文通知源主機。第8章我們討論Traceroute程序時將再回來討論該字段。我們已經在第1章討論了協議字段,并在圖1-8中示出了它如何被I P用來對數據報進行分
用。根據它可以識別是哪個協議向IP傳送數據。
首部檢驗和字段是根據IP首部計算的檢驗和碼。它不對首部后面的數據進行計算。ICMP、IGMP、UDP和TCP在它們各自的首部中均含有同時覆蓋首部和數據檢驗和碼。
為了計算一份數據報的IP檢驗和,首先把檢驗和字段置為0。然后,對首部中每個16 bit進行二進制反碼求和(整個首部看成是由一串16 bit的字組成),結果存在檢驗和字段中。當收到一份IP數據報后,同樣對首部中每個16bit進行二進制反碼的求和。由于接收方在計算過程中包含了發送方存在首部中的檢驗和,因此,如果首部在傳輸過程中沒有發生任何差錯,那么接收方計算的結果應該為全1。如果結果不是全1(即檢驗和錯誤),那么IP就丟棄收到的數據報。但是不生成差錯報文,由上層去發現丟失的數據報并進行重傳。
ICMP、IGMP、UDP和TCP都采用相同的檢驗和算法,盡管TCP和UDP除了本身的首部和數據外,在IP首部中還包含不同的字段。在RFC 1071[Braden, Borman and Patridge 1988]中有關于如何計算Internet檢驗和的實現技術。由于路由器經常只修改TTL字段(減1),因此當路由器轉發一份報文時可以增加它的檢驗和,而不需要對IP整個首部進行重新計算。RFC 1141[Mallory and Kullberg 1990]為此給出了一個很有效的方法。
但是,標準的BSD實現在轉發數據報時并不是采用這種增加的辦法。
每一份IP數據報都包含源IP地址和目的IP地址。我們在1.4節中說過,它們都是32 bit的值。
最后一個字段是任選項,是數據報中的一個可變長的可選信息。目前,這些任選項定義如下:
? 安全和處理限制(用于軍事領域,詳細內容參見RFC 1108[Kent 1991])
? 記錄路徑(讓每個路由器都記下它的I P地址,見7.3節)
? 時間戳(讓每個路由器都記下它的I P地址和時間,見7.4節)
? 寬松的源站選路(為數據報指定一系列必須經過的I P地址,見8.5節)
? 嚴格的源站選路(與寬松的源站選路類似,但是要求只能經過指定的這些地址,不能經過其他的地址)。
這些選項很少被使用,并非所有的主機和路由器都支持這些選項。選項字段一直都是以32 bit作為界限,在必要的時候插入值為0的填充字節。這樣就保證IP首部始終是32 bit的整數倍(這是首部長度字段所要求的)。
- 第1章 概述
- 1.1 引言
- 1.2 分層
- 1.3 TCP/IP的分層
- 1.4 互聯網的地址
- 1.5 域名系統
- 1.6 封裝
- 1.7 分用
- 1.8 客戶-服務器模型
- 1.9 端口號
- 1.10 標準化過程
- 1.11 RFC
- 1.12 標準的簡單服務
- 1.13 互聯網
- 1.14 實現
- 1.15 應用編程接口
- 1.16 測試網絡
- 1.17 小結
- 第2章 鏈路層
- 2.1 引言
- 2.2 以太網和IEEE 802封裝
- 2.3 尾部封裝
- 2.4 SLIP:串行線路IP
- 2.5 壓縮的SLIP
- 2.6 PPP:點對點協議
- 2.7 環回接口
- 2.8 最大傳輸單元MTU
- 2.9 路徑MTU
- 2.10 串行線路吞吐量計算
- 2.11 小結
- 第3章 IP:網際協議
- 3.1 引言
- 3.2 IP首部
- 3.3 IP路由選擇
- 3.4 子網尋址
- 3.5 子網掩碼
- 3.6 特殊情況的IP地址
- 3.7 一個子網的例子
- 3.8 ifconfig命令
- 3.9 netstat命令
- 3.10 IP的未來
- 3.11 小結
- 第4章 ARP:地址解析協議
- 4.1 引言
- 4.2 一個例子
- 4.3 ARP高速緩存
- 4.4 ARP的分組格式
- 4.5 ARP舉例
- 4.5.1 一般的例子
- 4.5.2 對不存在主機的ARP請求
- 4.5.3 ARP高速緩存超時設置
- 4.6 ARP代理
- 4.7 免費ARP
- 4.8 arp命令
- 4.9 小結
- 第5章 RARP:逆地址解析協議
- 5.1 引言
- 5.2 RARP的分組格式
- 5.3 RARP舉例
- 5.4 RARP服務器的設計
- 5.4.1 作為用戶進程的RARP服務器
- 5.4.2 每個網絡有多個RARP服務器
- 5.5 小結
- 第6章 ICMP:Internet控制報文協議
- 6.1 引言
- 6.2 ICMP報文的類型
- 6.3 ICMP地址掩碼請求與應答
- 6.4 ICMP時間戳請求與應答
- 6.4.1 舉例
- 6.4.2 另一種方法
- 6.5 ICMP端口不可達差錯
- 6.6 ICMP報文的4.4BSD處理
- 6.7 小結
- 第7章 Ping程序
- 7.1 引言
- 7.2 Ping程序
- 7.2.1 LAN輸出
- 7.2.2 WAN輸出
- 7.2.3 線路SLIP鏈接
- 7.2.4 撥號SLIP鏈路
- 7.3 IP記錄路由選項
- 7.3.1 通常的例子
- 7.3.2 異常的輸出
- 7.4 IP時間戳選項
- 7.5 小結
- 第8章 Traceroute程序
- 8.1 引言
- 8.2 Traceroute程序的操作
- 8.3 局域網輸出
- 8.4 廣域網輸出
- 8.5 IP源站選路選項
- 8.5.1 寬松的源站選路的traceroute程序示例
- 8.5.2 嚴格的源站選路的traceroute程序示例
- 8.5.3 寬松的源站選路traceroute程序的往返路由
- 8.6 小結
- 第9章 IP選路
- 9.1 引言
- 9.2 選路的原理
- 9.2.1 簡單路由表
- 9.2.2 初始化路由表
- 9.2.3 較復雜的路由表
- 9.2.4 沒有到達目的地的路由
- 9.3 ICMP主機與網絡不可達差錯
- 9.4 轉發或不轉發
- 9.5 ICMP重定向差錯
- 9.5.1 一個例子
- 9.5.2 更多的細節
- 9.6 ICMP路由器發現報文
- 9.6.1 路由器操作
- 9.6.2 主機操作
- 9.6.3 實現
- 9.7 小結