天天看點

iptables防火牆原理詳解1. netfilter與iptables2. Linux資料包路由原理3. iptables編寫規則

原文位址:http://seanlook.com/2014/02/23/iptables-understand/

Netfilter是由Rusty Russell提出的Linux 2.4核心防火牆架構,該架構既簡潔又靈活,可實作安全政策應用中的許多功能,如資料包過濾、資料包處理、位址僞裝、透明代理、動态網絡位址轉換(Network Address Translation,NAT),以及基于使用者及媒體通路控制(Media Access Control,MAC)位址的過濾和基于狀态的過濾、包速率限制等。Iptables/Netfilter的這些規則可以通過靈活組合,形成非常多的功能、涵蓋各個方面,這一切都得益于它的優秀設計思想。

Netfilter是Linux作業系統核心層内部的一個資料包處理子產品,它具有如下功能:

網絡位址轉換(Network Address Translate)

資料包内容修改

以及資料包過濾的防火牆功能

Netfilter 平台中制定了資料包的五個挂載點(Hook Point,我們可以了解為回調函數點,資料包到達這些位置的時候會主動調用我們的函數,使我們有機會能在資料包路由的時候改變它們的方向、内容),這5個挂載點分别是<code>PRE_ROUTING</code>、<code>INPUT</code>、<code>OUTPUT</code>、<code>FORWARD</code>、<code>POST_ROUTING</code>。

Netfilter 所設定的規則是存放在核心記憶體中的,而 iptables 是一個應用層的應用程式,它通過 Netfilter 放出的接口來對存放在核心記憶體中的 XXtables(Netfilter的配置表)進行修改。這個XXtables由表<code>tables</code>、鍊<code>chains</code>、規則<code>rules</code>組成,iptables在應用層負責修改這個規則檔案。類似的應用程式還有 firewalld 。

<a target="_blank" href="http://sean-images.qiniudn.com/iptables-netfilter.png"></a>

<a target="_blank"></a>

filter表

主要用于對資料包進行過濾,根據具體的規則決定是否放行該資料包(如DROP、ACCEPT、REJECT、LOG)。filter 表對應的核心子產品為iptable_filter,包含三個規則鍊:

<code>INPUT</code>鍊:INPUT針對那些目的地是本地的包

<code>FORWARD</code>鍊:FORWARD過濾所有不是本地産生的并且目的地不是本地(即本機隻是負責轉發)的包

<code>OUTPUT</code>鍊:OUTPUT是用來過濾所有本地生成的包

nat表

主要用于修改資料包的IP位址、端口号等資訊(網絡位址轉換,如SNAT、DNAT、MASQUERADE、REDIRECT)。屬于一個流的包(因為包

的大小限制導緻資料可能會被分成多個資料包)隻會經過這個表一次。如果第一個包被允許做NAT或Masqueraded,那麼餘下的包都會自動地被做相同的操作,也就是說,餘下的包不會再通過這個表。表對應的核心子產品為 iptable_nat,包含三個鍊:

<code>PREROUTING</code>鍊:作用是在包剛剛到達防火牆時改變它的目的位址

<code>OUTPUT</code>鍊:改變本地産生的包的目的位址

<code>POSTROUTING</code>鍊:在包就要離開防火牆之前改變其源位址

mangle表

主要用于修改資料包的TOS(Type Of Service,服務類型)、TTL(Time To Live,生存周期)指以及為資料包設定Mark标記,以實作Qos(Quality Of Service,服務品質)調整以及政策路由等應用,由于需要相應的路由裝置支援,是以應用并不廣泛。包含五個規則鍊——PREROUTING,POSTROUTING,INPUT,OUTPUT,FORWARD。

raw表

是自1.2.9以後版本的iptables新增的表,主要用于決定資料包是否被狀态跟蹤機制處理。在比對資料包時,raw表的規則要優先于其他表。包含兩條規則鍊——OUTPUT、PREROUTING

iptables中資料包和4種被跟蹤連接配接的4種不同狀态:

<code>NEW</code>:該包想要開始一個連接配接(重新連接配接或将連接配接重定向)

<code>RELATED</code>:該包是屬于某個已經建立的連接配接所建立的新連接配接。例如:FTP的資料傳輸連接配接就是控制連接配接所 RELATED出來的連接配接。<code>--icmp-type 0</code> ( ping 應答) 就是<code>--icmp-type 8</code> (ping 請求)所RELATED出來的。

<code>ESTABLISHED</code> :隻要發送并接到應答,一個資料連接配接從NEW變為ESTABLISHED,而且該狀态會繼續比對這個連接配接的後續資料包。

<code>INVALID</code>:資料包不能被識别屬于哪個連接配接或沒有任何狀态比如記憶體溢出,收到不知屬于哪個連接配接的ICMP錯誤資訊,一般應該DROP這個狀态的任何資料。

在處理各種資料包時,根據防火牆規則的不同介入時機,iptables供涉及5種預設規則鍊,從應用時間點的角度了解這些鍊:

<code>INPUT</code>鍊:當接收到防火牆本機位址的資料包(入站)時,應用此鍊中的規則。

<code>OUTPUT</code>鍊:當防火牆本機向外發送資料包(出站)時,應用此鍊中的規則。

<code>FORWARD</code>鍊:當接收到需要通過防火牆發送給其他位址的資料包(轉發)時,應用此鍊中的規則。

<code>PREROUTING</code>鍊:在對資料包作路由選擇之前,應用此鍊中的規則,如DNAT。

<code>POSTROUTING</code>鍊:在對資料包作路由選擇之後,應用此鍊中的規則,如SNAT。

1

2

3

4

5

6

7

8

9

10

--&gt;PREROUTING--&gt;[ROUTE]--&gt;FORWARD--&gt;POSTROUTING--&gt;

mangle | mangle ^ mangle

nat | filter | nat

| |

v |

INPUT OUTPUT

| mangle ^ mangle

| filter | nat

v ------&gt;local-------&gt;| filter

其中中INPUT、OUTPUT鍊更多的應用在“主機防火牆”中,即主要針對伺服器本機進出資料的安全控制;而FORWARD、PREROUTING、POSTROUTING鍊更多的應用在“網絡防火牆”中,特别是防火牆伺服器作為網關使用時的情況。

防火牆處理資料包的方式(規則):

<code>ACCEPT</code>:允許資料包通過

<code>DROP</code>:直接丢棄資料包,不給任何回應資訊

<code>REJECT</code>:拒絕資料包通過,必要時會給資料發送端一個響應的資訊。

<code>SNAT</code>:源位址轉換。在進入路由層面的route之前,重新改寫源位址,目标位址不變,并在本機建立NAT表項,當資料傳回時,根據NAT表将目的位址資料改寫為資料發送出去時候的源位址,并發送給主機。解決内網使用者用同一個公網位址上網的問題。

<code>MASQUERADE</code>,是SNAT的一種特殊形式,适用于像adsl這種臨時會變的ip上

<code>DNAT</code>:目标位址轉換。和SNAT相反,IP包經過route之後、出本地的網絡棧之前,重新修改目标位址,源位址不變,在本機建立NAT表項,當資料傳回時,根據NAT表将源位址修改為資料發送過來時的目标位址,并發給遠端主機。可以隐藏後端伺服器的真實位址。

<code>REDIRECT</code>:是DNAT的一種特殊形式,将網絡包轉發到本地host上(不管IP頭部指定的目标位址是啥),友善在本機做端口轉發。

<code>LOG</code>:在/var/log/messages檔案中記錄日志資訊,然後将資料包傳遞給下一條規則

除去最後一個<code>LOG</code>,前3條規則比對資料包後,該資料包不會再往下繼續比對了,是以編寫的規則順序極其關鍵。

我們已經知道了Netfilter和Iptables的架構和作用,并且學習了控制Netfilter行為的Xtables表的結構,那麼這個Xtables表是怎麼在核心協定棧的資料包路由中起作用的呢?

網口資料包由底層的網卡NIC接收,通過資料鍊路層的解包之後(去除資料鍊路幀頭),就進入了TCP/IP協定棧(本質就是一個處理網絡資料包的核心驅動)和Netfilter混合的資料包處理流程中了。資料包的接收、處理、轉發流程構成一個有限狀态向量機,經過一些列的核心處理函數、以及Netfilter Hook點,最後被轉發、或者本次上層的應用程式消化掉。是時候看這張圖了:

<a target="_blank" href="http://sean-images.qiniudn.com/iptables-routing.jpg"></a>

從上圖中,我們可以總結出以下規律:

當一個資料包進入網卡時,資料包首先進入PREROUTING鍊,在PREROUTING鍊中我們有機會修改資料包的DestIP(目的IP),然後核心的”路由子產品”根據”資料包目的IP”以及”核心中的路由表”判斷是否需要轉送出去(注意,這個時候資料包的DestIP有可能已經被我們修改過了)

如果資料包就是進入本機的(即資料包的目的IP是本機的網口IP),資料包就會沿着圖向下移動,到達INPUT鍊。資料包到達INPUT鍊後,任何程序都會-收到它

本機上運作的程式也可以發送資料包,這些資料包經過OUTPUT鍊,然後到達POSTROTING鍊輸出(注意,這個時候資料包的SrcIP有可能已經被我們修改過了)

如果資料包是要轉發出去的(即目的IP位址不再目前子網中),且核心允許轉發,資料包就會向右移動,經過FORWARD鍊,然後到達POSTROUTING鍊輸出(選擇對應子網的網口發送出去)

我們在寫Iptables規則的時候,要時刻牢記這張路由次序圖,根據所在Hook點的不同,靈活配置規則。

指令格式:

<a target="_blank" href="http://sean-images.qiniudn.com/iptables-cli.png"></a>

<code>[-t 表名]</code>:該規則所操作的哪個表,可以使用filter、nat等,如果沒有指定則預設為filter

<code>-A</code>:新增一條規則,到該規則鍊清單的最後一行

<code>-I</code>:插入一條規則,原本該位置上的規則會往後順序移動,沒有指定編号則為1

<code>-D</code>:從規則鍊中删除一條規則,要麼輸入完整的規則,或者指定規則編号加以删除

<code>-R</code>:替換某條規則,規則替換不會改變順序,而且必須指定編号。

<code>-P</code>:設定某條規則鍊的預設動作

<code>-nL</code>:<code>-L</code>、<code>-n</code>,檢視目前運作的防火牆規則清單

<code>chain名</code>:指定規則表的哪個鍊,如INPUT、OUPUT、FORWARD、PREROUTING等

<code>[規則編号]</code>:插入、删除、替換規則時用,<code>--line-numbers</code>顯示号碼

<code>[-i|o 網卡名稱]</code>:i是指定資料包從哪塊網卡進入,o是指定資料包從哪塊網卡輸出

<code>[-p 協定類型]</code>:可以指定規則應用的協定,包含tcp、udp和icmp等

<code>[-s 源IP位址]</code>:源主機的IP位址或子網位址

<code>[--sport 源端口号]</code>:資料包的IP的源端口号

<code>[-d目标IP位址]</code>:目标主機的IP位址或子網位址

<code>[--dport目标端口号]</code>:資料包的IP的目标端口号

<code>-m</code>:extend matches,這個選項用于提供更多的比對參數,如:

-m state —state ESTABLISHED,RELATED

-m tcp —dport 22

-m multiport —dports 80,8080

-m icmp —icmp-type 8

<code>&lt;-j 動作&gt;</code>:處理資料包的動作,包括ACCEPT、DROP、REJECT等

參考

2小時玩轉iptables企業版.ppt (網上可下)

<a target="_blank" href="http://www.netfilter.org/documentation/index.html">netfilter/iptables documentation</a>

繼續閱讀