diff options
author | Pablo Neira Ayuso <pablo@netfilter.org> | 2023-06-01 21:28:28 +0200 |
---|---|---|
committer | Phil Sutter <phil@nwl.cc> | 2023-06-02 13:05:13 +0200 |
commit | f6d6ad24354ecd2997a48ba51b12e7dc34addd15 (patch) | |
tree | 5a7534a1f5bcd3d617539c7b96a0b0ecec7d7c37 /iptables/nft-ipv4.c | |
parent | 4c923250269f9ef4a7b4235f4dc127b04932a8eb (diff) |
nft: check for source and destination address in first place
When generating bytecode, check for source and destination address in
first place, then, check for the input and output device. In general,
the first expression in the rule is the most evaluated during the
evaluation process. These selectors are likely to show more variability
in rulesets.
# iptables-nft -vv -I INPUT -s 1.2.3.4 -p tcp
tcp opt -- in * out * 1.2.3.4 -> 0.0.0.0/0
table filter ip flags 0 use 0 handle 0
ip filter INPUT use 0 type filter hook input prio 0 policy accept packets 0 bytes 0
ip filter INPUT
[ payload load 4b @ network header + 12 => reg 1 ]
[ cmp eq reg 1 0x04030201 ]
[ meta load l4proto => reg 1 ]
[ cmp eq reg 1 0x00000006 ]
[ counter pkts 0 bytes 0 ]
Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
Signed-off-by: Phil Sutter <phil@nwl.cc>
Diffstat (limited to 'iptables/nft-ipv4.c')
-rw-r--r-- | iptables/nft-ipv4.c | 30 |
1 files changed, 16 insertions, 14 deletions
diff --git a/iptables/nft-ipv4.c b/iptables/nft-ipv4.c index 6df4e46b..d67d8198 100644 --- a/iptables/nft-ipv4.c +++ b/iptables/nft-ipv4.c @@ -33,6 +33,22 @@ static int nft_ipv4_add(struct nft_handle *h, struct nftnl_rule *r, uint32_t op; int ret; + if (cs->fw.ip.src.s_addr || cs->fw.ip.smsk.s_addr || cs->fw.ip.invflags & IPT_INV_SRCIP) { + op = nft_invflags2cmp(cs->fw.ip.invflags, IPT_INV_SRCIP); + add_addr(h, r, NFT_PAYLOAD_NETWORK_HEADER, + offsetof(struct iphdr, saddr), + &cs->fw.ip.src.s_addr, &cs->fw.ip.smsk.s_addr, + sizeof(struct in_addr), op); + } + + if (cs->fw.ip.dst.s_addr || cs->fw.ip.dmsk.s_addr || cs->fw.ip.invflags & IPT_INV_DSTIP) { + op = nft_invflags2cmp(cs->fw.ip.invflags, IPT_INV_DSTIP); + add_addr(h, r, NFT_PAYLOAD_NETWORK_HEADER, + offsetof(struct iphdr, daddr), + &cs->fw.ip.dst.s_addr, &cs->fw.ip.dmsk.s_addr, + sizeof(struct in_addr), op); + } + if (cs->fw.ip.iniface[0] != '\0') { op = nft_invflags2cmp(cs->fw.ip.invflags, IPT_INV_VIA_IN); add_iniface(h, r, cs->fw.ip.iniface, op); @@ -48,20 +64,6 @@ static int nft_ipv4_add(struct nft_handle *h, struct nftnl_rule *r, add_l4proto(h, r, cs->fw.ip.proto, op); } - if (cs->fw.ip.src.s_addr || cs->fw.ip.smsk.s_addr || cs->fw.ip.invflags & IPT_INV_SRCIP) { - op = nft_invflags2cmp(cs->fw.ip.invflags, IPT_INV_SRCIP); - add_addr(h, r, NFT_PAYLOAD_NETWORK_HEADER, - offsetof(struct iphdr, saddr), - &cs->fw.ip.src.s_addr, &cs->fw.ip.smsk.s_addr, - sizeof(struct in_addr), op); - } - if (cs->fw.ip.dst.s_addr || cs->fw.ip.dmsk.s_addr || cs->fw.ip.invflags & IPT_INV_DSTIP) { - op = nft_invflags2cmp(cs->fw.ip.invflags, IPT_INV_DSTIP); - add_addr(h, r, NFT_PAYLOAD_NETWORK_HEADER, - offsetof(struct iphdr, daddr), - &cs->fw.ip.dst.s_addr, &cs->fw.ip.dmsk.s_addr, - sizeof(struct in_addr), op); - } if (cs->fw.ip.flags & IPT_F_FRAG) { uint8_t reg; |