iptables 規則不適用於允許特定 IP

iptables 規則不適用於允許特定 IP

我有一台帶有 2 個網路介面的主機:wifi 和站點-站點 vpn (zerotier)。

root@host:~# ifconfig wlp0s20f3
wlp0s20f3: flags=4163<UP,BROADCAST,RUNNING,MULTICAST>  mtu 1500
        inet 192.168.1.38  netmask 255.255.255.0  broadcast 192.168.1.255
        inet6 fe80::a098:2166:78af:d78d  prefixlen 64  scopeid 0x20<link>
        ether ac:12:03:ab:6e:31  txqueuelen 1000  (Ethernet)
        RX packets 1071869  bytes 1035656551 (1.0 GB)
        RX errors 0  dropped 0  overruns 0  frame 0
        TX packets 911450  bytes 134092251 (134.0 MB)
        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0


root@host:~# ifconfig ztklh3tu4b
ztklh3tu4b: flags=4163<UP,BROADCAST,RUNNING,MULTICAST>  mtu 2800
        inet 10.147.18.192  netmask 255.255.255.0  broadcast 10.147.18.255
        inet6 fe80::f8f6:d1ff:fe3d:4f09  prefixlen 64  scopeid 0x20<link>
        ether fa:f6:d1:3d:4f:09  txqueuelen 1000  (Ethernet)
        RX packets 8836  bytes 1146994 (1.1 MB)
        RX errors 0  dropped 0  overruns 0  frame 0
        TX packets 667  bytes 281732 (281.7 KB)
        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0

我想封鎖該主機的所有流量(入站和出站),VPN 後面的 IP 除外。所以我加入了以下 iptable 規則:

iptables -P INPUT DROP
iptables -P OUTPUT DROP
iptables -P FORWARD DROP
iptables -A INPUT -s 10.147.18.80 -j ACCEPT
iptables -A OUTPUT -d 10.147.18.80 -j ACCEPT

當我 ping 10.147.18.80 時,我無法執行此操作。以下是 ping 結果:

PING 8.8.8.8 (8.8.8.8) 56(84) bytes of data.
^C
--- 8.8.8.8 ping statistics ---
4 packets transmitted, 0 received, 100% packet loss, time 3067ms

root@host:~# ping 10.147.18.80
PING 10.147.18.80 (10.147.18.80) 56(84) bytes of data.
^C
--- 10.147.18.80 ping statistics ---
6 packets transmitted, 0 received, 100% packet loss, time 5097ms

當我將 iptables 規則中的 IP 更改為其他內容(例如 8.8.8.8)時,一切都按預期工作,即我無法與除 8.8.8.8 之外的任何內容進行通訊。

編輯 iptables -nvL 的以下輸出顯示了這些鏈:

root@host:~# iptables -nvL
Chain INPUT (policy DROP 23 packets, 4560 bytes)
 pkts bytes target     prot opt in     out     source               destination         
    0     0 ACCEPT     all  --  *      *       10.147.18.80         0.0.0.0/0           

Chain FORWARD (policy DROP 0 packets, 0 bytes)
 pkts bytes target     prot opt in     out     source               destination         

Chain OUTPUT (policy DROP 330 packets, 25776 bytes)
 pkts bytes target     prot opt in     out     source               destination         
    8   672 ACCEPT     all  --  *      *       0.0.0.0/0            10.147.18.80         

iptables 的上述輸出顯示,當規則到位時,資料包發送到 IP,但沒有收到回應。

我的主機上的 Tcpdump 顯示了相同的行為:

tcpdump: data link type LINUX_SLL2
tcpdump: listening on any, link-type LINUX_SLL2 (Linux cooked v2), snapshot length 262144 bytes


13:28:32.323064 ztklh3tu4b Out IP (tos 0x0, ttl 64, id 17342, offset 0, flags [DF], proto ICMP (1), length 84)
    10.147.18.192 > 10.147.18.80: ICMP echo request, id 61, seq 1, length 64
13:28:33.330145 ztklh3tu4b Out IP (tos 0x0, ttl 64, id 17567, offset 0, flags [DF], proto ICMP (1), length 84)
    10.147.18.192 > 10.147.18.80: ICMP echo request, id 61, seq 2, length 64
13:28:34.354178 ztklh3tu4b Out IP (tos 0x0, ttl 64, id 17694, offset 0, flags [DF], proto ICMP (1), length 84)
    10.147.18.192 > 10.147.18.80: ICMP echo request, id 61, seq 3, length 64
13:28:35.378135 ztklh3tu4b Out IP (tos 0x0, ttl 64, id 17714, offset 0, flags [DF], proto ICMP (1), length 84)
    10.147.18.192 > 10.147.18.80: ICMP echo request, id 61, seq 4, length 64

10.147.18.80 上的 Tcpdump 不顯示來自 10.147.18.192 的任何入站 ICMP 回顯請求。可能出了什麼問題?

答案1

如果您在此主機上使用 VPN 用戶端來建立第二個接口,請不要忘記允許連接到 VPN 伺服器,否則你的本地ip10.147.18.192將無法存取。

您至少需要允許介面上的 VPN 伺服器進出站和入站流量wlp0s20f3

iptables -I OUTPUT -d $vpn_server_ip -p $proto --dport $vpn_port -j ACCEPT
iptables -I INPUT -m state --state RELATED,ESTABLISHED -j ACCEPT

$proto 將是udptcp, and $vpn_server_ip: $vpn_portVPN 伺服器的 IP 位址或範圍和連接埠

我無法猜測這些值,但您的 VPN 文件或與 VPN 隧道建立有效連接的 tcpdump/wireguard 應該可以為您提供這些資訊。

答案2

您在問題中提到的這兩個命令:

iptables -A INPUT -s 10.147.18.80 -j ACCEPT
iptables -A OUTPUT -d 10.147.18.80 -j ACCEPT

他們將這些規則附加到鏈的末端。 -A選項將規則附加到末尾。如果您使用-I選項,您會將規則放在鏈的頂部。

這裡的問題是,在其中一個鏈中的規則之前,您可能已經有一個DROPorREJECT規則,該ACCEPT規則會在流量到達鏈末端之前丟棄流量。例如,一條規則會丟棄進出包含 IP 10.147.18.80 的整個子網路的流量。

如果鏈中存在丟棄/拒絕流向該 IP 或來自該 IP 的流量(取決於它是 INPUT 鏈還是 OUTPUT 鏈)的規則,則在 ACCEPT 規則之前,無論該規則僅指定該 IP 還是整個子網,流量被刪除,並且鏈中的所有其他規則不再被處理。

DROPREJECTACCEPT是終止目標,一旦 iptables 符合該規則,它就會停止處理鏈中的其他規則,不會繼續處理下一條規則。

嘗試

iptables -I INPUT -s 10.147.18.80 -j ACCEPT
iptables -I OUTPUT -d 10.147.18.80 -j ACCEPT

這會將這些規則放在鏈的頂部,因此它們是第一個被命中的規則,然後不會針對這些鏈中的流量處理其他規則。

您可以列出鏈中的所有規則,例如

iptables -nvL

或者如果您只想查看特定的鏈

iptables -nvL INPUT 
iptables -nvL OUTPUT

編輯

鑑於您貼上的輸出,以及如果您將預設操作更改為此可以 ping 的事實ACCEPT似乎不是問題。

您可以使用 tcpdump 之類的工具來查看流量是否正在傳輸並傳回。

這樣的命令將為您提供機器發送或接收的所有 icmp 資料包

tcpdump -nnvvi any icmp

如果你在輸出中得到類似的東西

10:13:48.866598 IP (tos 0x0, ttl 255, id 30625, offset 0, flags [DF], proto ICMP (1), length 84)
    10.147.18.192 > 10.147.18.80: ICMP echo request, id 26621, seq 4, length 64
10:13:48.867771 IP (tos 0x0, ttl 53, id 0, offset 0, flags [none], proto ICMP (1), length 84)
    10.147.18.80 > 10.147.18.192: ICMP echo reply, id 26621, seq 4, length 64

然後,您的 ping 封包將被發送出去並返回,但會被其他規則拒絕。

您可以檢查其他表格(例如 nat 或 Mingle 表)中是否有其他規則,是否有一些規則與流量衝突。

iptables -t nat -nvL
iptables -t mingle -nvL

pkts您也可以透過清單中的數字查看資料包是否正在通過 OUTPUT 鏈中的 ACCEPT 規則。如果在您嘗試 ping 後該數字不斷增加,但 INPUT 鏈中的數字仍為 0,則問題出在傳入流量規則上。

也要檢查您的路由,使用ip r命令或類似的東西,如果流量可能不是透過同一子網路中的介面退出,那麼傳回封包的來源 IP 可能會因為沿途的某些 NAT 規則而改變。

相關內容