From: Pablo Neira Ayuso <pablo@netfilter.org>
To: Florian Westphal <fw@strlen.de>
Cc: netfilter-devel@vger.kernel.org, Sunny73Cr <Sunny73Cr@protonmail.com>
Subject: Re: [PATCH nft 1/3] netlink_delinarize: fix bogus munging of mask value
Date: Fri, 7 Feb 2025 10:54:13 +0100 [thread overview]
Message-ID: <Z6XYRU-KObYW-w3M@calendula> (raw)
In-Reply-To: <20250130174718.6644-1-fw@strlen.de>
On Thu, Jan 30, 2025 at 06:47:12PM +0100, Florian Westphal wrote:
> Given following input:
> table ip t {
> chain c {
> @ih,58,6 set 0 @ih,86,6 set 0 @ih,170,22 set 0
> }
> }
>
> nft will produce following output:
> chain c {
> @ih,48,16 set @ih,48,16 & 0x3f @ih,80,16 set @ih,80,16 & 0x3f0 @ih,160,32 set @ih,160,32 & 0x3fffff
> }
>
> The input side is correct, the generated expressions sent to kernel are:
>
> 1 [ payload load 2b @ inner header + 6 => reg 1 ]
> 2 [ bitwise reg 1 = ( reg 1 & 0x0000c0ff ) ^ 0x00000000 ]
> 3 [ payload write reg 1 => 2b @ inner header + 6 .. ]
> 4 [ payload load 2b @ inner header + 10 => reg 1 ]
> 5 [ bitwise reg 1 = ( reg 1 & 0x00000ffc ) ^ 0x00000000 ]
> 6 [ payload write reg 1 => 2b @ inner header + 10 .. ]
> 7 [ payload load 4b @ inner header + 20 => reg 1 ]
> 8 [ bitwise reg 1 = ( reg 1 & 0x0000c0ff ) ^ 0x00000000 ]
> 9 [ payload write reg 1 => 4b @ inner header + 20 .. ]
>
> @ih,58,6 set 0 <- Zero 6 bits, starting with bit 58
>
> Changes to inner header mandate a checksum update, which only works for
> even byte counts (except for last byte in the payload).
>
> Thus, we load 2b at offet 6. (16bits, offset 48).
>
> Because we want to zero 6 bits, we need a mask that retains 10 bits and
> clears 6: b1111111111000000 (first 8 bit retains 48-57, last 6 bit clear
> 58-63). The '0xc0ff' is not correct, but thats because debug output comes
> from libnftnl which prints values in host byte order, the value will be
> interpreted as big endian on kernel side, so this will do the right thing.
>
> Next, same problem:
>
> @ih,86,6 set 0 <- Zero 6 bits, starting with bit 86.
>
> nft needs to round down to even-sized byte offset, 10, then retain first
> 6 bits (80 + 6 == 86), then clear 6 bits (86-91), then keep 4 more as-is
> (92-95).
>
> So mask is 0xfc0f (in big endian) would be correct (b1111110000001111).
>
> Last expression, @ih,170,22 set 0, asks to clear 22 bits starting with bit
> 170, nft correctly rounds this down to a 32 bit read at offset 160.
>
> Required mask keeps first 10 bits, then clears 22
> (b11111111110000000000000000000000). Required mask would be 0xffc00000,
> which corresponds to the wrong-endian-printed value in line 8 above.
>
> Now that we convinced ourselves that the input side is correct, fix up
> netlink delinearize to undo the mask alterations if we can't find a
> template to print a human-readable payload expression.
>
> With this patch, we get this output:
>
> @ih,48,16 set @ih,48,16 & 0xffc0 @ih,80,16 set @ih,80,16 & 0xfc0f @ih,160,32 set @ih,160,32 & 0xffc00000
>
> ... which isn't ideal. We should fixup the payload expression to display
> the same output as the input, i.e. adjust payload->len and offset as per
> mask and discard the mask instead.
>
> This will be done in a followup patch.
>
> Fixes: 50ca788ca4d0 ("netlink: decode payload statment")
> Reported-by: Sunny73Cr <Sunny73Cr@protonmail.com>
> Signed-off-by: Florian Westphal <fw@strlen.de>
Reviewed-by: Pablo Neira Ayuso <pablo@netfilter.org>
prev parent reply other threads:[~2025-02-07 9:54 UTC|newest]
Thread overview: 6+ messages / expand[flat|nested] mbox.gz Atom feed top
2025-01-30 17:47 [PATCH nft 1/3] netlink_delinarize: fix bogus munging of mask value Florian Westphal
2025-01-30 17:47 ` [PATCH nft 2/3] src: add and use payload_expr_trim_force Florian Westphal
2025-02-07 9:54 ` Pablo Neira Ayuso
2025-01-30 17:47 ` [PATCH nft 3/3] tests: py: extend raw payload match tests Florian Westphal
2025-02-07 9:54 ` Pablo Neira Ayuso
2025-02-07 9:54 ` Pablo Neira Ayuso [this message]
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=Z6XYRU-KObYW-w3M@calendula \
--to=pablo@netfilter.org \
--cc=Sunny73Cr@protonmail.com \
--cc=fw@strlen.de \
--cc=netfilter-devel@vger.kernel.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.