我正在尝试使用 ebtables 来匹配特定的 VLAN ID(非零)以及特定的 VLAN PCP 值。
我尝试了以下方法:
ebtables -A 转发 -p 0x8100 --vlan-id 5 --vlan-prio 3 -j DROP
Ebtables 不会抱怨(因为检查已在 ebtables 中注释掉),但使用“ebtables -L”返回的规则仅包含 VLAN ID 的匹配。
我确实在 ebtables 手册页中看到,当使用 vlan-prio 时,vlan-id 必须为零或未指定。
为什么会出现这样的情况呢?到目前为止,我还没有找到任何参考资料来支持使用优先级位时 ID 必须为零。
除了创建一个单独的链来分别匹配 vlan-id 和 vlan-prio 之外,还有什么办法可以实现这一点吗?
答案1
这个解释实际上没有意义,但它在内核中linux/net/bridge/netfilter/ebt_vlan.c
:
if (GET_BITMASK(EBT_VLAN_ID)) { if (!!info->id) { /* if id!=0 => check vid range */ if (info->id > VLAN_N_VID) { pr_debug("id %d is out of range (1-4096)\n", info->id); return -EINVAL; } /* Note: This is valid VLAN-tagged frame point. * Any value of user_priority are acceptable, * but should be ignored according to 802.1Q Std. * So we just drop the prio flag. */ info->bitmask &= ~EBT_VLAN_PRIO; } /* Else, id=0 (null VLAN ID) => user_priority range (any?) */ }
据我了解,核心ebtables 的一侧强制在接收具有非空 VLAN ID (VID) 的规则时忽略 prio (PCP) 标志/选项,因此我不知道如果不使用具有两个规则的用户链作为解决方法,您如何能够成功。
没有账号就很难查阅任何802.1Q的官方文档,但我在2005年的版本中找不到对此评论的解释。我知道它写的是 VID=0 意味着只有 PCP,但并不是说 PCP 意味着 VID=0,也不是两个参数之间有任何交互(我的意思是没有写任何内容)。
笔记:nftables没有这个限制:
nft add table bridge filter
nft add chain bridge filter forward '{ type filter hook forward priority -200; policy accept; }'
nft add rule bridge filter forward ether type vlan vlan id 5 vlan pcp 3 counter drop
将返回所提供的内容(包括调试字节码,此处以小尾数显示,因此为 0x81 而不是 0x8100 等):
# nft --debug=netlink list chain bridge filter forward -a
bridge filter forward 2
[ payload load 2b @ link header + 12 => reg 1 ]
[ cmp eq reg 1 0x00000081 ]
[ payload load 2b @ link header + 14 => reg 1 ]
[ bitwise reg 1 = (reg=1 & 0x0000ff0f ) ^ 0x00000000 ]
[ cmp eq reg 1 0x00000500 ]
[ payload load 1b @ link header + 14 => reg 1 ]
[ bitwise reg 1 = (reg=1 & 0x000000e0 ) ^ 0x00000000 ]
[ cmp eq reg 1 0x00000060 ]
[ counter pkts 0 bytes 0 ]
[ immediate reg 0 drop ]
table bridge filter {
chain forward { # handle 1
type filter hook forward priority -200; policy accept;
vlan id 5 vlan pcp 3 counter packets 0 bytes 0 drop # handle 2
}
}