From: Martin KaFai Lau <martin.lau@linux.dev>
To: "Hudson, Nick" <nhudson@akamai.com>
Cc: Willem de Bruijn <willemdebruijn.kernel@gmail.com>,
"Tottenham, Max" <mtottenh@akamai.com>,
"Glasgall, Anna" <aglasgal@akamai.com>,
Alexei Starovoitov <ast@kernel.org>,
Daniel Borkmann <daniel@iogearbox.net>,
Andrii Nakryiko <andrii@kernel.org>,
"David S. Miller" <davem@davemloft.net>,
Eric Dumazet <edumazet@google.com>,
Jakub Kicinski <kuba@kernel.org>, Paolo Abeni <pabeni@redhat.com>,
"bpf@vger.kernel.org" <bpf@vger.kernel.org>,
"netdev@vger.kernel.org" <netdev@vger.kernel.org>,
"linux-kernel@vger.kernel.org" <linux-kernel@vger.kernel.org>
Subject: Re: [PATCH v2 3/5] bpf: add helper masks for ADJ_ROOM flags and encap validation
Date: Fri, 27 Mar 2026 12:02:56 -0700 [thread overview]
Message-ID: <af12c536-adcb-4071-9b25-15035273a217@linux.dev> (raw)
In-Reply-To: <8B5AD797-623A-441E-8D46-EEBDC44793F0@akamai.com>
On 3/27/26 3:55 AM, Hudson, Nick wrote:
>
>
>> On Mar 26, 2026, at 5:49 PM, Martin KaFai Lau <martin.lau@linux.dev> wrote:
>>
>> !-------------------------------------------------------------------|
>> This Message Is From an External Sender
>> This message came from outside your organization.
>> |-------------------------------------------------------------------!
>>
>>
>>
>> On 3/26/26 10:02 AM, Hudson, Nick wrote:
>>>>> static int bpf_skb_net_grow(struct sk_buff *skb, u32 off, u32 len_diff,
>>>>> u64 flags)
>>>>> @@ -3502,6 +3513,11 @@ static int bpf_skb_net_grow(struct sk_buff *skb, u32 off, u32 len_diff,
>>>>> unsigned int gso_type = SKB_GSO_DODGY;
>>>>> int ret;
>>>>> + if (unlikely(flags & ~(BPF_F_ADJ_ROOM_ENCAP_MASK |
>>>>> + BPF_F_ADJ_ROOM_NO_CSUM_RESET |
>>>>> + BPF_F_ADJ_ROOM_FIXED_GSO)))
>>>> Under which case this new check will be hit?
>>> If a user supplies +ve len_diff and attempts to pass a DECAP flag.
>>> The commit message had
>>> Add flag validation to bpf_skb_net_grow() to reject invalid encap
>>> flags early.
>>
>> There is DECAP_MASK check in bpf_skb_adjust_room() and then !shrink is rejected. What am I missing?
>
> Duh, right.
>
> Do you prefer the do all the flag checking in bpf_skb_adjust_room or keep the encap/decap split?
>
The new decap flag checks added in patch 4? I do not have a strong
preference on whether they should be moved to shrink() or remain in
bpf_skb_adjust_room().
If the decap flag checks move into shrink(), it would also make sense to
move the corresponding length checks into grow() and shrink(). These
check refactoring probably needs another patch after the macro
refactoring patch mentioned earlier.
Likely still broken, maybe still worth to share compiler-tested code for
this. It is based on patch 3 (with the new flags check in grow). The
error return value can differ for some invalid shrink cases because of
the check ordering, but I do not think that matters.
diff --git a/net/core/filter.c b/net/core/filter.c
index de61503f06f6..895e94865a9f 100644
--- a/net/core/filter.c
+++ b/net/core/filter.c
@@ -3510,6 +3510,8 @@ static u32 bpf_skb_net_base_len(const struct
sk_buff *skb)
BPF_F_ADJ_ROOM_DECAP_MASK | \
BPF_F_ADJ_ROOM_NO_CSUM_RESET)
+#define BPF_SKB_MAX_LEN SKB_MAX_ALLOC
+
static int bpf_skb_net_grow(struct sk_buff *skb, u32 off, u32 len_diff,
u64 flags)
{
@@ -3518,6 +3520,7 @@ static int bpf_skb_net_grow(struct sk_buff *skb,
u32 off, u32 len_diff,
u16 mac_len = 0, inner_net = 0, inner_trans = 0;
const u8 meta_len = skb_metadata_len(skb);
unsigned int gso_type = SKB_GSO_DODGY;
+ u32 len_max = BPF_SKB_MAX_LEN;
int ret;
if (unlikely(flags & ~(BPF_F_ADJ_ROOM_ENCAP_MASK |
@@ -3525,6 +3528,9 @@ static int bpf_skb_net_grow(struct sk_buff *skb,
u32 off, u32 len_diff,
BPF_F_ADJ_ROOM_FIXED_GSO)))
return -EINVAL;
+ if (skb->len + len_diff > len_max && !skb_is_gso(skb))
+ return -ENOTSUPP;
+
if (skb_is_gso(skb) && !skb_is_gso_tcp(skb)) {
/* udp gso_size delineates datagrams, only allow if fixed */
if (!(skb_shinfo(skb)->gso_type & SKB_GSO_UDP_L4) ||
@@ -3632,6 +3638,8 @@ static int bpf_skb_net_grow(struct sk_buff *skb,
u32 off, u32 len_diff,
static int bpf_skb_net_shrink(struct sk_buff *skb, u32 off, u32 len_diff,
u64 flags)
{
+ u32 len_cur = skb->len - skb_network_offset(skb);
+ u32 len_min = bpf_skb_net_base_len(skb);
int ret;
if (unlikely(flags & ~(BPF_F_ADJ_ROOM_DECAP_MASK |
@@ -3639,6 +3647,22 @@ static int bpf_skb_net_shrink(struct sk_buff
*skb, u32 off, u32 len_diff,
BPF_F_ADJ_ROOM_NO_CSUM_RESET)))
return -EINVAL;
+ if (flags & BPF_F_ADJ_ROOM_DECAP_L3_MASK) {
+ switch (flags & BPF_F_ADJ_ROOM_DECAP_L3_MASK) {
+ case BPF_F_ADJ_ROOM_DECAP_L3_IPV4:
+ len_min = sizeof(struct iphdr);
+ break;
+ case BPF_F_ADJ_ROOM_DECAP_L3_IPV6:
+ len_min = sizeof(struct ipv6hdr);
+ break;
+ default:
+ return -EINVAL;
+ }
+ }
+
+ if (len_diff >= len_cur || len_cur - len_diff < len_min)
+ return -ENOTSUPP;
+
if (skb_is_gso(skb) && !skb_is_gso_tcp(skb)) {
/* udp gso_size delineates datagrams, only allow if fixed */
if (!(skb_shinfo(skb)->gso_type & SKB_GSO_UDP_L4) ||
@@ -3677,8 +3701,6 @@ static int bpf_skb_net_shrink(struct sk_buff *skb,
u32 off, u32 len_diff,
return 0;
}
-#define BPF_SKB_MAX_LEN SKB_MAX_ALLOC
-
BPF_CALL_4(sk_skb_adjust_room, struct sk_buff *, skb, s32, len_diff,
u32, mode, u64, flags)
{
@@ -3723,9 +3745,7 @@ static const struct bpf_func_proto
sk_skb_adjust_room_proto = {
BPF_CALL_4(bpf_skb_adjust_room, struct sk_buff *, skb, s32, len_diff,
u32, mode, u64, flags)
{
- u32 len_cur, len_diff_abs = abs(len_diff);
- u32 len_min = bpf_skb_net_base_len(skb);
- u32 len_max = BPF_SKB_MAX_LEN;
+ u32 len_diff_abs = abs(len_diff);
__be16 proto = skb->protocol;
bool shrink = len_diff < 0;
u32 off;
@@ -3750,29 +3770,6 @@ BPF_CALL_4(bpf_skb_adjust_room, struct sk_buff *,
skb, s32, len_diff,
return -ENOTSUPP;
}
- if (flags & BPF_F_ADJ_ROOM_DECAP_L3_MASK) {
- if (!shrink)
- return -EINVAL;
-
- switch (flags & BPF_F_ADJ_ROOM_DECAP_L3_MASK) {
- case BPF_F_ADJ_ROOM_DECAP_L3_IPV4:
- len_min = sizeof(struct iphdr);
- break;
- case BPF_F_ADJ_ROOM_DECAP_L3_IPV6:
- len_min = sizeof(struct ipv6hdr);
- break;
- default:
- return -EINVAL;
- }
- }
-
- len_cur = skb->len - skb_network_offset(skb);
- if ((shrink && (len_diff_abs >= len_cur ||
- len_cur - len_diff_abs < len_min)) ||
- (!shrink && (skb->len + len_diff_abs > len_max &&
- !skb_is_gso(skb))))
- return -ENOTSUPP;
-
ret = shrink ? bpf_skb_net_shrink(skb, off, len_diff_abs, flags) :
bpf_skb_net_grow(skb, off, len_diff_abs, flags);
if (!ret && !(flags & BPF_F_ADJ_ROOM_NO_CSUM_RESET))
next prev parent reply other threads:[~2026-03-27 19:03 UTC|newest]
Thread overview: 23+ messages / expand[flat|nested] mbox.gz Atom feed top
2026-03-18 13:42 [PATCH v2 0/5] bpf: skb_adjust_room helper refactor and tunnel decap flags Nick Hudson
2026-03-18 13:42 ` [PATCH v2 1/5] bpf: name the enum for BPF_FUNC_skb_adjust_room flags Nick Hudson
2026-03-21 0:39 ` Willem de Bruijn
2026-03-24 17:34 ` Martin KaFai Lau
2026-03-18 13:42 ` [PATCH v2 2/5] bpf: add BPF_F_ADJ_ROOM_DECAP_* flags for tunnel decapsulation Nick Hudson
2026-03-21 0:39 ` Willem de Bruijn
2026-03-18 13:42 ` [PATCH v2 3/5] bpf: add helper masks for ADJ_ROOM flags and encap validation Nick Hudson
2026-03-21 0:39 ` Willem de Bruijn
2026-03-24 18:12 ` Martin KaFai Lau
2026-03-26 17:02 ` Hudson, Nick
2026-03-26 17:49 ` Martin KaFai Lau
2026-03-27 10:55 ` Hudson, Nick
2026-03-27 19:02 ` Martin KaFai Lau [this message]
2026-03-18 13:42 ` [PATCH v2 4/5] bpf: allow new DECAP flags and add guard rails Nick Hudson
2026-03-18 20:02 ` Willem de Bruijn
2026-03-19 8:17 ` Hudson, Nick
2026-03-19 13:24 ` Willem de Bruijn
2026-03-21 0:40 ` Willem de Bruijn
2026-03-24 18:30 ` Martin KaFai Lau
2026-03-26 17:02 ` Hudson, Nick
2026-03-18 13:42 ` [PATCH v2 5/5] bpf: clear decap tunnel GSO state in skb_adjust_room Nick Hudson
2026-03-18 20:09 ` Willem de Bruijn
2026-03-18 20:01 ` [PATCH v2 0/5] bpf: skb_adjust_room helper refactor and tunnel decap flags Willem de Bruijn
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=af12c536-adcb-4071-9b25-15035273a217@linux.dev \
--to=martin.lau@linux.dev \
--cc=aglasgal@akamai.com \
--cc=andrii@kernel.org \
--cc=ast@kernel.org \
--cc=bpf@vger.kernel.org \
--cc=daniel@iogearbox.net \
--cc=davem@davemloft.net \
--cc=edumazet@google.com \
--cc=kuba@kernel.org \
--cc=linux-kernel@vger.kernel.org \
--cc=mtottenh@akamai.com \
--cc=netdev@vger.kernel.org \
--cc=nhudson@akamai.com \
--cc=pabeni@redhat.com \
--cc=willemdebruijn.kernel@gmail.com \
/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 a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox