SNMP報文結構以下:(編碼以前)安全
版本號網絡 |
團體名數據結構 |
協議數據單元PDUide |
SNMP共有5種報文,因此其PDU也有5中,第七點會詳細介紹SNMP的5種協議數據單元。編碼
SNMP規定了5種協議數據單元PDU(也就是SNMP報文),用來在管理進程和代理之間的交換。spa
get-request操做:從代理進程處提取一個或多個參數值。.net
get-next-request操做:從代理進程處提取緊跟當前參數值的下一個參數值。代理
set-request操做:設置代理進程的一個或多個參數值。code
get-response操做:返回的一個或多個參數值。這個操做是由代理進程發出的,它是前面三種操做的響應操做。trap操做:代理進程主動發出的報文,通知管理進程有某些事情發生。
前面的3種操做是由管理進程向代理進程發出的,後面的2個操做是代理進程發給管理進程的,爲了簡化起見,前面3個操做從此叫作get、get-next和set操做。圖1描述了SNMP的這5種報文操做。請注意,在代理進程端是用熟知端口161倆接收get或set報文,而在管理進程端是用熟知端口162來接收trap報文。orm
圖1 SNMP的5種報文操做
圖2是封裝成UDP數據報的5種操做的SNMP報文格式。可見一個SNMP報文共有三個部分組成,即公共SNMP首部、get/set首部、trap首部、變量綁定。
(1)公共SNMP首部
共三個字段:
版本
寫入版本字段的是版本號減1,對於SNMP(即SNMPV1)則應寫入0。
共同體(community)
共同體就是一個字符串,做爲管理進程和代理進程之間的明文口令,經常使用的是6個字符「public」。
PDU類型
根據PDU的類型,填入0~4中的一個數字,其對應關係如表2所示意圖。
表2 PDU類型
PDU類型 |
名稱 |
0 |
get-request |
1 |
get-next-request |
2 |
get-response |
3 |
set-request |
4 |
trap |
(2)get/set首部
請求標識符(request ID)
這是由管理進程設置的一個整數值。代理進程在發送get-response報文時也要返回此請求標識符。管理進程可同時向許多代理髮出get報文,這些報文都使用UDP傳送,先發送的有可能後到達。設置了請求標識符可以使管理進程可以識別返回的響應報文對於哪個請求報文
差錯狀態(error status)
由代理進程回答時填入0~5中的一個數字,見表3的描述
表3 差錯狀態描述
差錯狀態 |
名字 |
說明 |
0 |
noError |
一切正常 |
1 |
tooBig |
代理沒法將回答裝入到一個SNMP報文之中 |
2 |
noSuchName |
操做指明瞭一個不存在的變量 |
3 |
badValue |
一個set操做指明瞭一個無效值或無效語法 |
4 |
readOnly |
管理進程試圖修改一個只讀變量 |
5 |
genErr |
某些其餘的差錯 |
差錯索引(error index)
當出現noSuchName、badValue或readOnly的差錯時,由代理進程在回答時設置的一個整數,它指明有差錯的變量在變量列表中的偏移。
(3)trap首部
企業(enterprise)
填入trap報文的網絡設備的對象標識符。此對象標識符確定是在圖3的對象命名樹上的enterprise結點{1.3.6.1.4.1}下面的一棵子樹上。
trap類型
此字段正式的名稱是generic-trap,共分爲表4中的7種。
trap類型 |
名字 |
說明 |
0 |
coldStart |
代理進行了初始化 |
1 |
warmStart |
代理進行了從新初始化 |
2 |
linkDown |
一個接口從工做狀態變爲故障狀態 |
3 |
linkUp |
一個接口從故障狀態變爲工做狀態 |
4 |
authenticationFailure |
從SNMP管理進程接收到具備一個無效共同體的報文 |
5 |
egpNeighborLoss |
一個EGP相鄰路由器變爲故障狀態 |
6 |
enterpriseSpecific |
代理自定義的事件,須要用後面的「特定代碼」來指明 |
當使用上述類型二、三、5時,在報文後面變量部分的第一個變量應標識響應的接口。
特定代碼(specific-code)
指明代理自定義的時間(若trap類型爲6),不然爲0。
時間戳(timestamp)
指明自代理進程初始化到trap報告的事件發生所經歷的時間,單位爲10ms。例如時間戳爲1908代表在代理初始化後1908ms發生了該時間。
(4)變量綁定(variable-bindings)
指明一個或多個變量的名和對應的值。在get或get-next報文中,變量的值應忽略。
管理變量的表示
管理變量表示管理對象類型在某一時刻的值(或稱該類型的實例),SNMP以管理變量做爲操做對象。
管理變量的表示方法是這樣規定的:形如x.y,其中x是管理對象的object identifer。y是能惟一肯定對象類型值的一組數字,在非表型變量中爲0,在表型變量中是這個表的索引,好比接口表中的接口號,或路由表中的目的網絡地址等等 。如:在MIB文件裏定義了ipAdEntNetMask這一管理對象,其object identifier爲1.3.6.1.1.5.6.1.3它是個路由表中的一項,它的一個實例就是路由表中某一行的子網掩碼,若是這行的索引、目的網絡地址爲129.102.1.0。則這個變量名是:1.3.6.1.1.5.6.1.3.129.102.1.0。在之後的說明中,爲了方便,把惟一肯定管理變量的一組數字,也就是x.y中的y稱做實例。
駐留在被管設備上的AGENT從UDP端口161接受來自網管站的串行化報文,經解碼、團體名驗證、分析獲得管理變量在MIB樹中對應的節點,從相應的模塊中獲得管理變量的值,再造成響應報文,編碼發送回網管站。網管站獲得響應報文後,再經一樣的處理,最終顯示結果。
下面根據RFC1157詳細介紹Agent接受到報文後採起的動做:
首先解碼生成用內部數據結構表示的報文,解碼依據ASN.1的基本編碼規則,若是在此過程當中出現錯誤致使解碼失敗則丟棄該報文,不作進一步處理。
第二步:將報文中的版本號取出,若是與本Agent支持的SNMP版本不一致,則丟棄該報文,不作進一步處理。當前北研的數據通訊產品只支持SNMP版本1。
第三步:將報文中的團體名取出,此團體名由發出請求的網管站填寫。如與本設備承認的團體名不符,則丟棄該報文,不作進一步處理,同時產生一個陷阱報文。SNMPv1只提供了較弱的安全措施,在版本3中這一功能將大大增強。
第四步:從經過驗證的ASN.1對象中提出協議數據單元PDU,若是失敗,丟棄報文,不作進一不處理。不然處理PDU,結果將產生一個報文,該報文的發送目的地址應同收到報文的源地址一致。
根據不一樣的PDU,SNMP協議實體將作不一樣的處理:
第一種狀況:若是PDU中的變量名在本地維護的MIB樹中不存在,則接受到這個PDU的協議實體將向發出者發送一個GetResponse報文,其中的PDU與源PDU只有一點不一樣:將ERROR-STATUS置爲noSuchName,並在ERROR-INDEX中指出產生該變量在變量LIST中的位置。
第二種狀況:若是本地協議實體將產生的響應報文的長度大於本地長度限制,將向該PDU的發出者發送一個GetResponse報文,該PDU除了ERROR-STATUS置爲tooBig,ERROR-INDEX置爲0之外,與源PDU相同。
第三種狀況:若是本地協議實體由於其餘緣由不能產生正確的響應報文,將向該PDU的發出者發送一個GetResponse報文,該PDU除了ERROR-STATUS置爲genErr,ERROR-INDEX置爲出錯變量在變量LIST中的位置,其他與源PDU相同。
第四中狀況:若是上面的狀況都沒有發生,則本地協議實體向該PDU的發出者發送一個GetResponse報文,該PDU中將包含變量名和相應值的對偶表,ERROR-STATUS爲noError,ERROR-INDEX爲0,request-id域的值應與收到PDU的request-id相同。
GetNextRequest PDU的最重要的功能是表的遍歷,這種操做受到了前面所說的管理變量的表示方法的支持,從而能夠訪問一組相關的變量,就好象他們在一個表內。
下面經過一個例子解釋表遍歷的過程:
被管設備維護以下路由表:
Destination NextHop Metric
10.0.0.99 89.1.1.42 5
9.1.2.3 99.0.0.3 3
10.0.0.51 89.1.1.42 5
假設網管站欲取得這張路由表的信息,該表的索引是目的網絡地址。
網管站向被管設備發送一個GetNextRequest PDU,其中的受管對象的標識以下
GetNextRequest ( ipRouteDest, ipRouteNextHop, ipRouteMetric1 )
SNMP agent響應以下GetResponse PDU:
GetResponse (( ipRouteDest.9.1.2.3 = "9.1.2.3" ),
( ipRouteNextHop.9.1.2.3 = "99.0.0.3" ),
( ipRouteMetric1.9.1.2.3 = 3 ))
網管站繼續:
GetNextRequest ( ipRouteDest.9.1.2.3,
ipRouteNextHop.9.1.2.3,
ipRouteMetric1.9.1.2.3 )
agent響應:
GetResponse (( ipRouteDest.10.0.0.51 = "10.0.0.51" ),
( ipRouteNextHop.10.0.0.51 = "89.1.1.42" ),
( ipRouteMetric1.10.0.0.51 = 5 ))
值得注意的是agent必須可以肯定下一個管理變量名,以保證全部變量能被取到且只被取到一次。
網管站繼續:
GetNextRequest ( ipRouteDest.10.0.0.51,
ipRouteNextHop.10.0.0.51,
ipRouteMetric1.10.0.0.51 )
agent 響應:
GetResponse (( ipRouteDest.10.0.0.99 = "10.0.0.99" ),
( ipRouteNextHop.10.0.0.99 = "89.1.1.42" ),
( ipRouteMetric1.10.0.0.99 = 5 ))
網管站繼續
GetNextRequest ( ipRouteDest.10.0.0.99,
ipRouteNextHop.10.0.0.99,
ipRouteMetric1.10.0.0.99 )
這時由於路由表中全部的行都被取遍,agent因返回路由表對象的下一字典後繼即該管理對象在MIB樹中的後序遍歷的直接後繼。這裏應是nettoMediaIndex,管理對象的OBJECT IDENTIFIER。這個響應通知網管站對錶的遍歷已經完成。
GetResponse PDU只有當受到getRequest GetNextRequest SetRequest才由協議實體產生,網管站收到這個PDU後,應顯示其結果。
SetRequest PDU除了PDU類型標識之外,和GetRequest相同,當須要對被管變量進行寫操做時,網管站側的協議實體將生成該PDU。
對SetRequest的響應將根據下面狀況分別處理:
若是是關於一個只讀變量的設置請求,則收到該PDU的協議實體產生一個GetReponse報文,並置error status爲noSuchName, error index的值是錯誤變量在變量list中的位置。
若是被管設備上的協議實體收到的PDU中的變量對偶中的值,類型、長度不符和要求,則收到該PDU的協議實體產生一個GetReponse報文,並置error status爲badValue, error index的值是錯誤變量在變量list中的位置。
若是須要產生的GetReponse報文長度超過了本地限制,則收到該PDU的協議實體產生一個GetReponse報文,並置error status爲tooBig, error index的值是0。
若是是其餘緣由致使SET失敗,則收到該PDU的協議實體產生一個GetReponse報文,並置error status爲genErr, error index的值是錯誤變量在變量list中的位置。
若是不符合上面任何狀況,則agent將把管理變量設置收到的PDU中的相應值,這每每能夠改變被管設備的運行狀態。同時產生一個GetResponse PDU,其中error status置爲noError,error index的值爲0。
Trap PDU的有以下的形式
產生trap的系統的OBJECT IDENTIFIER
|
系統的IP地址 |
普通類型 |
特定類型 |
時戳 |
變量對偶表 |
Trap是被管設備遇到緊急狀況時主動向網管站發送的消息。網管站收到trap PDU後要將起變量對偶表中的內容顯示出來。一些經常使用的trap類型有冷、熱啓動,鏈路狀態發生變化等。