計網-ping服務命令與ICMP協議
- 2020 年 3 月 30 日
- 筆記
目錄
一、IP協議的助手 —— ICMP 協議(網路層協議)
二、ping —— 查詢報文類型的使用
三、traceroute —— 差錯報文類型的使用
參考:從Wireshark抓包軟體角度理解PING命令:https://juejin.im/post/5c15ec0f6fb9a049ec6af8b2
參考:ping好幾年 ?今天終於把 ping 的原理搞懂了,打算圖解教你!
ping(Packet Internet Groper)是一個服務命令,它可以用來測試網路連通性、網路時延、根據域名得到伺服器 IP等。它使用ICMP協議【具體來說,使用了 ICMP協議中的查詢報文類型:ECHO REQUEST回送請求(類型為8)和 ECHO REPLY回送應答(類型為0)】,所以了解PING命令的原理之前我們先熟悉與了解ICMP協議。
一、IP協議的助手 —— ICMP 協議(網路層協議)
ping 是基於 ICMP
協議工作的,所以要明白 ping 的工作,首先我們先來熟悉 ICMP 協議。
ICMP 是什麼?
ICMP 全稱是 Internet Control Message Protocol,也就是互聯網控制報文協議。
裡面有個關鍵詞 —— 控制,如何控制的呢?
網路包在複雜的網路傳輸環境里,常常會遇到各種問題。當遇到問題的時候,總不能死個不明不白,沒頭沒腦的作風不是電腦網路的風格。所以需要傳出消息,報告遇到了什麼問題,這樣才可以調整傳輸策略,以此來控制整個局面。
ICMP 功能都有啥?
ICMP
主要的功能包括:確認 IP 包是否成功送達目標地址、報告發送過程中 IP 包被廢棄的原因和改善網路設置等。
在 IP
通訊中如果某個 IP
包因為某種原因未能達到目標地址,那麼這個具體的原因將由 ICMP 負責通知。
如上圖例子,主機 A
向主機 B
發送了數據包,由於某種原因,途中的路由器 2
未能發現主機 B
的存在,這時,路由器 2
就會向主機 A
發送一個 ICMP
目標不可達數據包,說明發往主機 B
的包未能成功。
ICMP 的這種通知消息會使用 IP
進行發送 。
因此,從路由器 2
返回的 ICMP 包會按照往常的路由控制先經過路由器 1
再轉發給主機 A
。
收到該 ICMP 包的主機 A
則分解 ICMP 的首部和數據域以後得知具體發生問題的原因。
ICMP 包頭格式
ICMP 報文是封裝在 IP 包裡面,它工作在網路層,是 IP 協議的助手。
ICMP 報頭的類型欄位,大致可以分為兩大類:
-
一類是用於診斷的查詢消息,也就是「查詢報文類型」
-
另一類是通知出錯原因的錯誤消息,也就是「差錯報文類型」
查詢報文類型
回送消息 —— 類型
0
和8
回送消息用於進行通訊的主機或路由器之間,判斷所發送的數據包是否已經成功到達對端的一種消息,ping
命令就是利用這個消息實現的。
可以向接收端主機發送回送請求的消息(ICMP Echo Request Message
,類型 8
),也可以接收來自接收端主機發回來的回送應答消息(ICMP Echo Reply Message
,類型 0
)。
相比原生的 ICMP,這裡多了兩個欄位:
-
標識符:用以區分是哪個應用程式發 ICMP 包,比如用進程
PID
作為標識符; -
序號:序列號從
0
開始,每發送一次新的回送請求就會加1
, 可以用來確認網路包是否有丟失。
在選項數據中,ping
還會存放發送請求的時間值,來計算往返時間,說明路程的長短。
差錯報文類型
接下來,說明幾個常用的 ICMP 差錯報文的例子:
-
目標不可達消息 —— 類型 為
3
-
原點抑制消息 —— 類型
4
-
重定向消息 —— 類型
5
-
超時消息 —— 類型
11
目標不可達消息(Destination Unreachable Message) —— 類型為
3
IP 路由器無法將 IP 數據包發送給目標地址時,會給發送端主機返回一個目標不可達的 ICMP 消息,並在這個消息中顯示不可達的具體原因,原因記錄在 ICMP 包頭的程式碼欄位。
由此,根據 ICMP 不可達的具體消息,發送端主機也就可以了解此次發送不可達的具體原因。
舉例 6 種常見的目標不可達類型的程式碼:
-
網路不可達程式碼為
0
-
主機不可達程式碼為
1
-
協議不可達程式碼為
2
-
埠不可達程式碼為
3
-
需要進行分片但設置了不分片位程式碼為
4
為了給大家說清楚上面的目標不可達的原因,以送外賣為例講解。
a. 網路不可達程式碼為 0
外賣版本:
小林第一次送外賣時,小區里只有 A 和 B 區兩棟樓,但送餐地址寫的是 C 區樓,小林表示頭上很多問號,壓根就沒這個地方。
正常版本:
IP 地址是分為網路號和主機號的,所以當路由器中的路由器表匹配不到接收方 IP 的網路號,就通過 ICMP 協議以網路不可達(Network Unreachable
)的原因告知主機。
自從不再有網路分類以後,網路不可達也漸漸不再使用了。
b. 主機不可達程式碼為 1
外賣版本:
小林第二次送外賣時,這次小區有 5 層樓高的 C 區樓了,找到地方了,但送餐地址寫的是 C 區樓 601 號房 ,說明找不到這個房間。
正常版本:
當路由表中沒有該主機的資訊,或者該主機沒有連接到網路,那麼會通過 ICMP 協議以主機不可達(Host Unreachable
)的原因告知主機。
c. 協議不可達程式碼為 2
外賣版本:
小林第三次送外賣時,這次小區有 C 區樓,也有 601 號房,找到地方了,也找到房間了,但是一開門人家是外國人說的是英語,我說的是中文!語言不通,外賣送達失敗~
正常版本:
當主機使用 TCP 協議訪問對端主機時,能找到對端的主機了,可是對端主機的防火牆已經禁止 TCP 協議訪問,那麼會通過 ICMP 協議以協議不可達的原因告知主機。
d. 埠不可達程式碼為 3
外賣版本:
小林第四次送外賣時,這次小區有 C 區樓,也有 601 號房,找到地方了,也找到房間了,房間里的人也是說中文的人了,但是人家說他要的不是外賣,而是快遞。。。
正常版本:
當主機訪問對端主機 8080 埠時,這次能找到對端主機了,防火牆也沒有限制,可是發現對端主機沒有進程監聽 8080 埠,那麼會通過 ICMP 協議以埠不可達的原因告知主機。
e. 需要進行分片但設置了不分片位程式碼為 4
外賣版本:
小林第五次送外賣時,這次是個吃播部落客了 100 份外賣,但是吃播部落客要求一次性要把全部外賣送達,小林的一台電動車裝不下呀,這樣就沒辦法送達了。
正常版本:
發送端主機發送 IP 數據報時,將 IP 首部的分片禁止標誌位設置為1
。根據這個標誌位,途中的路由器遇到超過 MTU 大小的數據包時,不會進行分片,而是直接拋棄。
隨後,通過一個 ICMP 的不可達消息類型,程式碼為 3 的報文,告知發送端主機。
原點抑制消息(ICMP Source Quench Message) —— 類型
4
在使用低速廣域線路的情況下,連接 WAN 的路由器可能會遇到網路擁堵的問題。
ICMP
原點抑制消息的目的就是為了緩和這種擁堵情況。
當路由器向低速線路發送數據時,其發送隊列的快取變為零而無法發送出去時,可以向 IP 包的源地址發送一個 ICMP 原點抑制消息。
收到這個消息的主機藉此了解在整個線路的某一處發生了擁堵的情況,從而增大 IP 包的傳輸間隔,減少網路擁堵的情況。
然而,由於這種 ICMP 可能會引起不公平的網路通訊,一般不被使用。
重定向消息(ICMP Redirect Message) —— 類型
5
如果路由器發現發送端主機使用了「不是最優」的路徑發送數據,那麼它會返回一個 ICMP 重定向消息給這個主機。
在這個消息中包含了最合適的路由資訊和源數據。這主要發生在路由器持有更好的路由資訊的情況下。路由器會通過這樣的 ICMP 消息告知發送端,讓它下次發給另外一個路由器。
好比,小林本可以過條馬路就能到的地方,但小林不知道,所以繞了一圈才到,後面小林知道後,下次小林就不會那麼傻再繞一圈了。
超時消息(ICMP Time Exceeded Message) —— 類型
11
IP 包中有一個欄位叫做 TTL
(Time To Live
,生存周期),它的值隨著每經過一次路由器就會減 1,直到減到 0 時該 IP 包會被丟棄。
此時,IP 路由器將會發送一個 ICMP 超時消息給發送端主機,並通知該包已被丟棄。
設置 IP 包生存周期的主要目的,是為了在路由控制遇到問題發生循環狀況時,避免 IP 包無休止地在網路上被轉發。
此外,有時可以用 TTL 控制包的到達範圍,例如設置一個較小的 TTL 值。
二、ping —— 查詢報文類型的使用
接下來,我們重點來看 ping
的發送和接收過程。
同個子網下的主機 A 和 主機 B,主機 A 執行ping
主機 B 後,我們來看看其間發送了什麼?
ping 命令執行的時候,源主機首先會構建一個 ICMP 回送請求消息數據包。
ICMP 數據包內包含多個欄位,最重要的是兩個:
-
第一個是類型,對於回送請求消息而言該欄位為
8
; -
另外一個是序號,主要用於區分連續 ping 的時候發出的多個數據包。
每發出一個請求數據包,序號會自動加 1
。為了能夠計算往返時間 RTT
,它會在報文的數據部分插入發送時間。
然後,由 ICMP 協議將這個數據包連同地址 192.168.1.2 一起交給 IP 層。IP 層將以 192.168.1.2 作為目的地址,本機 IP 地址作為源地址,協議欄位設置為 1
表示是 ICMP
協議,在加上一些其他控制資訊,構建一個 IP
數據包。
接下來,需要加入 MAC
頭。如果在本地 ARP 映射表中查找出 IP 地址 192.168.1.2 所對應的 MAC 地址,則可以直接使用;如果沒有,則需要發送 ARP
協議查詢 MAC 地址,獲得 MAC 地址後,由數據鏈路層構建一個數據幀,目的地址是 IP 層傳過來的 MAC 地址,源地址則是本機的 MAC 地址;還要附加上一些控制資訊,依據乙太網的介質訪問規則,將它們傳送出去。
主機 B
收到這個數據幀後,先檢查它的目的 MAC 地址,並和本機的 MAC 地址對比,如符合,則接收,否則就丟棄。
接收後檢查該數據幀,將 IP 數據包從幀中提取出來,交給本機的 IP 層。同樣,IP 層檢查後,將有用的資訊提取後交給 ICMP 協議。
主機 B
會構建一個 ICMP 回送響應消息數據包,回送響應數據包的類型欄位為 0
,序號為接收到的請求數據包中的序號,然後再發送出去給主機 A。
在規定的時候間內,源主機如果沒有接到 ICMP 的應答包,則說明目標主機不可達;如果接收到了 ICMP 回送響應消息,則說明目標主機可達。
此時,源主機會檢查,用當前時刻減去該數據包最初從源主機上發出的時刻,就是 ICMP 數據包的時間延遲。
針對上面買的發送的事情,總結成了如下圖:
當然這只是最簡單的,同一個區域網裡面的情況。如果跨網段的話,還會涉及網關的轉發、路由器的轉發等等。
但是對於 ICMP 的頭來講,是沒什麼影響的。會影響的是根據目標 IP 地址,選擇路由的下一跳,還有每經過一個路由器到達一個新的區域網,需要換 MAC 頭裡面的 MAC 地址。
說了這麼多,可以看出 ping 這個程式是使用了 ICMP 協議中查詢報文類型:ECHO REQUEST(類型為8)和ECHO REPLY (類型為0)。
三、traceroute —— 差錯報文類型的使用
有一款充分利用 ICMP 差錯報文類型的應用叫做traceroute(
在UNIX、MacOS中是這個命令,而在Windows中對等的命令叫做 tracert)。其原理主要是利用ICMP差錯報文類型中的超時消息(ICMP Time Exceeded Message)。
traceroute命令 用於追蹤數據包在網路上的傳輸時的全部路徑,它默認發送的數據包大小是40位元組。
通過traceroute我們可以知道資訊從你的電腦到互聯網另一端的主機是走的什麼路徑。當然每次數據包由某一同樣的出發點(source)到達某一同樣的目的地(destination)走的路徑可能會不一樣,但基本上來說大部分時候所走的路由是相同的。