Linux

使用 iptables 在 VLAN 之間轉發流量

  • May 26, 2016

我們的網路上有以下 4 個 VLAN,通過 DHCP 連接到 Ubuntu Linux 機器。這個 Linux 也應該充當 L3 路由器。

VLAN 10  on interface eth1.10  with subnet 10.10.10.0/24
VLAN 20  on interface eth1.20  with subnet 10.10.20.0/24
VLAN 50  on interface eth1.50  with subnet 10.10.50.0/24
VLAN 100 on interface eth1.100 with subnet 10.10.100.0/24

這是/etc/network/interfaces

auto lo
iface lo inet loopback

auto eth0
iface eth0 inet static
       address 192.168.10.169
       netmask 255.255.255.0
       gateway 192.168.10.1

auto eth1
iface eth1 inet static
       address 10.10.0.1
       network 10.10.0.0
       netmask 255.255.255.0
       broadcast 10.10.0.255

auto eth1.100
iface eth1.100 inet static
       address 10.10.100.1
       network 10.10.100.0
       netmask 255.255.255.0
       broadcast 10.10.100.255

auto eth1.10
iface eth1.10 inet static
       address 10.10.10.1
       network 10.10.10.0
       netmask 255.255.255.0
       broadcast 10.10.10.255

auto eth1.20
iface eth1.20 inet static
       address 10.10.20.1
       network 10.10.20.0
       netmask 255.255.255.0
       broadcast 10.10.20.255

auto eth1.50
iface eth1.50 inet static
       address 10.10.50.1
       network 10.10.50.0
       netmask 255.255.255.0
       broadcast 10.10.50.255

現在,來自所有 VLAN 的所有客戶端都應該能夠通過該介面連接到公共網際網路eth0。該部分實際上適用於 iptables 規則-A POSTROUTING -o eth0 -j MASQUERADE。DHCP 伺服器也正常工作。

但是由於 VLAN 100 將成為管理電腦的網路,因此 VLAN 100 中的客戶端應該能夠訪問 VLAN 10、20 和 50 上的所有其他電腦。並且 VLAN 10、20 和 50的客戶端應該只能夠訪問自己的 VLAN 內的電腦。

到目前為止,我已經嘗試了以下 iptables 規則以及MASQUERADE

-A FORWARD -i eth1.100 -o eth1.10 -j ACCEPT
-A FORWARD -i eth1.100 -o eth1.20 -j ACCEPT
-A FORWARD -i eth1.100 -o eth1.50 -j ACCEPT
-A FORWARD -i eth1.10 -o eth1.100 -m state --state RELATED,ESTABLISHED -j ACCEPT
-A FORWARD -i eth1.20 -o eth1.100 -m state --state RELATED,ESTABLISHED -j ACCEPT
-A FORWARD -i eth1.50 -o eth1.100 -m state --state RELATED,ESTABLISHED -j ACCEPT

我嘗試從 IP 地址為 10.10.100.101 的 PC 上 ping IP 地址為 10.10.20.100 的 PC,但沒有成功。我也無法從 100 子網 ping 10.10.50.101。

並且有一個奇怪的副作用:VLAN 20 是偶然的(我不知道為什麼)表現得像 100 應該的那樣。從那裡我可以 ping VLAN 10 和 100 中的 PC,這最終應該是不可能的。

我在核心中啟用了 IPv4 轉發,外部網際網路按預期工作。

這是完整的輸出iptables-save

# Generated by iptables-save v1.6.0 on Thu May 26 09:28:59 2016
*filter
:INPUT ACCEPT [7375:724156]
:FORWARD ACCEPT [0:0]
:OUTPUT ACCEPT [3695:415474]
-A FORWARD -i eth1.100 -o eth1.10 -j ACCEPT
-A FORWARD -i eth1.100 -o eth1.20 -j ACCEPT
-A FORWARD -i eth1.100 -o eth1.50 -j ACCEPT
-A FORWARD -i eth1.10 -o eth1.100 -m state --state RELATED,ESTABLISHED -j ACCEPT
-A FORWARD -i eth1.20 -o eth1.100 -m state --state RELATED,ESTABLISHED -j ACCEPT
-A FORWARD -i eth1.50 -o eth1.100 -m state --state RELATED,ESTABLISHED -j ACCEPT
COMMIT
# Completed on Thu May 26 09:28:59 2016
# Generated by iptables-save v1.6.0 on Thu May 26 09:28:59 2016
*nat
:PREROUTING ACCEPT [32796:9980970]
:INPUT ACCEPT [142:30526]
:OUTPUT ACCEPT [1829:211124]
:POSTROUTING ACCEPT [128:29756]
-A POSTROUTING -o eth0 -j MASQUERADE
COMMIT
# Completed on Thu May 26 09:28:59 2016

和輸出route

Destination     Gateway         Genmask         Flags Metric Ref    Use Iface
default         192.168.10.1    0.0.0.0         UG    0      0        0 eth0
10.10.0.0       *               255.255.255.0   U     0      0        0 eth1
10.10.10.0      *               255.255.255.0   U     0      0        0 eth1.10
10.10.20.0      *               255.255.255.0   U     0      0        0 eth1.20
10.10.50.0      *               255.255.255.0   U     0      0        0 eth1.50
10.10.100.0     *               255.255.255.0   U     0      0        0 eth1.100
link-local      *               255.255.0.0     U     1000   0        0 eth0
192.168.10.0    *               255.255.255.0   U     0      0        0 eth0

在此先感謝,希望有人能弄清楚我應該使用哪些 iptables 規則來實現我想要的(如果這就是問題所在)。

編輯:

正如@Sanael 所要求的,我做了更多的日誌記錄(-A FORWARD -o eth1+ -p icmp -j LOG --log-prefix "IPTABLES FORWARD: " --log-level 7),結果如下:

Ping 10.10.20.101 –> 10.10.50.100成功,日誌如下:

May 26 12:14:57 homeserver kernel: IPTABLES FORWARD: IN=eth1.20 OUT=eth1.50 MAC=00:0a:5e:50:7c:c1:c8:0a:a9:e5:f0:bc:08:00:45:00:00:3c SRC=10.10.20.101 DST=10.10.50.100 LEN=60 TOS=0x00 PREC=0x00 TTL=127 ID=23708 PROTO=ICMP TYPE=8 CODE=0 ID=1 SEQ=96
May 26 12:14:57 homeserver kernel: IPTABLES FORWARD: IN=eth1.50 OUT=eth1.20 MAC=00:0a:5e:50:7c:c1:00:1e:ec:fa:d1:10:08:00:45:00:00:3c SRC=10.10.50.100 DST=10.10.20.101 LEN=60 TOS=0x00 PREC=0x00 TTL=63 ID=15185 PROTO=ICMP TYPE=0 CODE=0 ID=1 SEQ=96
May 26 12:14:58 homeserver kernel: IPTABLES FORWARD: IN=eth1.20 OUT=eth1.50 MAC=00:0a:5e:50:7c:c1:c8:0a:a9:e5:f0:bc:08:00:45:00:00:3c SRC=10.10.20.101 DST=10.10.50.100 LEN=60 TOS=0x00 PREC=0x00 TTL=127 ID=23709 PROTO=ICMP TYPE=8 CODE=0 ID=1 SEQ=97
May 26 12:14:58 homeserver kernel: IPTABLES FORWARD: IN=eth1.50 OUT=eth1.20 MAC=00:0a:5e:50:7c:c1:00:1e:ec:fa:d1:10:08:00:45:00:00:3c SRC=10.10.50.100 DST=10.10.20.101 LEN=60 TOS=0x00 PREC=0x00 TTL=63 ID=15317 PROTO=ICMP TYPE=0 CODE=0 ID=1 SEQ=97
May 26 12:14:59 homeserver kernel: IPTABLES FORWARD: IN=eth1.20 OUT=eth1.50 MAC=00:0a:5e:50:7c:c1:c8:0a:a9:e5:f0:bc:08:00:45:00:00:3c SRC=10.10.20.101 DST=10.10.50.100 LEN=60 TOS=0x00 PREC=0x00 TTL=127 ID=23710 PROTO=ICMP TYPE=8 CODE=0 ID=1 SEQ=98
May 26 12:14:59 homeserver kernel: IPTABLES FORWARD: IN=eth1.50 OUT=eth1.20 MAC=00:0a:5e:50:7c:c1:00:1e:ec:fa:d1:10:08:00:45:00:00:3c SRC=10.10.50.100 DST=10.10.20.101 LEN=60 TOS=0x00 PREC=0x00 TTL=63 ID=15349 PROTO=ICMP TYPE=0 CODE=0 ID=1 SEQ=98
May 26 12:15:00 homeserver kernel: IPTABLES FORWARD: IN=eth1.20 OUT=eth1.50 MAC=00:0a:5e:50:7c:c1:c8:0a:a9:e5:f0:bc:08:00:45:00:00:3c SRC=10.10.20.101 DST=10.10.50.100 LEN=60 TOS=0x00 PREC=0x00 TTL=127 ID=23711 PROTO=ICMP TYPE=8 CODE=0 ID=1 SEQ=99
May 26 12:15:00 homeserver kernel: IPTABLES FORWARD: IN=eth1.50 OUT=eth1.20 MAC=00:0a:5e:50:7c:c1:00:1e:ec:fa:d1:10:08:00:45:00:00:3c SRC=10.10.50.100 DST=10.10.20.101 LEN=60 TOS=0x00 PREC=0x00 TTL=63 ID=15597 PROTO=ICMP TYPE=0 CODE=0 ID=1 SEQ=99

Ping 10.10.20.101 –> 10.10.100.100失敗,日誌如下:

May 26 12:09:06 homeserver kernel: IPTABLES FORWARD: IN=eth1.20 OUT=eth1.100 MAC=00:0a:5e:50:7c:c1:c8:0a:a9:e5:f0:bc:08:00:45:00:00:3c SRC=10.10.20.101 DST=10.10.100.100 LEN=60 TOS=0x00 PREC=0x00 TTL=127 ID=18715 PROTO=ICMP TYPE=8 CODE=0 ID=1 SEQ=85
May 26 12:09:11 homeserver kernel: IPTABLES FORWARD: IN=eth1.20 OUT=eth1.100 MAC=00:0a:5e:50:7c:c1:c8:0a:a9:e5:f0:bc:08:00:45:00:00:3c SRC=10.10.20.101 DST=10.10.100.100 LEN=60 TOS=0x00 PREC=0x00 TTL=127 ID=18716 PROTO=ICMP TYPE=8 CODE=0 ID=1 SEQ=86
May 26 12:09:16 homeserver kernel: IPTABLES FORWARD: IN=eth1.20 OUT=eth1.100 MAC=00:0a:5e:50:7c:c1:c8:0a:a9:e5:f0:bc:08:00:45:00:00:3c SRC=10.10.20.101 DST=10.10.100.100 LEN=60 TOS=0x00 PREC=0x00 TTL=127 ID=18717 PROTO=ICMP TYPE=8 CODE=0 ID=1 SEQ=87

Ping 10.10.50.100 –> 10.10.20.101失敗,日誌如下:

May 26 12:11:28 homeserver kernel: IPTABLES FORWARD: IN=eth1.50 OUT=eth1.20 MAC=00:0a:5e:50:7c:c1:00:1e:ec:fa:d1:10:08:00:45:00:00:54 SRC=10.10.50.100 DST=10.10.20.101 LEN=84 TOS=0x00 PREC=0x00 TTL=63 ID=54378 DF PROTO=ICMP TYPE=8 CODE=0 ID=1903 SEQ=1
May 26 12:11:29 homeserver kernel: IPTABLES FORWARD: IN=eth1.50 OUT=eth1.20 MAC=00:0a:5e:50:7c:c1:00:1e:ec:fa:d1:10:08:00:45:00:00:54 SRC=10.10.50.100 DST=10.10.20.101 LEN=84 TOS=0x00 PREC=0x00 TTL=63 ID=54495 DF PROTO=ICMP TYPE=8 CODE=0 ID=1903 SEQ=2
May 26 12:11:30 homeserver kernel: IPTABLES FORWARD: IN=eth1.50 OUT=eth1.20 MAC=00:0a:5e:50:7c:c1:00:1e:ec:fa:d1:10:08:00:45:00:00:54 SRC=10.10.50.100 DST=10.10.20.101 LEN=84 TOS=0x00 PREC=0x00 TTL=63 ID=54693 DF PROTO=ICMP TYPE=8 CODE=0 ID=1903 SEQ=3

Ping 10.10.50.100 –> 10.10.100.100失敗,日誌如下:

May 26 12:12:24 homeserver kernel: IPTABLES FORWARD: IN=eth1.50 OUT=eth1.100 MAC=00:0a:5e:50:7c:c1:00:1e:ec:fa:d1:10:08:00:45:00:00:54 SRC=10.10.50.100 DST=10.10.100.100 LEN=84 TOS=0x00 PREC=0x00 TTL=63 ID=8069 DF PROTO=ICMP TYPE=8 CODE=0 ID=1905 SEQ=1
May 26 12:12:25 homeserver kernel: IPTABLES FORWARD: IN=eth1.50 OUT=eth1.100 MAC=00:0a:5e:50:7c:c1:00:1e:ec:fa:d1:10:08:00:45:00:00:54 SRC=10.10.50.100 DST=10.10.100.100 LEN=84 TOS=0x00 PREC=0x00 TTL=63 ID=8269 DF PROTO=ICMP TYPE=8 CODE=0 ID=1905 SEQ=2
May 26 12:12:26 homeserver kernel: IPTABLES FORWARD: IN=eth1.50 OUT=eth1.100 MAC=00:0a:5e:50:7c:c1:00:1e:ec:fa:d1:10:08:00:45:00:00:54 SRC=10.10.50.100 DST=10.10.100.100 LEN=84 TOS=0x00 PREC=0x00 TTL=63 ID=8375 DF PROTO=ICMP TYPE=8 CODE=0 ID=1905 SEQ=3

Ping 10.10.100.100 –> 10.10.20.101失敗 沒有創建任何日誌輸出。

Ping 10.10.100.100 –> 10.10.50.100成功 沒有創建任何日誌輸出。

現在問題至少部分解決了(我對此很好)。

我一開始是用 Windows 客戶端測試網路,最近兩台電腦都升級了 Windows 10。問題本身非常愚蠢:Windows 沒有響應 ping,因為 Windows 10 中預設啟用了一些新的安全性。當我將一台 Linux 筆記型電腦添加到網路時,我遇到了所有其他人都可以 ping Linux 筆記型電腦的情況(預設策略是ALLOW),但 Linux PC 無法 ping 其他任何東西(Windows 沒有響應 ping)。然後我嘗試遠端桌面到 VLAN 10 和 50 中的 Windows PC,從 VLAN 100 中的 Linux PC 和繁榮 - 它工作!

所以 iptables/netfilter 規則完全沒有問題。

非常感謝您的所有回答和評論!

這是我最終的、工作的和簡化的 iptables 配置:

# Generated by iptables-save v1.6.0 on Thu May 26 16:00:55 2016
*filter
:INPUT ACCEPT [359:39449]
:FORWARD DROP [0:0]
:OUTPUT ACCEPT [563:89333]
-A FORWARD -i eth1+ -o eth1.100 -m state --state RELATED,ESTABLISHED -j ACCEPT
-A FORWARD -i eth1.100 -o eth1+ -j ACCEPT
-A FORWARD -i eth1+ -o eth0 -j ACCEPT
-A FORWARD -i eth0 -o eth1+ -m state --state RELATED,ESTABLISHED -j ACCEPT
COMMIT
# Completed on Thu May 26 16:00:55 2016
# Generated by iptables-save v1.6.0 on Thu May 26 16:00:55 2016
*nat
:PREROUTING ACCEPT [5650:1147271]
:INPUT ACCEPT [91:14019]
:OUTPUT ACCEPT [325:31088]
:POSTROUTING ACCEPT [44:7161]
-A POSTROUTING -o eth0 -j MASQUERADE
COMMIT
# Completed on Thu May 26 16:00:55 2016

首先,您在 FORWARD 鏈中的預設策略是 ACCEPT,因此您實際上並沒有拒絕任何流量。這解釋了為什麼 20 -> 50 轉發有效。您可以使用iptables -P FORWARD DROP.

至於其他 ping,請注意在您的日誌條目中,TTL 是 127 或 63,表明防火牆已經做出了路由決定並減少了 TTL。此外,您的防火牆未配置為阻止任何流量。這表明問題出在客戶端的路由配置中。我可以建議您在 ping 接收者上使用嗅探器來查看原始 ping 數據包是否到達?確保 10.10.10.0/24 上的客戶端(不是防火牆)的預設網關是 10.10.10.1 等。祝你好運!

並跟進路由表註釋,您的路由表是正確的,表明您的防火牆直接連接到您的 VLAN 網路。

引用自:https://serverfault.com/questions/779115