nftables 链优先级不起作用

nftables 链优先级不起作用

所以我有两个输入链,input并且dyn是动态生成的。

但是,由于 , 的规则dyn不起作用input。我尝试将 的优先级设置input1,甚至将dyn设置为。仍然没有结果。0-200

当我刷新input规则时,它就开始dyn起作用了。

我在这里做错了什么?

sudo nft list ruleset
table inet filter {
chain input {
    type filter hook input priority filter + 1; policy accept;
    iif "lo" accept
    ct state established,related accept
    tcp dport 299 ip saddr 3x.xx.xx.xx accept
    icmpv6 type { destination-unreachable, packet-too-big, time-exceeded, parameter-problem, echo-request, echo-reply, nd-router-solicit, nd-router-advert, nd-neighbor-solicit, nd-neighbor-advert, 148, 149 } accept
    ip6 saddr fe80::/10 icmpv6 type { mld-listener-query, mld-listener-report, mld-listener-done, mld2-listener-report, 151, 152, 153 } accept
    counter packets 10 bytes 5255 drop
}

chain dyn {
    type filter hook input priority filter; policy accept;
    iif "lo" accept
    ct state established,related accept
    ip saddr 2x.xx.xx.xx udp dport 8999 log prefix "dyn" accept
    ip6 saddr xxx:xxxx:xxxx:xxxx::9999 udp dport 8999 log prefix "dyn" accept
    ip saddr 2x.xx.xx.xx tcp dport 7999 log prefix "dyn" accept
    ip6 saddr xxx:xxxx:xxxx:xxxx::9999 tcp dport 7999 log prefix "dyn" accept
    ip saddr 2x.xx.xx.xx icmp type echo-request log prefix "dyn" accept
    ip6 saddr xxx:xxxx:xxxx:xxxx::9999 icmp type echo-request log prefix "dyn"
    ip saddr 2x.xx.xx.xx tcp dport 6999 log prefix "dyn" accept
    ip6 saddr xxx:xxxx:xxxx:xxxx::aaaa tcp dport 6999 log prefix "dyn" accept
}
}

答案1

每个链都会挂接到 Netfilter:只要存在数据包,Netfilter 就会调用挂接到当前阶段(例如:输入)的所有链。

这意味着每个链都提供了丢弃数据包的机会。一旦数据包被丢弃,它就不再存在:剩余的链将不会被调用进行遍历,因为没有任何东西可用于遍历:数据包已经消失了。

因此,无论这两条链的优先级顺序如何,当每条链都有自己的接受或丢弃数据包的规则时,独立从另一条链来看,最终结果是每个结果之间的逻辑与,其中降低方法错误的并接受手段真的

drop   AND drop   = drop
drop   AND accept = drop
accept AND drop   = drop
accept AND accept = accept

这是nft(8)VERDICT STATEMENT部分:

accept

终止规则集评估并接受数据包。该数据包稍后仍可以通过另一个钩子丢弃,例如在 forward 钩子中接受仍然允许稍后丢弃数据包在后路由钩子中,或者另一个具有更高优先级数的前向基链,在处理管道中随后进行评估

drop

终止规则集评估并丢弃数据包。丢弃立即发生,不会评估其他链或钩子。不可能再次在后续链中接受数据包,因为对于数据包来说这些不再被评估。

如果您想避免这种情况,则评估不能是独立的。例如,您可以在第一个链和第二个链之间传递一条消息(按钩子和钩子的优先级顺序),使用防火墙标记将其解释为“已做出决定,接受此数据包”。这需要双方的合作,因此不能强加给不知情的工具(例如:不能将其添加到由防火墙无需修改防火墙无论作为消息创建者还是消息消费者,都要考虑到这一点。

对于您的情况,您可以用以下变体替换您的规则集:

table inet filter {

chain markandaccept {
    meta mark set 0x900d accept
}

chain input {
    type filter hook input priority filter + 1; policy accept;
    meta mark 0x900d accept
    iif "lo" accept
    ct state established,related accept
    tcp dport 299 ip saddr 3x.xx.xx.xx accept
    icmpv6 type { destination-unreachable, packet-too-big, time-exceeded, parameter-problem, echo-request, echo-reply, nd-router-solicit, nd-router-advert, nd-neighbor-solicit, nd-neighbor-advert, 148, 149 } accept
    ip6 saddr fe80::/10 icmpv6 type { mld-listener-query, mld-listener-report, mld-listener-done, mld2-listener-report, 151, 152, 153 } accept
    counter drop
}

chain dyn {
    type filter hook input priority filter; policy accept;
    iif "lo" goto markandaccept
    ct state established,related goto markandaccept
    ip saddr 2x.xx.xx.xx udp dport 8999 log prefix "dyn" goto markandaccept
    ip6 saddr xxx:xxxx:xxxx:xxxx::9999 udp dport 8999 log prefix "dyn" goto markandaccept
    ip saddr 2x.xx.xx.xx tcp dport 7999 log prefix "dyn" goto markandaccept
    ip6 saddr xxx:xxxx:xxxx:xxxx::9999 tcp dport 7999 log prefix "dyn" goto markandaccept
    ip saddr 2x.xx.xx.xx icmp type echo-request log prefix "dyn" goto markandaccept
    ip6 saddr xxx:xxxx:xxxx:xxxx::9999 icmp type echo-request log prefix "dyn"
    ip saddr 2x.xx.xx.xx tcp dport 6999 log prefix "dyn" goto markandaccept
    ip6 saddr xxx:xxxx:xxxx:xxxx::aaaa tcp dport 6999 log prefix "dyn" goto markandaccept
}
}

这是一个未经任何简化的例子,我相信可以做得更好。

因此,每当动态链认为数据包应该保持接受状态,数据包会被标记(内部标记,仅在当前网络堆栈中)。修改后的输入链将检查此标记:如果存在,则立即接受数据包而无需进一步处理:第一个链中做出的决定在第二个链中得到尊重。

相关内容