伺服器架設篇 - RedHat 9

第十一章、簡易 Firewall 架設

利用簡單的 iptables 規則,配合 TCP_Wrappers 來進行防火牆建置呢!

最近更新時間: 2003/08/25

本文資料主要針對 RedHat 9 的系統進行說明,要注意的是,RedHat 9 與 Red Hat Enterprise Linux (RHEL) 是完全不同的東西!RedHat 9 在 2003 年推出,在 2004 年就不再維護了!這部份網站更新到 2005 年,也沒有再維護過! 因此,建議您前往本站查詢最新版本的 Linux distribution 文章來閱讀,比較不會浪費時間。那為何還需要編輯 RedHat 9 的資料呢? 鳥哥只想要做個自己曾經撰寫過的文件內容保存而已囉! ^_^!最新文章請前往鳥站首頁查閱囉!
在談完了基本的網路安全觀念之後,這個章節主要就要針對『防火牆』來進行介紹了!目前的防火牆機制主要是以 Linux Kernel 2.4 版的 iptables 為主的,而 iptables 可以使用指令來下達,也可以透過編寫 shell script 來進行指令的整合。鳥哥本人比較習慣使用 scripts 來進行 iptables 的機制規劃呢!除了 iptables 之外,事實上,比較簡單的還有 TCP Wrappers 這個玩意兒,他則主要是針對某些服務來進行管理的吶!本章的內容主要就是在介紹這兩個重要的防火牆軟體了!

防火牆:

    網路安全除了隨時注意套件的漏洞,以及網路上的安全通報之外,您最好能夠依據自己的環境來訂定防火牆機制,這樣對於您的網路環境,會比較有保障一點喔!那麼什麼是防火牆呢?說穿了,其實防火牆就是在管制進入到我們網域內的主機(或者可以說是網域)的資料封包的一種機制,例如我們在前一章節認識網路安全當中提到的 iptables 就是一種防火牆機制了。當然了,更廣義的來說,只要能夠分析與過濾進入我們管理之網域的封包資料,就可以稱為防火牆,所以這個防火牆又可以分為硬體防火牆與本機的軟體防火牆啊!硬體防火牆也就是一些廠商設計好的硬體,裡面的系統軟體已經設定好了封包資料的過濾機制,因為他幾乎單純就是用來進行網路安全管理的,所以稱為硬體防火牆。至於軟體防火牆呢?那就是我們這個章節要來談論的啊!軟體防火牆本身就是在保護系統網路安全的一套軟體(或稱為機制),例如 iptables 與 TCP Wrappers 都可以稱為軟體防火牆。無論怎麼分,反正防火牆就是用來保護我們網路安全的咚咚就對啦!呵呵!我們這個章節主要在介紹 Linux 系統本身提供的軟體防火牆的功能,那就是 iptables 與 TCP Wrappers 喔!
     

    為何需要防火牆
     
    因為不希望常常在網路上面看到『唉呀!我依據某某網頁的資訊架設了一個 Linux 主機,為什麼過了一個星期之後,以 root 的密碼無法登入我的主機?』,還有一種說法『唉呦!我的 Linux 主機為什麼無法查詢登錄檔了?為什麼被 ISP 警告說我的 mail server 被列為黑名單了,為什麼被偵測到說我有攻擊人家?我都沒有做壞事呀!?』呵呵!很傷腦筋對不對~沒錯啦!網路安全果然是很麻煩!又得要天天照顧他,又得要隨時更新到最新版的套件!唉~麻煩吶!但是網路安全卻又是一個網管人員的基本知識要求,一個具有良好的防火牆措施的主機,可以讓一個網管人員過的更開心呀!
     
    要曉得的是,我們是一般的小家庭,所以主機即使被 Cracker 入侵,只要在對方利用我們的 IP 幹壞事之前就將主機給他關掉的話,還能稍微保護一下自己,但是若您是一個大型企業的主機,而且還提供有關信用卡啦,個人用戶的資訊啦等等的訊息時,那麼可不能說關機就關機的,這個時候怎麼辦?如果您沒有設定緊急應變手則,沒有良好的登錄檔案分析習慣,也沒有即時回報系統在幫您偵測您的主機,嘿嘿!那總損失除了金額之外,還包括公司的信譽,那可是很可怕的呦!由國外的分析可以發現,幾乎主機被入侵之後,損失的除了金錢之外,還有主機維護的時間、軟硬體重新設定的費用等等,相當可觀的一筆費用呀~
     
    所以啦!架設一部具有較為安全的主機,對我們來說,也是相當重要的,怎麼說呢?別以為我們是一般的 ADSL 撥接的小站就無所謂呦!等到真的被入侵之後,然後您的主機被利用來作壞事,然後利用您的主機作壞事的那個人又將他的登錄資訊殺掉,讓人家找不到他,嘿嘿!到時候吃官司的可會是您!別以為 ADSL 撥接制的頻寬不足呢!要使用您的主機來做事那也不需要多大的頻寬,只要能連上 Internet ,只要能再藉由您的主機向外面擴散,嘿嘿!再怎麼小的頻寬都有人會利用的!『千萬不要小看系統的安全性~
     

    防火牆的主要類別
     
    除了以軟體及硬體作為防火牆的分類之外,基本上,我們也可以使用防火牆對於封包的抵擋機制來進行分類。主要可以分為兩大類,分別是代理伺服器 (Proxy) 以及 IP Filter 。在代理伺服器方面,由名稱我們就可以知道,代理伺服器僅是代理 Client 端去向 Internet 要求資料,所以呢, Proxy 其實已經將可代理的協定限制的很少很少,並且由於內部與外部電腦的並不能直接互通,所以可以達到良好的保護效果;另一種則是上面提到的 IP fileter 啦!利用封包過濾的方式來達到防火牆的目的!
     
    • Proxy :

    • 這是屬於網路『應用層』的咚咚了,這個 Proxy ( 代理伺服器 ) 基本上就是一種『服務』喔!他的功能可以如下圖來表示:
       

      圖一、Proxy 主機的示意圖
       
      當 Client 有要求的時候, Proxy Server 會幫 Client 去外面捉取資料,然後再將資料丟回給 Client 端!請注意,此時真正出去 Internet 的,其實是 Proxy Server ,而不是 Client 端呦!( 這個跟 NAT 服務並不太一樣,會在後續的 NAT主機設定時再提到。) 由於 Client 端並不是直接出去,加上 Proxy Server 一般僅開放 80 及 21, 20 port 而已,因此可以較為安全!相對的,對於 Client 端的限制自然就較多了!更詳細的 Proxy 說明我們會在後續的代理伺服器章節中提到。
       
    • IP fileter :

    • 直接以 IP filter 來進行封包的過濾!這個時候會由 TCP 的 header 分析起來,再決定是否可以讓該 TCP 封包進入主機。因為是分析 TCP/IP 的封包,所以使用到的網路協定是比較底層的資訊喔,因為底層的資訊相當的複雜,包括了網路卡的硬體位址(MAC)、軟體位址、TCP, UDP, ICMP 等封包的 Header 訊息、TCP 封包的三向交握觀念等等,所以 IP Filter 可以達成的功能可就大的多了!另外,一般我們談到的 Linux 上的防火牆大多指的就是 iptables 這個 IP Filter 機制了,他利用一些封包過濾的規則設定,來定義出什麼資料可以接收,什麼資料需要剔除,以達到保護主機的目的喔!
     
    在這個章節中,我們先不談 Proxy 這個東西,僅來分析一下最基礎的兩個防火牆機制,一個是 iptables ,另一個則是 TCP_Wrappers !
     

    防火牆的一般線路佈線與抵擋技巧
     
    由前面的說明當中,您應該可以瞭解到一件事,那就是防火牆除了可以『保護防火牆機制(iptables)本身所在的那部主機』之外,還可以『保護防火牆後面的主機或 PC』。呵呵!沒錯!防火牆的功能可是很大的喔!除了可以幫助我們抵禦外來的主動連線之外,也可以幫我們控管網路流量,並且,在簡單的區域網路規劃中, Firewall 搭配 Router ( 就是 NAT 主機的架構 ) 也是相當常見的一種規劃!這種規劃對於內部私有網域的安全也有一定程度的保護作用呢!底下我們稍微談一談目前常見的防火牆規劃:
     
    • 單一 Linux 主機兼任防火牆功能:

    • 我們的網域裡面僅有一部 Linux 主機,該主機負責我們整個 LAN 裡面所有個人電腦對外的連線,所以他也是我們 LAN 裡面的 Router 。該防火牆一般會有兩個介面,一個對內一個對外,同時,您也可以直接在 Linux 防火牆上面架設網站,這是目前針對小型的企業所常見的網路配置狀態。在這樣的配置狀態中,所有的 PC 都會經過 Firewall 的封包過濾之後,才能將資料封包送出或者是收受,而如果 Internet 上面出現問題,您只要管理 Firewall 那部主機,就可以很輕易的將來自 Internet 的不良封包抵擋掉喔!管理一部防火牆就能夠造福整個 LAN 裡面的 PC,很划算吧! ^_^!而且,在 Firewall 上面可以同時架設 Proxy ,用來控制 Client 端的 WWW 連線狀態,呵呵!控制的更詳盡吶!(註:也可以加設網路流量監控軟體,例如 MRTG 來分析頻寬喔!)基本上,這樣的配置好處為:
      • 安全維護在內部可以開放的權限較大!
      • 安全機制的設定可以針對 Linux 主機來維護即可!
      • 對外只看的到 Linux 主機,所以對於內部可以達到有效的安全防護!
       

      圖二、單一 Linux 防火牆主機
       
    • 單一 Linux 防火牆,但 LAN 內另設防火牆:

    • 一般來說,我們的防火牆對於 LAN 的防備都不會設定的很嚴格,因為是我們自己的 LAN 嘛!所以是信任網域之一囉!不過,最常聽到的入侵方法也是使用這樣的一個信任漏洞!因為您不能保證所有使用企業內部電腦的使用者都是公司的員工,也無法保證您的員工不會『搞破壞!』呵呵!所以,如果您有特別重要的部門需要更安全的保護網路環境,那麼將 LAN 裡面再加設一個防火牆,將安全等級分類,那麼將會讓您的重要資料獲得更佳的保護喔!
       

      圖三、LAN 裡面加設防火牆的配置
       
    • 在防火牆後端的主機設定:

    • 還有一種更有趣的設定,那就是將提供網路服務的伺服器放在防火牆後面,這有什麼好處呢?如下圖四所示,Web, Mail 與 FTP 都是透過防火牆連到 Internet 上面去,所以,底下這四部主機在 Internet 上面的 Public IP 都是一樣的!(這個觀念我們會在 NAT 主機的時候再次的強調)只是透過防火牆的封包分析後,將 WWW 的要求封包轉送到 Web 主機,將 Mail 送給 Mail Server 去處理而已(透過 port 的不同來轉遞)。好了,因為四部主機在 Internet 上面看到的 IP 都相同,但是事實上卻是四部不同的主機,而當有攻擊者想要入侵您的 FTP 主機好了,他使用各種分析方法去進攻的主機,其實是『防火牆』那一部,攻擊者想要攻擊您內部的主機,除非他能夠成功的搞定您的防火牆,否則就很難入侵您的內部主機呢!不過,這種架構下所進行的設定就得包含 port 的轉遞,對於新手來說,設定上有一定的難度,鳥哥個人不太建議新手這麼做,還是等以後有經驗之後再來玩這種架構吧!
       

      圖四、架設在防火牆後端的主機伺服器
     
    上面就是目前比較常見的幾種防火牆的配置方法。那麼如何進行封包的抵擋設定呢?再來複習一下一個資料封包的內容,如下圖所示:
     

    圖五、一般資料封包所含有的基礎資訊
     
    由於防火牆可以分析網路上傳送過來的資料封包,並取得分析該資料封包的表頭資料,亦即可以分析上面圖示中的目的地與來源地的 IP, port, 是否主動連線等等的其他資訊!所以經由分析這些資料後,我們不難發現抵擋的方法可以有幾個動作:
     
    • 拒絕讓封包進入主機的某些 port

    • 這個應該不難瞭解吧!例如您的 port 20-21 這個 FTP 相關的 port ,您只要開放給內部網路的話,所以不對 Internet 開放,那麼當 Internet 來的封包想要進入您的 port 20-21 的話,就可以將該資料封包丟掉!因為我們可以分析的到該封包所帶有的 port 號碼呀!
       
    • 拒絕讓某些來源 IP 的封包進入

    • 例如您已經發現某個 IP 主要都是來自攻擊行為的主機,那麼只要來自該 IP 的資料封包,就將他丟棄!這樣也可以達到基礎的安全呦!
       
    • 拒絕讓帶有某些特殊旗標( flag )的封包進入

    • 最常拒絕的就是帶有 SYN 的主動連線的旗標了!只要一經發現,嘿嘿!您就可以將該封包丟棄呀!
       
    • 分析硬體位址(MAC)來提供服務:

    • 如果您的區域網路裡面有比較搗蛋的但是又具有比較高強的網路功力的高手時,如果您使用 IP 來抵擋他使用網路的權限,而他卻懂得反正換一個 IP 就好了,都在同一個網域內嘛!同樣還是在搞破壞~怎麼辦?!沒關係,我們可以鎖死他的網路卡硬體位址啊!因為 MAC 是銲在網路卡上面的,所以您只要分析到該使用者所使用的 MAC 之後,可以利用防火牆將該 MAC 鎖住,呵呵!除非他能夠一換再換他的網路卡來取得新的 MAC,否則換 IP 是沒有用的啦!
       
    當然還有很多的技巧,這裡我們就不多提了!底下好好的來談一談怎樣建置一個簡單的 firewall 主機吧!此外,我預計使用兩層防火牆,分別是 iptables 與 TCP_Wrappers ,其中,兩者的相關性為:
     

    圖六、封包進入主機的流程
     
    也就是說,資料封包會先經過 iptables 才會經過 TCP_Wrappers 的作用!

    防火牆的使用限制
     
    什麼?!設定防火牆之後還不安全啊?!那當然啦!誰說設定了防火牆之後您的系統就一定安全?!那可不一定啊!防火牆雖然可以防止不受歡迎的封包進入我們的網路當中,不過,某些情況下,他並不能保證我們的網路一定就很安全。舉幾個例子來談一談:
     
    • 防火牆並不能很有效的抵擋病毒或木馬程式:假設您已經開放了 WWW 的服務,那麼您的 WWW 主機上面,防火牆一定得要將 WWW 服務的 port 開放給 Client 端登入才行吧!否則您的 WWW 主機設定了等於沒有用對吧!也就是說,只要進入您的主機的封包是要求 WWW 資料的,就可以通過您的防火牆。那好了,『萬一您的 WWW 伺服器軟體有漏洞,或者本身向您要求 WWW 服務的該封包就是病毒在偵測您的系統』時,您的防火牆可是一點辦法也沒有啊!因為本來設定的規則就是會讓他通過啊!尤其前一兩年的 Nimda 病毒就是攻擊 WWW 主機的,他是透過入侵 WWW 主機的 80 port ,呵呵!所以說,防火牆對於病毒並不能很有效就是了。

    •  
    • 防火牆對於來自內部 LAN 的攻擊較無承受力:一般來說,我們對於 LAN 裡面的主機都沒有什麼防火牆的設定,因為是我們自己的 LAN 啊,所以當然就設定為信任網域了!不過, LAN 裡面總是可能有些網路小白啊,雖然他們不是故意要搞破壞,但是他們就是不懂嘛!所以就亂用網路了。這個時候就很糟糕,因為 Firewall 對於內部的規則設定通常比較少,所以就容易造成內部員工對於網路誤用或濫用的情況。為了避免這種情況的發生,呵呵!身為系統管理員的您
     
    所以啦,在您的 Linux 主機實地上網之前,還是得先:
     
    • 關閉幾個不安全的服務;
    • 升級幾個可能有問題的套件;
    • 架設好最起碼的安全防護--防火牆--
     
    其他相關的訊息請到 認識網路安全--主機防護計畫 裡面去看一看怎麼增加自身的安全吧!

Linux 的封包過濾機制

    終於可以談到主題了!^_^!底下我們就要來談一談,什麼是 Linux 的封包過濾機制!
     

    Linux 核心版本與防火牆機制
     
    Linux 在封包過濾機制是慢慢演進形成目前的 iptables 的,在核心不為 2.4 的時代,使用的防火牆機制是不同的!
     
    • Version 2.0:使用 ipfwadm 這個防火牆機制;
    • Version 2.2:使用的是 ipchains 這個防火牆機制;
    • Version 2.4:主要是使用 iptables 這個防火牆機制,而為了相容於 ipchains ,因此在 Version 2.4 版本中,同時將 ipchains 編譯成為模組,好讓使用者仍然可以使用來自 2.2 版的 ipchains 的防火牆規劃。
     
    由上面的說明中,可以知道 Linux 上面的防火牆機制是依據不同核心而變的,而因為目前我們看到的新的 Linux 版本之核心都是 2.4.xx 版本,所以使用的防火牆機制當然就是以 iptables 為準了。此外,還要特別留意的是,核心為 2.4 版本的 Linux 同時支援 ipchains 這個在核心 2.2 版的防火牆機制,然而不幸的是,『iptables 與 ipchains 兩者不能同時執行!』,所以如果您發現您的系統已經在執行 ipchains 了,那麼就得將 ipchains 這個模組移除之後,才能夠使用 iptables ,反之亦然喔!
     
    無論如何,在核心為 2.4.xx 的系統上面,還是比較建議使用 iptables ,因為 iptables 功能比較強大而且在規則設定上面比較簡單,此外,還具有其他支援的外掛模組,而雖然 2.4 同時支援 ipchains ,不過在 2.2 上面支援 ipchains 的模組都不再 2.4 上面存在了,所以,當然選擇功能更強的 iptables 咯。那麼如何知道我的 Linux 核心版本?呵呵!使用 uname 這個指令就對了!
     

    iptables 的表格與封包進入的流程
     
    只要是防火牆機制,通常都是以『針對封包的分析規則來規範每種封包的通過與否,以及應該進行的動作』,同樣的道理,iptables 的工作方向,必須要依規則的順序來分析封包,舉個簡單的例子,假設我有十條防火牆規則好了,那麼當 Internet 來了一個封包想要進入我的主機,那麼防火牆會怎麼分析這個封包呢?我們以底下的圖示來說明好了:
     

    圖七、封包過濾的規則動作
     
    上面圖七的 Rule 是規則的意思,『這些規則是有順序的』,至於 Action 則是動作的意思,通常針對封包的動作有 ACCEPT/DROP (接受/丟棄) 兩種動作。什麼是『規則的順序呢』?讓我們看一下上面的例子,當 TCP 封包通過了 Rule 1 ,剛好符合 Rule 1 的規定,那麼 TCP 封包就會進行 Action 1 ,而不會理會 Rule 2 以後的規則了!而如果 TCP 不符合 Rule 1 的規定,那麼就會進入第二條規則 (Rule 2) 來檢查,....一直到 Rule 10 的時候,該 TCP 封包都沒有符合的規則可以進行,那麼此時就會以『預設動作 ( 封包政策, Policy )』來讓 TCP 封包進行通過與否的動作。所以啦,當您的規則的順序排列錯誤時,就會產生很大的困擾!怎麼說呢?我們再舉個例子好了,假設您的 Linux 主機提供了 WWW 的服務,那麼自然就要針對 port 80 來啟用通過的封包規則,但是您發現 IP 來源為 192.168.100.100 老是惡意的嘗試入侵您的系統,所以您想要將該 IP 拒絕往來,最後,所有的非 WWW 的封包都給他丟棄,就這三個規則來說,您要如何設定防火牆檢驗順序呢?
     
    1. Rule 1 先抵擋 192.168.100.100 ;
    2. Rule 2 再讓要求 WWW 服務的封包通過;
    3. Rule 3 將所有的封包丟棄。
     
    這樣的排列順序就能符合您的需求,不過,萬一您的順序排錯了,變成:
     
    1. Rule 1 先讓要求 WWW 服務的封包通過;
    2. Rule 2 再抵擋 192.168.100.100 ;
    3. Rule 3 將所有的封包丟棄。
     
    此時,那個 192.168.100.100 『可以使用您的 WWW 服務』喔!因為只要他對您的主機送出 WWW 要求封包,就可以使用您的 WWW 主機功能了,因為您的規則順序定義第一條就會讓他通過,而不去考慮第二條規則!這樣可以理解規則順序的意義了嗎?!現在再來想一想,如果 Rule 1 變成了『將所有的封包丟棄』,Rule 2 才設定『WWW 服務封包通過』,請問,我的 client 可以使用我的 WWW 服務嗎?!呵呵!答案是『否~』想通了嗎?! ^_^
     
    事實上,圖七就是 iptables 的『一張表格裡面的一條鏈(chains)』,您可以想像一下, iptables 的規則都是寫在『表格, table』裡面的,而每個表格又依據封包的行進路線,而可大略分為三條鏈:『進入、輸出、轉遞』等。在 iptables 裡面有兩個經常用到的內建表格 (build-in table) ,分別是針對主機的 filter 以及針對防火牆後端的主機設定的 nat 兩個,這兩個表格又分別具有三條鏈,分別是:
     
    • filter:主要跟 Linux 本機有關,這個是預設的 table 喔!
      • INPUT:主要與封包想要進入我們 Linux 本機有關;
      • OUTPUT:主要與我們 Linux 本機所要送出的封包有關;
      • FORWARD:這個咚咚與 Linux 本機比較沒有關係,他可以封包『轉遞』到後端的電腦中,與 nat 這個 table 相關性很高。
       
    • nat:主要跟 NAT 主機的設定有關
      • PREROUTING:在進行路由判斷之前所要進行的規則
      • POSTROUTING:在進行路由判斷之後所要進行的規則
      • OUTPUT:與發送出去的封包有關
     
    所以說,如圖七的規則訂定至少就會有六組吶!那麼這六條鏈有什麼相關性呢?這得需要由封包的行進路線來說明:
     
    • 封包想要進入本機:

    • 當有封包想要進入我們 Linux 本機時,該封包會經過兩條鏈,分別得先通過 nat 的 PREROUTING 鏈,再通過 filter 的 INPUT 鏈才能進入本機使用我們本機的資源。事實上,如果僅考慮本機的話,那麼 nat 的 PREROUTING 預設政策就給他通過,僅考慮 filter 的 INPUT 即可
       

      圖八、進入本機封包所需通過的 table 與 chains
       
    • 封包想要進入本機後端的電腦:

    • 當封包想要進入本機後端的電腦時,也就是說,其實該資料封包不是要使用本機的資源,所以如同底下的圖九所示,封包並不會進入本機喔!而且,此時封包的流通與 nat 的 PREROUTING, POSTROUTING 以及 filter 的 FORWARD 是有關係的!這點要特別特別注意啊!
       

      圖九、進入本機後端的電腦時,封包所需通過的 table 與 chains
    • 由本機發送的封包:

    • 呵呵!iptables 不只可以管制由外而內的封包,同時也可以管制由內而外的訊息呢!當封包由本機傳送出去時,會通過 nat 與 filter 的 OUTPUT 鏈,還會有 POSTROUTING 的檢查喔!事實上,如果不考慮我們本機後端的電腦,那麼僅要使用 filter 的 OUTPUT 鏈即可
       

      圖十、本機發送出的封包所需通過的 table 與 chains
     
    一般來說,如果您的防火牆是設在 Linux 本機上面,並且您的 Linux 本機並沒有啟用 NAT 的功能,那麼您只需要考慮 filter 這個 table 的 INPUT 與 OUTPUT 這兩條鏈就可以了!簡化的很多喔!但是如果您的 Linux 主機還有考慮到 NAT 的功能,那麼 nat table 的 PREROUTING 與 POSTROUTING 還有 filter table 的 FORWARD 就得需要好好的設定一番了!底下我們就來談一談,那麼要怎麼設定 iptables 的規則語法吧!
     

    iptables 的語法
     
    事實上, iptables 就是一個可以載入的模組,在開始進行 iptables 的設定之前,先確認一下,由於 ipchains 與 iptables 是不能同時存在的,所以先檢查一下 ipchains 是否不小心被載入到系統當中了呢?
     
    [root@test root]# lsmod
    # 若有發現 ipchains 的字樣,表示系統不小心載入了 ipchains 了,請使用:
    [root@test root]# rmmod ipchains
    # 這樣就能夠移除 ipchains 了!然後載入 iptables 吧!
    [root@test root]# modprobe ip_tables
     
    上頭的 ip_tables 就是 iptables 的模組了!載入之後,我們就可以使用 iptables 的語法了!因為 iptables 的語法相當的多,所以底下我將這些語法分成規則清除、定義政策以及新增與插入規則三部分來說明:(註:防火牆的設定是相當重要的工作,另外,他的設定過程當中常常會有『測試』的意味在裡面,因為是測試,有的時候我們會不小心『將自己的連線封包擋住了!』,導致無法連線,所以,『設定防火牆的時候,盡量在本機前面設定,不要利用遠端連線服務來設定,否則很容易產生自己將自己擋掉的重大問題!』)
     

      清除規則與觀察規則
       
      iptables 在一開始的時候,應該是沒有規則的,不過,可能因為您在安裝的時候就有選擇系統自動幫您建立防火牆機制,此時系統就會有預設的防火牆規則了!好了,無論如何,我們先來看看目前本機的防火牆規則是如何吧!?
       
      [root@test root]# iptables [-t tables] [-L] [-n]
      參數說明:
      -t:後面接 iptables 的 table ,例如 nat 或 filter ,如果沒有 -t table 
        的話,那麼預設就是 -t filter 這個 table 喔!
      -L:列出目前的 table 的規則
      -n:不進行 IP 與 HOSTNAME 的轉換,螢幕顯示訊息的速度會快很多!
      範例:
       
      [root@test root]# iptables -L -n
      Chain INPUT (policy ACCEPT)
      target     prot opt source               destination
       
      Chain FORWARD (policy ACCEPT)
      target     prot opt source               destination
       
      Chain OUTPUT (policy ACCEPT)
      target     prot opt source               destination
       
      # 仔細看到上面,因為沒有加上 -t 的參數,所以預設就是 filter 這個表格,
      # 在這個表格當中有三條鏈,分別是 INPUT, OUTPUT 與 FORWARD ,而且因為
      # 沒有規則,所以規則裡面都是空的!同時注意一下,在每個 chain 的後面 () 
      # 裡面,會發現有 policy 對吧!那就是『預設動作(政策)』咯!以上面來看,
      # 雖然我們啟動了 iptables ,但是我們沒有設定規則,然後政策又是 ACCEPT,
      # 所以『任何封包都會接受』的意思喔!
       
      [root@test root]# iptables -t nat -L -n
      Chain PREROUTING (policy ACCEPT)
      target     prot opt source               destination

      Chain POSTROUTING (policy ACCEPT)
      target     prot opt source               destination

      Chain OUTPUT (policy ACCEPT)
      target     prot opt source               destination
       
      # 與 filter 類似的, nat 這個表格裡面有的則是 PREROUTING, POSTROUTING
      # 以及 OUTPUT 三條鏈啊!

       
      至於要清除規則的話,就得要這樣下達指令了!
       
      [root@test root]# /sbin/iptables [-t tables] [-FXZ]
      參數說明:
      -F :清除所有的已訂定的規則;
      -X :殺掉所有使用者建立的 chain (應該說的是 tables )囉;
      -Z :將所有的 chain 的計數與流量統計都歸零
      範例:
      [root@test root]# /sbin/iptables -F
      [root@test root]# /sbin/iptables -X
      [root@test root]# /sbin/iptables -Z
      [root@test root]# /sbin/iptables -t nat -F 
      # 請注意,如果在遠端連線的時候,『這三個指令必須要用 scripts 來連續執行』,
      # 不然肯定『會讓您自己被主機擋在門外!』
       
      一般來說,我們在重新定義防火牆的時候,都會先將規則給他清除掉。還記得我們前面談到的,防火牆的『規則順序』是有特殊意義的,所以囉,當然先清除掉規則,然後一條一條來設定會比較容易一點啦!
       

      定義政策
       
      清除規則之後,再接下來就是要設定規則的政策啦!還記得政策指的是什麼嗎?『當您的封包不在您設定的規則之內時,則該封包的通過與否,以 Policy 的設定為準』,通常這個政策在 filter 這個 table 的 INPUT 鏈方面可以定義的比較嚴格一點,而 FORWARD 與 OUTPUT 則可以訂定的鬆一些!通常我都是將 INPUT 的 policy 定義為 DROP 啦!全部都擋掉再說!
       
      [root@test root]# /sbin/iptables [-t tables] [-P] [INPUT,OUTPUT,FORWARD| PREROUTING,OUTPUT,POSTROUTING] [ACCEPT,DROP]
      參數說明:
      -P   :定義政策( Policy )。注意,這個 P 為大寫啊!
      INPUT :封包為輸入主機的方向;
      OUTPUT :封包為輸出主機的方向;
      FORWARD:封包為不進入主機而向外再傳輸出去的方向;
      PREROUTING :在進入路由之前進行的工作;
      OUTPUT   :封包為輸出主機的方向;
      POSTROUTING:在進入路由之後進行的工作。
      範例:
      [root@test root]# /sbin/iptables -P   INPUT DROP
      [root@test root]# /sbin/iptables -P  OUTPUT ACCEPT
      [root@test root]# /sbin/iptables -P FORWARD ACCEPT
      [root@test root]# /sbin/iptables -t nat -P  PREROUTING ACCEPT
      [root@test root]# /sbin/iptables -t nat -P      OUTPUT ACCEPT
      [root@test root]# /sbin/iptables -t nat -P POSTROUTING ACCEPT
      # 除了 INPUT 之外,其他都給他設定為接受囉!在上面的設定之後,
      # 我們的主機發出的封包可以出去,但是任何封包都無法進入,
      # 包括回應給我們送出封包的回應封包(ACK)也無法進入喔! ^_^
       

      增加與插入規則
       
      好了,接下來準備要來定義規則了!請注意,在這個小節裡面我們完全都針對 Linux 本機來進行設定 ( 就是僅針對 filter table 囉! ),至於 NAT 後面的主機,我們一部分留到 NAT 主機設定再談,一部分留在本章最後面的進階篇再談,這裡先學基礎的就好了!要設定 iptables 規則的基本語法如下:
       
      [root@test root]# iptables [-t filter] [-AI INPUT,OUTPUT,FORWARD] \
      > [-io interface] [-p tcp,udp,icmp,all] [-s IP/network] [--sport ports]  \
      > [-d IP/network] [--dport ports] -j [ACCEPT,DROP]
      參數說明:
      -A  :新增加一條規則,該規則增加在最後面,例如原本已經有四條規則,
          使用 -A 就可以加上第五條規則!
      -I  :插入一條規則,如果沒有設定規則順序,預設是插入變成第一條規則,
          例如原本有四條規則,使用 -I 則該規則變成第一條,而原本四條變成 2~5
       INPUT :規則設定為 filter table 的 INPUT 鏈
       OUTPUT :規則設定為 filter table 的 OUTPUT 鏈
       FORWARD:規則設定為 filter table 的 FORWARD 鏈
       
      -i     :設定『封包進入』的網路卡介面
      -o    :設定『封包流出』的網路卡介面
       interface :網路卡介面,例如 ppp0, eth0, eth1....
       
      -p  :請注意,這是小寫呦!封包的協定啦!
       tcp :封包為 TCP 協定的封包;
       upd :封包為 UDP 協定的封包;
       icmp:封包為 ICMP 協定、
       all :表示為所有的封包!
       
      -s     :來源封包的 IP 或者是 Network ( 網域 );
      --sport:來源封包的 port 號碼,也可以使用 port1:port2 如 21:23
           同時通過 21,22,23 的意思
      -d     :目標主機的 IP 或者是 Network ( 網域 );
      --dport:目標主機的 port 號碼;
       
      -j   :動作,可以接底下的動作;
       ACCEPT :接受該封包
       DROP  :丟棄封包
       LOG  :將該封包的資訊記錄下來 (預設記錄到 /var/log/messages 檔案)
       
      範例:
       
      範例一:所有的來自 lo 這個介面的封包,都予以接受
      [root@test root]# iptables -A INPUT -i lo -j ACCEPT
      # 注意一下,因為 -d, --dport, -s, --sport 等等參數都沒有設定,這表示:
      # 不論封包來自何處或去到哪裡,只要是來自 lo 這個介面,就予以接受!
      # 這個觀念挺重要的,就是『沒有設定的規定,則表示該規定完全接受』的意思!
      # 例如這個案例當中,關於 -s, -d...等等的參數沒有規定時!
       
      範例二:來自 192.168.0.1 這個 IP 的封包都予以接受:
      [root@test root]# iptables -A INPUT -i eth0 -p tcp -s 192.168.0.1 -j ACCEPT
      # 新增一條規則,只要是來自於 192.168.0.1 的封包,不論他要去哪裡,
      # 使用的是那個協定 (port) 主機都會予以接受的意思~
       
      範例三:來自 192.168.1.0 這個 C Class 的網域的任何一部電腦,就予以接受!
      [root@test root]# iptables -A INPUT -i eth0 -p tcp -s 192.168.1.0/24 -j ACCEPT
      # 這個是網域的寫法喔!稍微注意一下的是,在範例二當中我們僅針對一個 IP ,
      # 至於這個範例當中,則是針對整個網域來開放吶!而網域的寫法可以是:
      # 192.168.1.0/24 也可以是 192.168.1.0/255.255.255.0 都能夠接受喔!
       
      範例四:來自 192.168.1.25 的封包都給他丟棄去!
      [root@test root]# iptables -A INPUT -i eth0 -p tcp -s 192.168.1.25 -j DROP
       
      範例五:只要是想進入本機的 port 21 的封包就給他丟棄
      [root@test root]# iptables -A INPUT -i eth0 -p tcp --dport 21 -j DROP
       
      範例六:來自 192.168.0.24 這個 IP 的封包,想要到我的 137,138,139 埠口時,都接受
      [root@test root]# iptables -A INPUT -i eth0 -p tcp -s 192.168.0.24  \
      > --dport 137:139 -j ACCEPT
       
      範例七:只要是接觸到我主機的 port 25 就將該封包記錄 (LOG) 下來
      [root@test root]# iptables -A INPUT -p tcp --dport 25 -j LOG
      # 還是請特別注意到『規則的順序排列』的問題喔!
       
      如上面的基本語法所示,我們的 iptables 可以規定封包『來自哪裡、要去哪裡、使用什麼協定(port number)』等等的資訊呢!所以他的功能就真的是挺強大的啊!而除了上述的功能之外,我們不是談過,好像還可以使用網路卡的硬體位址(MAC)來進行分析嗎?而且,那個 ping 的指令回應封包的 ICMP 協定也可以進行設定喔!此外,TCP 封包 Header 上面的 SYN 旗標的功能與否,也能夠設定呢!底下談一談這些更深入的規則喔!
       
      iptables 的其他相關參數說明:
       
      [!] --syn :這個設定僅能用於 -p tcp 的規則中,因為 TCP 封包有 syn 的旗標存
        在啊!當 TCP 封包存有 syn 旗標,表示這個連線是對方『主動』連過來的!
        若於 --syn 之前加上 ! 表示該封包不帶有 syn 的意思~(剛好相反之意!)
       
      範例一:將來自 192.168.100.200 的主動連線封包丟棄:
      [root@test root]# iptables -A INPUT -p tcp -i eth0 -s 192.168.1.235  \
      > --syn -j DROP
       
      --icmp-type:可以管制 ICMP 封包的某些類型!還記得我們在 網路基礎 裡面
        談到的 ICMP 的某些類型吧!對啦!如果您不想要讓對方 ping 到您的機器,
        就是利用這個項目啦!
       
      範例二:別的主機 ping 我們主機時,我們主機不予以回應
      [root@test root]# iptables -A INPUT -p icmp --icmp-type 8 -j DROP
      # 當您下達這樣的指令後,就表示未來別人對您使用 ping 的時候,
      # 我們的主機將不會回應,所以對方主機就會顯示我們主機『無法連接』的狀態!
       
      -m :表示封包的狀態,狀態有底下數種:
       -m mac --mac-source aa:bb:cc:dd:ee:ff 
         這個就是我們上面提到的可以控制『網路卡卡號, MAC』的設定方法囉!
         那個 aa:bb:cc:dd:ee:ff 就是網路卡的 MAC !
       -m state --state <狀態>
         有數種狀態,狀態有:
         INVALID:無效的封包,例如資料破損的封包狀態
         ESTABLISHED:已經連線成功的連線狀態;
         NEW:想要新建立連線的封包狀態;
         RELATED:這個最常用!表示這個封包是與我們主機發送出去的封包有關,
          可能是回應封包或者是連線成功之後的傳送封包!這個狀態很常被設定,
          因為設定了他之後,只要未來由本機發送出去的封包,即使我們沒有設定
          封包的 INPUT 規則,該有關的封包還是可以進入我們主機喔!
          可以簡化相當多的設定規則啦!
       
      範例三:讓 bb:cc:dd:aa:ee:ff 網路卡無法使用我們主機的資源
      [root@test root]# iptables -A INPUT -p all -m mac --mac-source \
      > 01:01:01:01:02:01 -j DROP
      # 這種方式可以用來管制網路卡卡號喔!就不怕別人使用 IP 搞怪了!
       
      範例四:讓已經建立或者是與我們主機有關的回應封包通過,但是讓不合法的,
          以及想要嘗試新建立的封包被抵擋在外!
      [root@test root]# iptables -A INPUT -p tcp -m state  \
      > --state ESTABLISHED,RELATED -j ACCEPT
      [root@test root]# iptables -A INPUT -p tcp -m state  \
      > --state INVALID,NEW -j DROP
      # 需要設定兩條喔!至於封包狀態則可以使用逗號隔開!逗號兩邊不要有空格
       
      -j <動作>:除了比較常見的 ACCEPT 與 DROP 之外,還有哪些動作?
       REDIRECT --to-ports <port number>
         這個也挺常見的,基本上,就是進行本機上面 port 的轉換就是了!
         不過,特別留意的是,這個動作僅能夠在 nat table 的 PREROUTING 以及
         OUTPUT 鏈上面實行而已喔!(關於連線流程,請參考圖八)
       MASQUERADE:封包偽裝
         這個就是 NAT 主機最重要的一個機制啦!進行封包的偽裝!
       
      範例五:將要求與 80 連線的封包轉遞到 8080 這個 port 
      [root@test root]# iptables -t nat -A PREROUTING -p tcp  --dport 80 \
      > -j REDIRECT --to-ports 8080
      # 這玩意最容易在您使用了非正規的 port 來進行某些 well known 的協定,
      # 例如使用 8080 這個 port 來啟動 WWW ,但是別人都以 port 80 來連線,
      # 所以,您就可以使用上面的方式來將對方對您主機的連線傳遞到 8080 囉!
       
      範例六:進行封包的偽裝,將來自 192.168.0.0/24 的封包的來源 IP 偽裝成為
          本機的 ppp0 那個介面的 IP
      [root@test root]# iptables -t nat -A POSTROUTING -s 192.168.0.0/24 \
      > -o ppp0 -j MASQUERADE
       

      紀錄與回復防火牆規則
       
      剛剛上面我們談了很多的設定了,那麼我該如何觀察目前主機上面的防火牆規則呢?我們可以使用『iptables -L -n 』來觀察,不過,該指令所顯示的資訊其實還是不太足夠的!這個時候,我們其實可以使用底下的兩個指令來將目前主機上面的防火牆機制『儲存』下來,在下次想要將這個規則『回復』的時候,就能夠直接利用指令將規則直接回復喔!
       
      [root@test root]# iptables-save > filename
      # 將目前的防火牆機制儲存成 filename 那個檔案!該檔案為 ASCII 格式,
      # 您可以進入查閱一下喔!
      [root@test root]# iptables-restore < filename
      # 將 filename 那個防火牆檔案 (注意!並不是 shell scripts 的格式) 的規則
      # 讀入目前的 Linux 主機環境中!
       
      利用 iptables-save 與 iptables-restore 也可以很輕鬆的管理好我們的防火牆系統吶!

一個簡單的防火牆設定:

    要實際設定防火牆之前,最好『先用筆將您所需要的規則與開放的服務設計一下』然後再來設計!而比較嚴密的防火牆規劃特點就是:
     
      拒絕所有,開放特定的設定方法較佳!
      
    也就是將 Policy 設定為 DROP 而將其他的服務一個一個的啟動,這樣會比較好的啦! ^_^!
     

    我的防火牆規則的草擬
     
    我這裡提一個蠻簡單的防火牆規劃,我的硬體連線如上面的 圖二 所示的那樣,亦即只有一部 Linux 主機,而我的網路設定為:
     
    • 外部網路使用 ppp0:由於是撥接的,所以實際對外是 ppp0 這一個界面;
    • 內部網路使用 eth0 :這個 eth0 使用在內部網路的連接上面,而且網域為 192.168.1.0/24 這個 C Class;
    • 主機開放的服務:目前我的主機雖然只有開放 NAT ,但是未來還會增加一些服務,目前我假設我的主機預計會有的對 Internet 上面啟用的服務有:
      • NAT
      • WWW
      • SSH
      • SMTP
      • POP3
      • IMAP
      • DNS
      • FTP, Telnet, DHCP, NFS 都只對內部網域開放!
     
    我們草擬的規則為:『關閉所有的,開放特定的』的模式,所以在政策上面( Policy )則選擇 DROP !而您也曉得, iptables 所訂定的規則為一條一條分析比對下去的,所以我們在 安排防火牆的規則 上面就顯得特別的重要了!為了預防某些動作被搞混亂了,加上未來我們要以這個簡易的防火牆進行更進一步的設定規劃,所以這裡我們需要用一個簡單的流程圖來示意!特別留意:這裡我們總共用了三個檔案,我放置的目錄在我 Linux 系統底下的 /usr/local/virus/iptables 裡面,檔名分別為:
     
    • iptables.rule :設定規則的檔案,包括清除防火牆規則、載入模組、設定一些服務的登入與否等等!
    • iptables.deny :設定惡意 IP 或網段的檔案,裡面完全都是抵擋的 IP 段落語法!
    • iptables.allow:可以想成是一些自己設定的後門啦!因為我們不知道哪一天會出到外頭去!這個時候,一個嚴格的防火牆說不定會擋死自己,所以需要加上一些 IP 的開放囉!
     
    注意:每次修改完了任何一個檔案,要立刻生效的話,請執行 iptables.rule 即可!而整個的流程有點像底下這樣:
     

    圖十一、簡單的防火牆規劃流程
     
    上面是我個人建議的小小流程,原則上,內部與主機的開放度很高,因為 Output 與 Forward 是完全開放不理的!對於小家庭的主機是可以接受的,因為我們內部的電腦數量不多,而且人員都是熟悉的,所以不需要特別加以控管!但是:『在大企業的內部,這樣的規劃是很不合格的,因為您不能保證內部所有的人都可以按照您的規定來使用 Network !』也就是說『家賊難防』呀!因此,連 Output 與 Forward 都需要特別加以管理才行!
     

    規則設定
     
    事實上,我們在設定防火牆的時候,不太可能會一個一個指令的輸入,通常是利用 shell scripts 來幫我們達成這樣的功能吶!底下是利用上面的流程圖所規劃出來的防火牆 scripts ,您可以參考看看,但是您需要將環境修改成適合您自己的環境才行喔!
     
    [root@test root]# mkdir -p /usr/local/virus/iptables
    [root@test root]# cd /usr/local/virus/iptables
    [root@test iptables]# vi iptables.rule
    #!/bin/bash
    #
    # ========================================================
    # 程式說明:
    # 歡迎使用 iptables.rule 這個 script 來建立您的防火牆!
    # 這支 script 還需要您的額外設定方可適合您的主機環境!
    # 基本規則定義為『拒絕所有,開放特定』的模式!
    #
    # 使用說明:
    # 請先將這個 scripts 的權限更改為可執行:
    #       chmod 755 iptables.rule
    # 在將這個程式放置在 /usr/local/virus/iptables 目錄下:
    #       mkdir -p /usr/local/virus/iptables
    #       mv /完整的路徑/iptables.rule /usr/local/virus/iptables
    # 執行測試:
    #       /usr/local/virus/iptables/iptables.rule
    #       iptables -L -n   (這個動作在檢查防火牆規則)
    # 將底下這一行加入 /etc/rc.d/rc.local 當中
    #       /usr/local/virus/iptables/iptables.rule
    # 取消防火牆:
    #       iptables -F
    #       iptables -X
    #       iptables -t nat -F
    #       iptables -t nat -X
    #
    # ========================================================
    # 版權宣告:
    # 這支程式為 GPL 授權,任何人皆可使用,
    # 然,若使用本 scripts 發生問題時,
    # 本人不負任何責任
    # VBird <vbird@tsai.adsldns.org>
    # ========================================================
    # 歷史紀錄:
    # 2002/08/20    VBird   首次釋出
    # 2003/04/26    VBird   加入砍站軟體的相關執行檔案!
    # 2003/08/25    VBird   修改 INPUT 的 Policy 成為 DROP
    # ========================================================

    # 0.0 Please key in your parameters
    # 這個 EXTIF 後面接的為『對外可連上 Internet 的網路介面』,
    # 一般來說,如果是撥接的 ADSL ,那麼底下就是 ppp0 ,
    # 如果是固定制的 IP ,那麼應該就是 eth0 囉!
    # The interface that connect Internet
      EXTIF="ppp0"

    # 底下這個 INIF 為對內的網路卡介面,
    # 如果您的 Linux 並沒有對內連接的網路卡,那麼底下請改成
    # INIF=""
    # 另外,如果INIF 不是 "" 的時候,請務必將您的內部網域
    # 填入 INNET 中!因為 INNET 為內部網域的設定值!
    # the inside interface. if you don't have this one
    # and you must let this be black ex> INIF=""
      INIF="eth0"
      INNET="192.168.1.0/24"        # This is for NAT's network

    # 1.0 測試您的核心版本與防火牆模組
      kver=`uname -r | cut -c 1-3`
      if [ "$kver" != "2.4" ] && [ "$kver" != "2.5" ]; then
            echo "Your Linux Kernel Version may not be suported by this script!"
            echo "This scripts will not be runing"
            exit
      fi
      ipchains=`lsmod | grep ipchains`
      if [ "$ipchains" != "" ]; then
            echo "unload ipchains in your system"
            rmmod ipchains 2> /dev/null
      fi

    # 2.0 載入適當的模組
      PATH=/sbin:/bin:/usr/sbin:/usr/bin
      export PATH EXTIF INIF INNET
      modprobe ip_tables            > /dev/null 2>&1
      modprobe iptable_nat          > /dev/null 2>&1
      modprobe ip_nat_ftp           > /dev/null 2>&1
      modprobe ip_nat_irc           > /dev/null 2>&1
      modprobe ip_conntrack         > /dev/null 2>&1
      modprobe ip_conntrack_ftp     > /dev/null 2>&1
      modprobe ip_conntrack_irc     > /dev/null 2>&1

    # 3.0 先清除所有的防火牆規則
      /sbin/iptables -F
      /sbin/iptables -X
      /sbin/iptables -Z
      /sbin/iptables -F -t nat
      /sbin/iptables -X -t nat
      /sbin/iptables -Z -t nat
      /sbin/iptables -P INPUT   DROP
      /sbin/iptables -P OUTPUT  ACCEPT
      /sbin/iptables -P FORWARD ACCEPT
      /sbin/iptables -t nat -P PREROUTING  ACCEPT
      /sbin/iptables -t nat -P POSTROUTING ACCEPT
      /sbin/iptables -t nat -P OUTPUT      ACCEPT

    # 4.0 先允許信任網域,這包含 lo 這個內部迴圈介面,
    #     以及剛剛指定的內部介面網域!
    #     當然,重點是可以啟動您的 Linux 成為 NAT 主機的啦!
      /sbin/iptables -A INPUT -i lo   -j ACCEPT
      if [ "$INIF" != "" ]; then
            /sbin/iptables -A INPUT -i $INIF -j ACCEPT
            echo "1" > /proc/sys/net/ipv4/ip_forward
            /sbin/iptables -t nat -A POSTROUTING -s $INNET -o $EXTIF -j MASQUERADE
      fi

    # 5.0 開始載入信任與拒絕的網域設定的檔案,
    #     底下兩個檔案可以自行建立喔!
      if [ -f /usr/local/virus/iptables/iptables.deny ]; then
            sh /usr/local/virus/iptables/iptables.deny
      fi
      if [ -f /usr/local/virus/iptables/iptables.allow ]; then
            sh /usr/local/virus/iptables/iptables.allow
      fi

    # 6.0 底下這個檔案若存在,則執行!請注意,
    #     這個檔案與杜絕砍站的軟體有關喔!
      if [ -f /usr/local/virus/httpd-err/iptables.http ]; then
            sh /usr/local/virus/httpd-err/iptables.http
      fi

    # 7.0 允許 ICMP 封包與允許已建立的連線通過!
      /sbin/iptables -A INPUT -m state --state ESTABLISHED,RELATED -j ACCEPT
      AICMP="0 3 3/4 4 11 12 14 16 18"
      for tyicmp in $AICMP
      do
            /sbin/iptables -A INPUT -i $EXTIF -p icmp --icmp-type $tyicmp -j ACCEPT
      done

    # 8.0 Allow services特別留意底下的服務,將您主機沒有開放的服務關閉吧!
      /sbin/iptables -A INPUT -p TCP -i $EXTIF --dport  22 -j ACCEPT        # SSH
      /sbin/iptables -A INPUT -p TCP -i $EXTIF --dport  25 -j ACCEPT        # SMTP
      /sbin/iptables -A INPUT -p UDP -i $EXTIF --dport  53 -j ACCEPT        # DNS
      /sbin/iptables -A INPUT -p TCP -i $EXTIF --dport  53 -j ACCEPT        # DNS
      /sbin/iptables -A INPUT -p TCP -i $EXTIF --dport  80 -j ACCEPT        # WWW
      /sbin/iptables -A INPUT -p TCP -i $EXTIF --dport 110 -j ACCEPT        # POP3
      /sbin/iptables -A INPUT -p TCP -i $EXTIF --dport 113 -j ACCEPT        # auth

     
    特別留意我上面的標註的粗體字部分,因為每個人的環境都不相同,因此您必須要設定屬於您自己的環境參數才行!不然,出了問題不要怪我啊!....再來看一下關於 iptables.allow 的內容是如何?假如我要讓一個 140.116.44.0/24 這個網域進入我的主機的話,那麼這個檔案的內容可以寫成這樣:
     
    [root@test iptables]# vi iptables.allow
    #!/bin/bash
    #
    # This program is used to allow some IP or hosts to access your Server
    #
    # HISTORY
    # 2002/08/20 first release by VBird

    /sbin/iptables -A INPUT  -i $EXTIF -s 140.116.44.0/24 -j ACCEPT

    [root@test iptables]# vi iptables.deny
    #!/bin/bash
    #
    # This script will deny some IPs that I don't want it IN
    #
    # HISTORY
    # 2002/08/20    revise        by VBird

    /sbin/iptables -A INPUT   -i $EXTIF -s 140.115.236.8   -j DROP
    /sbin/iptables -A INPUT   -i $EXTIF -s 140.120.13.237  -j DROP

     
    請特別注意,若您有新的 port 或者是沒有開啟某些 port 的時候,請在您的 iptables.rule 裡面的第 8 步驟,新增加其他的 port 的服務,這樣就可以啦!不過,還是如同前面我們所說的,這個 firewall 僅能提供基本的安全防護,其他的相關問題,還需要再測試測試呢!此外,如果您希望一開機就自動執行這個 script 的話,請將這個檔案的完整檔名寫入 /etc/rc.d/rc.local 當中,有點像底下這樣:
     
    [root@test /root]# vi /etc/rc.d/rc.local
    #!/bin/sh
    #
    # This script will be executed *after* all the other init scripts.
    # You can put your own initialization stuff in here if you don't
    # want to do the full Sys V style init stuff.

    touch /var/lock/subsys/local

    #1. adsl connectting.           2002/04/06      VBird
            /usr/sbin/adsl-start
    #2. Starting the NAT Server     2002/04/06      VBird
            /usr/local/nat/nat.sh
    #3. Starting firewall settings  2002/08/20      VBird
            /usr/local/virus/iptables/iptables.rule

    上面的三個檔案可以在底下的網站上取得下載:
    http://linux.vbird.org/download/index.php#firewall_iptables


TCP_Wrappers:

    在前一章認識網路安全當中,我們談到資料封包進入主機之前會通過的程序,第一道就是剛剛我們上面提到的 iptables ,那第二道大概就是 TCP Wrappers 囉!TCP Wrappers 有點類似 TCP 包裹的檢驗程序,其實這個 TCP Wrappers 也可以將他想成是另外一個防火牆就是了!事實上,這個 TCP Wrappers 其實是由 tcpd 這支程式所控制的,他可以協助主機來分析『某個服務的封包』呢!此外,目前的 xinetd 也含有類似的功能,所以雖然 xinetd 沒有使用 tcpd 這支程式,但是仍然可以具有相同的分析功能
     

    什麼是 TCP Wrappers 與他的抵擋機制
     
    剛剛說到,TCP Wrappers 的抵擋機制其實是以 tcpd 這支程式為主,而這支程式的主要參數檔在 /etc/hosts.allow 以及 /etc/hosts.deny 兩個檔案當中,『當某個軟體支援 tcpd (TCP Wrappers) 的功能,則當網路封包嘗試向該服務要求資料時,該網路封包將接受 TCP Wrappers 的檢驗,而檢驗的參數設定則是取自 /etc/hosts.allow 以及 /etc/hosts.deny兩個檔案』。所以囉,如果您要使用 TCP Wrappers 來管理某個程式時,需要特別留意該程式是否有支援 TCP Wrappers 喔!好了,那麼這裡有兩個檔案需要來設定,那麼那個檔案先被使用呢?
     
    • 在預設的狀態下,/etc/hosts.allow 這個檔案的設定內容會先被讀取;
    • 然後才會讀取 /etc/hosts.deny 的內容。
     
    那麼這兩個檔案如何設定呢?簡單的語法如下
     
    舊版的使用 tcpd 程式的語法
    <服務名稱> :  <IP/network> : <action>
    # 特別注意, network 可以使用 192.168.0.0/255.255.255.0 ,
    # 但不可使用 192.168.0.0/24 !
     
    範例一:
    [root@test root]# vi /etc/hosts.allow
    in.telnetd: 127.0.0.1 : allow
    in.telnetd: 192.168.1.0/255.255.255.0 : allow
    in.telnetd: .ncku.edu.tw : allow
    in.ftpd:    127.0.0.1 : allow
    # 允許的 127.0.0.1 這個 IP 使用本機的 telnet 及 ftp 這兩個服務!
    # 請特別注意,那個『服務名稱』其實就是『程式檔名』喔!
     
    [root@test root]# vi /etc/hosts.deny
    in.telnetd: 192.168.2.3 : deny
    # 將來自 192.168.2.3 對於使用本機 telnet 的權限關掉!
     
    # 特別注意,這個語法在 xinetd 裡面時,<action> 已經被拿掉了!
    # 所以,目前您可以使用這樣的格式:
    [root@test root]# vi /etc/hosts.allow
    in.telnetd: 127.0.0.1 
    in.telnetd: 192.168.1.0/255.255.255.0 
    in.telnetd: .ncku.edu.tw 
    # 事實上,這也是 TCP Wrappers 支援的格式,所以建議您直接使用此格式即可,
    # 亦即不需要加上 allow 或者是 deny 的動作,因為在 hosts.allow 裡面的
    # 規則就是 allow 而在 hosts.deny 裡面的規則就是 deny 的意思!
     
    在上面的語法當中,最重要的莫過於找出『服務名稱』!舉個例子來說,未來我們會介紹 ssh 這個遠端連線伺服器,而這個伺服器的啟動的 binary 可執行檔為 sshd 這個檔名的程式,所以您要讓某些來源的 IP 或主機名稱通過 TCP Wrappers 的檢驗時,就必須要:
     
      sshd: 192.168.0.100
     
    並且同時需要注意 SSH 是否有支援 TCP Wrappers 喔!重要重要!此外,您也可以使用 ALL 來代表『所有的服務』或者是『所有的來源』,例如在 /etc/hosts.deny 裡面加入:
     
      ALL: ALL
     
    代表『不論何種服務、不論來自哪裡的封包,全部都給他擋掉!』。
     

    TCP Wrapperes 的規則說明
     
    上面稍微提了一下 TCP Wrappers 的使用方法,其中最需要注意的是:封包的檢驗是先以 /etc/hosts.allow 為主,然後再以 /etc/hosts.deny 來管理!所以通常我們設定的方法就是:
     
    • 在 /etc/hosts.allow 裡面針對某些服務與封包來源開啟他們使用的權限;
    • 在 /etc/hosts.deny 裡面將該服務的其他來源都擋掉!
     
    注意喔!如果您在 /etc/hosts.deny 裡面沒有設定抵擋的話,那麼 TCP Wrappers 預設的動作是『可以通過檢驗,並進入主機』喔!舉例來說,同樣的以 SSH, Telnet 與 FTP 為例,如果您只想要讓『信任的主機』登入的話,那麼也可以在裡頭進行規劃!好了!這裡我們以私有網段 192.168.1.0/24 可以取用 Telnet 及 FTP 的 hosts 有 192.168.1.2, 192.168.1.10, 192.168.1.20 這三部電腦,及來自 Internet 上面可以取用 SSH 的主機為 xxx.yyy.zzz.qqq 這個主機,及 192.168.1.0/24 全部的電腦!則您的兩個檔案可以寫成這樣:
     
    [root@test root]# vi /etc/hosts.allow
    # 先寫關於 telnet, ftp 及 sshd 開放的資料
    in.telnetd: 192.168.1.2, 192.168.1.10, 192.168.1.20 
    in.ftpd:    192.168.1.2, 192.168.1.10, 102.168.1.20
    sshd:       192.168.1.0/255.255.255.0, xxx.yyy.zzz.qqq 
    # 每個 IP 或者主機之間,可以利用逗號或空格來隔開!
     
    [root@test root]# vi /etc/hosts.deny
    # 將上面的三個服務都關掉啦!
    in.telnetd: ALL 
    in.ftpd:    ALL 
    sshd:       ALL
     
    # 特別注意,很多朋友喜歡在 /etc/hosts.deny 裡面加入這一行:
    ALL: ALL
    # 來抵擋所有的服務與所有的來源!不過,我個人是不太建議這樣做的!
    # 因為很多時候,當您架設好網站之後,卻發現老是無法讓 Client 連線成功,
    # 很多經驗告訴我們,最大的問題就是出現在 ALL : ALL 這一行!
     
    其中,還有更高竿的 /etc/hosts.deny 的寫法,這是關於當有來自不明人士使用類似 nmap 掃 port 軟體來掃瞄您的主機時,他的 IP 會被記錄下喔!(注意,底下的寫法就需要有 TCP Wrappers 的輔助了!這包括了 safe_finger 這個指令!單純的使用 xinetd 是無法達到底下的功能的!所以,請安裝 tcp_wrappers 這個套件)
     
    [root@test root]# vi /etc/hosts.deny
    in.telnetd : ALL : spawn (/bin/echo Security notice from host `/bin/hostname`; \
    /bin/echo; /usr/sbin/safe_finger @%h ) | \
    /bin/mail -s "%d -%h security" root@localhost & \
    : twist ( /bin/echo -e "\n\nWARNING connectin not allowed. Your attempt has been logged. \n\n\n警告您尚未允許登入,您的連線將會被紀錄,並且作為以後的參考\n\n ". )

    in.ftpd : ALL : spawn (/bin/echo Security notice from host `/bin/hostname`; \
    /bin/echo; /usr/sbin/safe_finger @%h ) | \
    /bin/mail -s "%d -%h security" root@localhost & \
    : twist ( /bin/echo -e "\n\nWARNING connectin not allowed. Your attempt has been logged. \n\n\n警告您尚未允許登入,您的連線將會被紀錄,並且作為以後的參考\n\n ". )

    sshd : ALL : spawn (/bin/echo Security notice from host `/bin/hostname`; \
    /bin/echo; /usr/sbin/safe_finger @%h ) | \
    /bin/mail -s "%d -%h security" root@localhost & \
    : twist ( /bin/echo -e "\n\nWARNING connectin not allowed. Your attempt has been logged. \n\n\n警告您尚未允許登入,您的連線將會被紀錄,並且作為以後的參考\n\n ". )

     
    如此一來,當有來自非您所規定的合法 IP 試圖以 telnet, ftp 及 ssh 連線您的主機時,系統就會將該 IP 寄一份資料給 root 來留檔!不過,這有個傷腦筋的地方,萬一該 IP 最後成功的登入您的主機之後,可能會將 root 的信箱砍掉,導致這個作用就沒有效果了!所以,這個時候,請您將上面 root@localhost 改成另一個非主機的信箱來收信!這樣會比較有安全上的保障啦! ^_^這個咚咚一設定完畢立刻就生效了!所以不用去理他也沒關係!但是要隨時注意一下您的設定是否正確呦!上面的語法只要您修改『服務名稱』應該就能夠適用於其他的服務吧!但是,請注意喔!對 Internet 開放的服務不要設定這個樣子啊!不然人家可是無法連線進來的!上面的設定方法,大多是適用在『某些僅針對內部開放的服務』!
     
    上面的的 hosts.deny 範例您可以在底下的網頁下載:
    http://linux.vbird.org/download/index.php#firewall_iptables

其他相關測試:

雖然這樣一來就稍微建置好了您的防火牆了!但是誰都不知道到底這樣的防火牆效果如何?所以,您需要花費更多的時間來進行測試呢!測試的步驟可以是:
  1. 先由主機向外面主動連線試看看;
  2. 再由私有網域內的 PC 向外面主動連線試看看;
  3. 最後,由 Internet 上面的主機,主動連線到您的 Linux 主機試看看;
一步一步作下來,看看問題出在哪裡,然後多多的去改進、改良!!基本上,網路上目前很多的資料可以提供您不錯的參考了!這一篇的設定寫的是很簡單,大部分都還在介紹階段而已!希望對大家有幫助!我在參考資料當中列出幾個有用的防火牆網頁,希望大家有空真的要多多的去看看!會很有幫助的!

進階:防火牆後端伺服器的架設

我們來考慮一個比較有趣的問題,那就是如同圖四的情況,事實上,主機是架設在防火牆後端的!在這樣的情況下,我們要怎麼將來自 Internet 的封包,經由 firewall 轉遞到後端的主機上面呢?!我們可以參考一下封包的流程,如同上面圖九的說明,因為來自 Internet 的封包要丟給防火牆後端的主機,所以在『路由之前就需要先設定好轉換路由』的狀態了!因此在 nat table 的 PREROUTING 的鏈上面來進行所謂的『 Destination NAT, DNAT 』的動作才行啦!您需要在防火牆的 iptables 機制上面,在 nat table 上面新增一條規則才行!語法如下:
 
iptables 的其他相關參數說明:
 
-j <動作>:除了比較常見的 ACCEPT 與 DROP 之外,還有哪些動作?
 DNAT --to IP[:port]
   常用在防火牆後端的主機之封包轉遞上面!
 
範例:將來自 Internet 的 port 80 連線的封包轉遞到 192.168.10.10 這個主機上
[root@test root]# iptables -t nat -A PREROUTING -p tcp -i eth1 --dport 80 \
> -j DNAT --to 192.168.10.10:80
 
上面的範例是很簡單的一個例子,在比較簡易的環境下是可以成功的幫您進行 WWW 或者是 Mail 的服務的!不過,如果用在 FTP 上面可就很麻煩了~因為 FTP 除了正規的 21 這個命令通道埠口外,還有資料傳送的主動性與被動性!設定上很是困擾~有興趣的話,可以參考底下列出的幾個 iptables 的網站喔!這裡不再說明了!

重點回顧

  • 防火牆對於病毒的抵擋並不敏感;
  • 防火牆對於來自內部的網路誤用或濫用的抵擋性可能較不足;
  • 並不是架設防火牆之後,系統就一定很安全!還是需要更新套件漏洞的!
  • 防火牆依據封包抵擋的階層,可以分為 Proxy 以及 IP Filter 兩種類型;
  • 核心為 2.4 版的 Linux 使用的防火牆機制為 iptables ;
  • 防火牆的訂定與『規則順序』有很大的關係;
  • iptables 的 table 當中,至少就有 filter 與 nat 兩者,這兩者又各有三條鏈;
  • iptables 的指令列當中,可以下達的參數相當的多,當下達 -j LOG 的參數時,則該封包的流程會被紀錄到 /var/log/messages 當中;
  • 防火牆可以多重設定,例如雖然已經設定了 iptables ,但是仍然可以持續設定 TCP Wrappers ,因為誰也不曉得什麼時候 iptables 會有漏洞~或者是規則規劃不良!

參考資料


課後練習

  • 為什麼我架設了防火牆,我的主機還是可能中毒?
  • 請說明為何架設了防火牆,我的主機還是可能被入侵?入侵的依據可能是什麼方法?
  • 我們知道核心為 2.4 的 Linux 使用的防火牆機制為 iptables ,請問,如何知道我的 Linux 核心版本?
  • 請列出 iptables 預設的兩個 table ,以及各個 table 裡面的 chains 與各個 chains 所代表的意義;
  • 什麼是 iptables 的預設政策 (Policy)?
  • 假設今天我的 Linux 僅是作為 Client 之用,並沒有對 Internet 進行任何服務,那麼您的防火牆規劃應該如何設定比較好?!
  • 我要將來自 192.168.1.50 這個 IP 來源的封包,只要是向我的 21~23 埠口要求的封包,就將他抵擋,應該如何下達 iptables 指令?
  • 我要將我自己主機 ping 的回應功能取消,應該如何下達 iptables 的指令?
  • 請說明為何這個指令是錯誤的?『iptables -A INPUT -p udp --syn -s 192.168.0.20 -j DROP』?
  • DNS 的要求是必須的,那麼我該如何設定我的主機可以接受要求 DNS 的回應呢?
  • 如何取消 iptables 在我的系統上面?
  • 如何儲存目前的防火牆機制,以及如何將上次儲存下來的機制回復到目前的系統中?

  • 前往參考用解答
修改歷史:
2002/08/20:第一次完成日期!
2003/08/25:重新設計內容,改寫一些指令介紹,與前一篇『認識網路安全』分的比較完整一點!
其他連結
環境工程模式篇
鳥園討論區
鳥哥舊站

今日 人數統計
昨日 人數統計
本月 人數統計
上月 人數統計