Netfilter & iptables 原理

語言: CN / TW / HK

Netfilter 可能瞭解的人比較少,但是 iptables 用過 Linux 的都應該知道。本文主要介紹 Netfilter iptables 的原理,而下一篇將會介紹 Netfilter iptables 的實現。

什麼是 Netfilter

Netfilter 顧名思義就是網路過濾器,其主要功能就是對進出核心協議棧的資料包進行過濾或者修改,有名的 iptables 就是建立在 Netfilter 之上。

Netfilter 通過向核心協議棧中不同的位置註冊 鉤子函式(Hooks) 來對資料包進行過濾或者修改操作,這些位置稱為 掛載點 ,主要有 5 個: PRE_ROUTING LOCAL_IN FORWARD LOCAL_OUT POST_ROUTING ,如下圖所示:

這 5 個 掛載點 的意義如下:

  • PRE_ROUTING :路由前。資料包進入IP層後,但還沒有對資料包進行路由判定前。

  • LOCAL_IN :進入本地。對資料包進行路由判定後,如果資料包是傳送給本地的,在上送資料包給上層協議前。

  • FORWARD :轉發。對資料包進行路由判定後,如果資料包不是傳送給本地的,在轉發資料包出去前。

  • LOCAL_OUT :本地輸出。對於輸出的資料包,在沒有對資料包進行路由判定前。

  • POST_ROUTING :路由後。對於輸出的資料包,在對資料包進行路由判定後。

從上圖可以看出,路由判定是資料流向的關鍵點。

  • 第一個路由判定通過查詢輸入資料包 IP頭部 的目的 IP地址 是否為本機的 IP地址 ,如果是本機的 IP地址 ,說明資料是傳送給本機的。否則說明資料包是傳送給其他主機,經過本機只是進行中轉。

  • 第二個路由判定根據輸出資料包 IP頭部 的目的 IP地址 從路由表中查詢對應的路由資訊,然後根據路由資訊獲取下一跳主機(或閘道器)的 IP地址 ,然後進行資料傳輸。

通過向這些 掛載點 註冊鉤子函式,就能夠對處於不同階段的資料包進行過濾或者修改操作。由於鉤子函式能夠註冊多個,所以核心使用連結串列來儲存這些鉤子函式,如下圖所示:

如上圖所示,當資料包進入本地( LOCAL_IN 掛載點)時,就會相繼呼叫 ipt_hook fw_confirm 鉤子函式來處理資料包。另外,鉤子函式還有優先順序,優先順序越小越先執行。

正因為掛載點是通過連結串列來儲存鉤子函式,所以掛載點又被稱為 ,掛載點對應的鏈名稱如下所示:

  • LOCAL_IN 掛載點:又稱為 INPUT鏈

  • LOCAL_OUT 掛載點:又稱為 OUTPUT鏈

  • FORWARD 掛載點:又稱為 PORWARD鏈

  • PRE_ROUTING 掛載點:又稱為 PREROUTING鏈

  • POST_ROUTING 掛載點:又稱為 POSTOUTING鏈

什麼是 iptables

iptables 是建立在 Netfilter 之上的資料包過濾器,也就是說, iptables 通過向 Netfilter 的掛載點上註冊鉤子函式來實現對資料包過濾的。 iptables 的實現比較複雜,所以先要慢慢介紹一下它的一些基本概念。

iptables 這個名字可以看出,它一定包含了 這個概念。 是指一系列規則,可以看成是規則表。 iptables 通過把這些規則表掛載在 Netfilter 的不同鏈上,對進出核心協議棧的資料包進行過濾或者修改操作。

iptables 定義了 4 種表,每種表都有其不同的用途:

1. Filter表

Filter表 用於過濾資料包。是 iptables 的預設表,因此如果你配置規則時沒有指定表,那麼就預設使用 Filter表 ,它分別掛載在以下 3 個鏈上:

  • INPUT鏈

  • OUTPUT鏈

  • PORWARD鏈

2. NAT表

NAT表 用於對資料包的網路地址轉換(IP、埠),它分別掛載在以下 3 個鏈上:

  • PREROUTING鏈

  • POSTOUTING鏈

  • OUTPUT鏈

3. Mangle表

Mangle表 用於修改資料包的服務型別或TTL,並且可以配置路由實現QOS,它分別掛載在以下 5 個鏈上:

  • PREROUTING鏈

  • INPUT鏈

  • PORWARD鏈

  • OUTPUT鏈

  • POSTOUTING鏈

4. Raw表

Raw表 用於判定資料包是否被狀態跟蹤處理,它分別掛載在以下 2 個鏈上:

  • PREROUTING鏈

  • OUTPUT鏈

我們通過下圖來展示各個表所掛載的鏈:

上圖展示了,資料包從網路中進入到核心協議棧的過程中,要執行的 iptables 規則,如果在執行某條 iptables 規則失敗後,會直接把資料包丟棄,不會繼續執行下面的規則。

拿其中一個鏈來看,如下圖所示:

也就是說,當資料包從網路中進入到核心協議棧後,在路由判定前會分別執行 Raw表 Mangle表 NAT表 中的規則。如果在執行規則時,某一條規則拒絕了資料包,那麼資料包便會被丟棄,從而不會繼續執行下面的規則。

新增 iptables 規則

上面介紹了 iptables 的原理,下面主要介紹怎麼向 iptables 中新增規則。要向 iptables 中新增規則,可以使用 iptables 命令,其使用格式如下:

iptables [選項 引數] ...

可選的選項如下:

-t <表>:指定要操縱的表;
-A <鏈>:向規則鏈中新增條目;
-D <鏈>:從規則鏈中刪除條目;
-I <鏈>:向規則鏈中插入條目;
-R <鏈>:替換規則鏈中的條目;
-L:顯示規則鏈中已有的條目;
-F:清楚規則鏈中已有的條目;
-Z:清空規則鏈中的資料包計算器和位元組計數器;
-N:建立新的使用者自定義規則鏈;
-P:定義規則鏈中的預設目標;
-h:顯示幫助資訊;
-p:指定要匹配的資料包協議型別;
-s:指定要匹配的資料包源ip地址;
-j <動作>:指定要進行的動作行為;
-i <網路介面>:指定資料包進入本機的網路介面;
-o <網路介面>:指定資料包要離開本機所使用的網路介面。
--dport <埠>:匹配目標埠號。
--sport <埠>:匹配來源埠號。

iptables 規則的選項比較多,一般來說,一條 iptables 規則主要由四個部分組成,如下圖所示:

  • 第一部分可以通過 -t 選項來指定操作的表,如 filter nat mangle raw

  • 第二部分可以通過 -A -D -I -R 選項來指定操作的鏈,如 INPUT OUTPUT FORWARD PREROUTING POSTOUTING

  • 第三部分主要設定規則的匹配條件,如匹配源IP地址或者埠等。

  • 第四部分主要設定規則匹配成功後進行的動作,如接收或拒絕等。

第一和第二部分比較簡單,我們詳細介紹一下第三和第四部分。

匹配條件

匹配條件 分為 基本匹配條件 擴充套件匹配條件 ,基本匹配條件包括 源IP地址 目標IP地址 等,擴充套件匹配條件包括 源埠 目標埠 等。

處理動作

處理動作 是指當匹配條件成功後要進行的一系列操作過程,動作也可以分為 基本動作 擴充套件動作

此處列出一些常用的動作:

  • ACCEPT :允許資料包通過。

  • DROP :直接丟棄資料包,不給任何迴應資訊。

  • REJECT :拒絕資料包通過,必要時會給資料傳送端一個響應的資訊,客戶端剛請求就會收到拒絕的資訊。

  • SNAT :源IP地址轉換。

  • MASQUERADE :是SNAT的一種特殊形式,適用於動態IP上。

  • DNAT :目標IP地址轉換。

  • REDIRECT :在本機做埠對映。

  • LOG :在 /var/log/messages 檔案中記錄日誌資訊,然後將資料包傳遞給下一條規則,也就是說除了記錄以外不對資料包做任何其他操作,仍然讓下一條規則去匹配。

下面我們通過幾個簡單的例子來闡明 iptables 命令的使用:

1. 允許本地迴環介面(即執行本機訪問本機)

iptables -A INPUT -s 127.0.0.1 -d 127.0.0.1 -j ACCEPT  # 不指定表名時, 預設為filter表

2. 允許訪問80埠

iptables -A INPUT -p tcp --dport 80 -j ACCEPT

3. 禁止資料轉發

iptables -A FORWARD -j REJECT

4. 禁止IP段訪問

iptables -I INPUT -s 124.45.0.0/16 -j DROP   # 禁止IP段從123.45.0.1到123.45.255.254訪問

5. 檢視已新增的 iptables 規則

iptables -L -n -v

總結

本文主要介紹了 Netfilter iptables 的原理,並且還介紹了 iptables 命令的簡單使用。由於 iptables 是一個複雜的系統,所以本文不能完整的介紹其所有功能,有興趣的可以繼續查閱其他相關的資料。

下一篇文章我們將會介紹 Netfilter iptables 的實現過程。

技術交流群: