歡迎來到Linux教程網
Linux教程網
Linux教程網
Linux教程網
您现在的位置: Linux教程網 >> UnixLinux >  >> Linux綜合 >> Linux資訊 >> 更多Linux

Linux下的IP隧道研究(2)

摘要  在Linux中,隧道的實現主要基於兩個文件new_tunnel.c和ipip.c.本文參考    在Linux中,隧道的實現主要基於兩個文件new_tunnel.c和ipip.c    同時Linux定義了一種新的協議類型--IPIP(IPPROTO_IPIP),與上面所說封包類型類似。    基本思路   在Linux中IP Tunnel的實現也分為兩個部件:封裝部件和解封部件,分別司職發送和接收。但這兩個部分是在不同的層次以不同的方式實現的。封裝部件是在數據鏈路層以虛設備的方式實現。所有源代碼見    /usr/src/linux/drivers/net/new_tunnel.c       為實現封裝,Linux實現一個稱為tunl的網絡設備(類似loopback設備),此設備具有其他網絡設備共有的特征,對於使用此設備的上層應用來說,對這些網絡設備不加區分,調用及處理方法當然也完全一樣。      tunnel_init()和tunnel_xmit()是new_tunnel.c中的兩個主要過程。  tunnel_init()初始化與設備tunl相關的device結構。         而tunnel_xmit()在從tunl設備發送數據時被調用,tunl設備作為實現IP隧道技術的封裝部分,在此過程中完成對相應的數據報進行封裝所需的全部操作,形成IPIP類型的IP包,並重新轉發此數據包(ip_forward())。    解碼器在IP的上層實現,系統把它作為一個虛的傳輸層(實際上與傳輸層毫無關系),具體處理見文件    /usr/src/linux/net/ipv4/ipip.c。       我們知道,每一個IP數據包均交由ip_rcv函數處理,在進行一些必要的判斷後,ip_rcv對於發送給本機的數據包將交給上層處理程序。對於IPIP包來說,其處理函數是ipip_rcv(就如TCP包的處理函數是tcp_rcv一樣,IP層不加區分)。也就是說,當一個目的地址為本機的封包到達後,ip_rcv函數進行一些基本檢查並除去IP頭,然後交由ipip_rcv解封。ipip_rcv所做的工作就是去掉封包頭,還原數據包,然後把還原後的數據包放入相應的接收隊列(netif_rx())。    從以上IP Tunnel實現的思想來看,思路十分清晰,但由於IP Tunnel的特殊性,其實現的層次並不單純。實際上,它的封裝和解封部件不能簡單地象上面所說的那樣分層。tunl設備雖應算進鏈路層,但其發送程序中做了更多的工作,如制作IPIP頭及新的IP頭(這些一般認為是傳輸層或網絡層的工作),調用ip_forward轉發新包也不是一個網絡設備應當做的事。可以說,tunl借網絡設備之名,一把抓干了不少工作,真是‘高效’。而解封部件宏觀上看在網絡層之上,解出IPIP頭,恢復原數據包是它分內的事,但在它解出數據包(即原完整的協議數據包)後,它把這個包放入相應的協議接收隊列。這種事可不是一個上層協議干的,這是網絡設備中斷接收程序的義務。看到了,在這點上,它好象到了數據鏈路層。    三、為實現VPN的擴展   實際上Linux只為實現隧道機制提供了一個框架,圖二中的封包協議頭在Linux中被忽略了,也就是說,封包頭只含封包IP頭,其後緊跟原IP數據包。這樣的結構用於傳輸公開數據沒有關系,但對於一個VPN來說,安全保密是不可缺少的重要功能。我們希望通過隧道的數據可靠且不可竊取和冒充的,那麼,加密和認證就必不可少。為實現這一構想,設計以下封包協議頭:       0 4 8 16 24 31   +-----+-----+-----------+------------------------+   ver type hlen OldPacketLen    +-----------------------+------------------------+   DeviceID EncapID    +-----------------------+------------------------+   Flags CheckSum    +------------------------------------------------+   IPIP Options( If any )    +------------------------------------------------+   . padding    . .   +------------------------------------------------+           圖三、 IPIP頭設想圖    ver: 版本號,利於擴展   type: 用於建立不同目的的隧道(可能處理上有差別)   OldPacketLen: 進入隧道的原數據包長度   DeviceID: 對數據包進行封裝的設備標識   EncapID: 此封包的ID號   Flags: 標志位,共16位,初步定義如下:   0 保留   1 有否加密   2 有否做摘要   3 有否簽名   4 保留   5 有否傳送消息密鑰   6 消息密鑰有否加密   7 消息密鑰是否需保留   8-15 保留   CheckSum: 頭校驗   IPIP Options: 用來傳送一些必要的數據,比如消息密鑰、簽名等   格式:  +-------------------------------------+   類型 長度 數據 ...   +-------------------------------------+         好了,有了這個東西,我們就可以擴展Linux IP Tunnel為我們的VPN服務了。首先,改寫new_tunnel.c和ipip.c兩個文件,加入對IPIP頭的處理。      接著,我們要實現一種密鑰的管理和傳送機制。    當然,對稱密鑰是必需的,而對IP數據包加密要使用序列密碼。從全體考慮,    我們可以提出建立VPN的邏輯步驟;    1、准備工作:建網安裝系統完成配置等等   2、隧道的兩端分別向對方發送自己的公開密碼和設備號   3、如有必要,產生序列密碼,後加密簽名傳給對方   4、正常通信,----放心,你的數據已經很保險了。   在一個VPN的隧道中,一個封包的格式應如圖四所示。       / +-----------------+   封包IP頭    封包頭 +-----------------+   封包協議頭    +-----------------+   /    原協議頭    及    封包數據 原協議數據    . (密文) .   . .      +-----------------+             圖四. VPN封包結構    你的幾種使用方法   事情往往不能兩全其美,你在安全強度和通信速度上必須作出選擇,(不然你就需要在安全強度和Money的耗費中做選擇。)使用這樣的協議,根據你的需求不同,你可有不同的使用方法,下面列舉一些:    跨Internet的公司多個內部網之間進行通信,保密性並不重要直接使用原框架機制,無任何加密措施這樣速度快、效率高,公司也不用申請多個IP地址,方便可行   一般性的商業應用,具有保密要求利用事先產生的序列密碼,每次對原數據包加密安全度提高了,是一種十分實用的方法。只要強度足夠,一般很難破譯速度快   密碼不變的方式你認為不夠安全你可以自己實現一種密碼傳送方法,每隔一段時間更換一次密碼。其中一些握手關系需要完善,有興趣的歡迎探討。如果發展成熟,此法相信很有前途。   高度機密領域:敬請使用一次一密,並進行每次簽名。每次產生新密鑰和簽名十分費時,在目前我國Internet網絡的速度下幾乎不可行。但相信有此需要的部門也能夠設法提高其網絡帶寬,讓網絡狀況適合這種應用。另外,當然還可以就加密強度自身作出選擇,比如選擇128位,還是512位、1024位   四、待完善   主要牽涉到隧道的管理,在封包的傳送過程中如果出現錯誤是十分正常的,當一台路由器檢測到錯誤時,它會發送一個ICMP包給隧道的發送端,但遺憾的是ICMP返回的數據除了IP頭外,只含8個字節的上層協議信息。只憑這個難以對ICMP信息作出反應,因此,在隧道端保留一些狀態信息是必須的。這些信息主要包括:    隧道的另一端的可達性   隧道的擁塞狀況   隧道的MTU   同時所發送的封包信息也是需要保留的,舉例說,當一個路由不可達信息到來時,封包的發送者要能夠找出所封裝的數據來自何方,並發送相應的ICMP包。  




 



Copyright © Linux教程網 All Rights Reserved