這是我的網路設定:
我的網頁設定http://daveden.files.wordpress.com/2013/05/network-configuration.png
代理伺服器在連接埠 3128 上執行 Ubuntu,並在連接埠 3128 上執行 Squid,在連接埠 8080 上執行 DansGuardian。
我想強制所有客戶端使用代理伺服器 - 特別是連接埠 8080 - 進行任何 HTTP/HTTPS 存取。
但是,我不想透明地重定向,因為這不適用於 HTTPS。我不介意配置每個客戶端,也不介意每個客戶端都知道它正在使用代理伺服器。我只是不希望客戶端能夠在沒有代理設定的情況下上網。
我該怎麼做呢?如果用戶端未配置為使用連接埠 8080 上的代理伺服器,我可以直接丟棄封包嗎?
我嘗試使用 iptables 丟棄 dport 不是 8080 的資料包,但我認為拒絕了太多,我無法再存取任何內容。
編輯
我重寫了這個問題,使其不是特定於 iptables 的,但我根本不反對使用 iptables。我只是想吸引更廣泛的可能解決方案。
編輯2
我想我可能給一些人留下了錯誤的印象。澄清一下,我一點興趣濾HTTPS 流量(即在代理程式處查看資料包並檢查內容)。我更感興趣的是阻塞使用 DansGuardian 的站點,無論是透過 HTTP 還是 HTTPS(透過查看封包的目的地)。
編輯3
根據下面 Alexandru-Florin Vintil 的建議,這是我目前正在做的事情:
# Redirect HTTP traffic to port 8080 (DansGuardian)
iptables -t nat -A PREROUTING -i eth1 -p tcp --dport 80 -j REDIRECT --to-port 8080
# Check TCP and UDP traffic against whitelist
iptables -A FORWARD -i eth1 -p tcp --dport 443 -j whitelist
iptables -A FORWARD -i eth1 -p udp --dport 443 -j whitelist
# Drop all other HTTPS traffic
iptables -A FORWARD -i eth1 -p tcp --dport 443 -j DROP
iptables -A FORWARD -i eth1 -p udp --dport 443 -j DROP
# Drop all traffic aimed straight at the proxy
iptables -A FORWARD -i eth1 -p tcp --dport 3128 -j DROP
iptables -A FORWARD -i eth1 -p udp --dport 3128 -j DROP
iptables -A FORWARD -i eth1 -p tcp --dport 8080 -j DROP
iptables -A FORWARD -i eth1 -p udp --dport 8080 -j DROP
簡而言之,將 HTTP 流量重定向到連接埠 8080,丟棄所有未列入白名單的 HTTPS 流量(在單獨的鏈中),並丟棄所有明確使用代理的流量。如果沒有最後一條規則,客戶端只要將瀏覽器配置為使用代理程式就可以使用 HTTPS 存取任何網站,因為目標連接埠是 8080 而不是 443。 。
答案1
我的2分錢:
關於 HTTP:讓防火牆透明地將連接埠 80 流量轉送到代理/過濾器是最簡單的方法。無需客戶端配置,+您可以免除任何主機/子網路使用代理,而無需客戶端重新配置。這是您可以放心所有應該透過代理商傳遞的內容的唯一方法。
除了阻止所有傳出 HTTPS 443 流量並僅允許基於允許傳出連接埠 443 的 IP 的網站子集之外,任何方法都無法如預期般運作。 HTTPS 的安全協定旨在防止中間人攻擊(代理是「合法」MITM)(除了一些缺陷)。這樣,HTTPS 就可以完成其設計目的。但是,如果您想要忽略HTTPS,您應該將您的魷魚設定為使用 DIRECT 而不是使用 CONNECT(點擊),但即使是這種情況,您仍然可能會遇到具有混合 HTTP/HTTPS 部分的有問題的網站。這樣,您的 Squid 代理程式也會管理 HTTPS。這也應該反映在防火牆的透明轉送部分。
答案2
每當您發現應該起作用的東西不起作用時,您需要詢問是否涉及其他一些您沒有看到的因素。規則
sudo iptables -A INPUT -p tcp ! --dport 8080 -j REJECT
看起來應該可以,但是你有附加的它被添加到 INPUT 鏈中,因此它可能被鏈中先前的規則所規避。這個規則本身就足夠了,因為 INPUT 鍊是傳入封包命中的第一個鏈。如果它們在 INPUT 鏈處被 REJECTed,則它們永遠不會到達 FORWARD 或 OUTPUT 鏈。當然,這條規則會阻止一切TCP 的目標連接埠不是 8080,這可能不是您最終真正想要的,除非 8080 上的代理是電腦上唯一的服務,並且您只從控制台登入。
因此,首先要做的是列出規則並查找可能導致資料包通過的原因:
sudo iptables -L
如果您的防火牆是反向 NAT,那麼您也應該列出 NAT 表。
sudo iptables -L -t nat
然後,嘗試將相同的規則放在開始鏈條的:
sudo iptables -I INPUT -p tcp ! --dport 8080 -j REJECT
看看這是否不能解決問題,或至少讓您更有信心了解如何iptables
工作,以便您可以完成規則集。如果您正在遠端操作該主機,我的建議會打斷您,因此您應該僅從控制台執行此操作。為了安全地遠距工作,請見我的同事Eli Rosencruft 關於遠端調整防火牆的帖子。
答案3
標準
單獨的(使用者定義的)鏈可能會有所幫助。
# create a chain just for user 100 (192.168.1.100)
iptables -N custom_user_100
# redirect all traffic FROM user 100 to custom chain
iptables -A INPUT -p tcp -s 192.168.1.100 -j custom_user_100
# return from user chain for valid traffic, drop all other
iptables -A custom_user_100 -p tcp --dport 8080 -j RETURN
iptables -A custom_user_100 -j DROP
因此,它的作用是將來自 192.168.1.100 的任何流量重定向到自訂鏈中。如果找到有效的符合項目(發送至連接埠 8080 的流量),則此自訂(使用者定義)鏈僅傳回。不會導致鏈返回的所有其他不匹配流量是掉落。
稍後您可以查看表格統計資料以驗證是否發生了這種情況:
iptables -L -v -n
轉發
現在,如果您正在處理轉送流量,將會有一組不同的規則 - 但使用自訂(使用者定義)鏈的想法是相同的。我喜歡參考此連結中的圖表:http://www.csie.ntu.edu.tw/~b93070/CNL/v4.0/CNLv4.0.files/Page697.htm當試圖了解資料包的流向時。
在這種情況下,您可能需要執行以下操作:
# create a chain just for user 100 (192.168.1.100)
iptables -N custom_user_100
# redirect all traffic FROM user 100 to custom chain
iptables -A FORWARD -p tcp -s 192.168.1.100 -j custom_user_100
# return from user chain for valid traffic, drop all other
iptables -A custom_user_100 -p tcp --dport 8080 -j RETURN
iptables -A custom_user_100 -j DROP
這與第一個相同,只是應用於 INPUT 鏈的規則改為應用於 FORWARD 鏈。
更新2013-05-24
我重新閱讀了你的問題。所以會重新開始。
我們假設您的“代理”實際上是路由器。也就是說 - 它將所有資料包從一個介面傳遞到另一個介面 - 可能使用 NAT。這意味著所有感興趣的資料包都流經 FORWARD 鏈。
接下來:您說您將使用連接埠 8080 配置所有客戶端以存取代理本身。美好的。這意味著所有那些資料包將透過INPUT鏈進入「代理」。
所以:你只是想阻止任何人從 FORWARD 鏈上的 8080 端口出去。
iptables -A FORWARD -p tcp --dport 8080 -j REJECT
此規則將確保轉送至目標連接埠 8080 的任何內容都將被拒絕(ICMP 封包將傳送至嘗試透過代理傳遞封包的用戶端)。
實施此規則後,透過嘗試建立此類禁止的連線來測試這一點至關重要 - 然後透過鍵入以下內容列出規則:
iptables -L -v -n |grep 8080
並確保計數器增加。如果不是,則路由器設定有問題。
答案4
如果您不希望客戶端在沒有代理的情況下僅訪問 http{s} 站點,那麼您可以將DROP
封包REJECT
轉送到連接埠 80 和 443:
IPTABLES -I FORWARD -i eth1 -p tcp -m multiport --dports 80,443 -j REJECT
eth1
你的內部介面在哪裡。透過這種方式,您將不必與其他連接埠/存取發生衝突。