* [PATCH net] xdp: fix zero-copy frame layout
@ 2026-08-18 15:45 Weiming Shi
2026-08-19 15:49 ` sashiko-bot
2026-08-22 20:20 ` patchwork-bot+netdevbpf
0 siblings, 2 replies; 3+ messages in thread
From: Weiming Shi @ 2026-08-18 15:45 UTC (permalink / raw)
To: Alexei Starovoitov, Daniel Borkmann, David S. Miller,
Jakub Kicinski, Jesper Dangaard Brouer, John Fastabend,
Stanislav Fomichev, Eric Dumazet, Paolo Abeni, Simon Horman
Cc: netdev, bpf, linux-kernel, Björn Töpel, Xiang Mei,
stable
xdp_convert_zc_to_xdp_frame() clones an XSK packet into an order-0 page
and advertises PAGE_SIZE as its frame size. It allows the copied frame
to occupy the page tail needed by skb_shared_info and records zero
headroom even when metadata separates the frame header from packet data.
An AF_XDP zero-copy packet redirected through cpumap can therefore make
the skb overlap skb_shared_info or place it beyond the allocated page.
Limit the copied layout to SKB_WITH_OVERHEAD(PAGE_SIZE) and include the
metadata length in frame headroom. Redirect callers already handle a
NULL conversion result.
BUG: KASAN: slab-out-of-bounds in skb_gro_receive
Write of size 4 at addr ffff88800cf37004 by task cpumap/1/map:1/146
Call Trace:
skb_gro_receive (net/core/gro.c:174)
udp_gro_receive (net/ipv4/udp_offload.c:812)
inet_gro_receive (net/ipv4/af_inet.c:1539)
dev_gro_receive (net/core/gro.c:515)
gro_receive_skb (net/core/gro.c:633)
cpu_map_kthread_run (kernel/bpf/cpumap.c:395)
kthread (kernel/kthread.c:436)
ret_from_fork (arch/x86/kernel/process.c:164)
ret_from_fork_asm (arch/x86/entry/entry_64.S:255)
Kernel panic - not syncing: KASAN: panic_on_warn set ...
Fixes: b0d1beeff2a9 ("xdp: implement convert_to_xdp_frame for MEM_TYPE_ZERO_COPY")
Cc: stable@vger.kernel.org
Reported-by: Xiang Mei <xmei5@asu.edu>
Assisted-by: Codex:gpt-5.6
Signed-off-by: Weiming Shi <bestswngs@gmail.com>
---
net/core/xdp.c | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/net/core/xdp.c b/net/core/xdp.c
index 9890a30584ba..4bb97790b189 100644
--- a/net/core/xdp.c
+++ b/net/core/xdp.c
@@ -585,7 +585,7 @@ struct xdp_frame *xdp_convert_zc_to_xdp_frame(struct xdp_buff *xdp)
xdp->data - xdp->data_meta;
totsize = xdp->data_end - xdp->data + metasize;
- if (sizeof(*xdpf) + totsize > PAGE_SIZE)
+ if (sizeof(*xdpf) + totsize > SKB_WITH_OVERHEAD(PAGE_SIZE))
return NULL;
page = dev_alloc_page();
@@ -602,7 +602,7 @@ struct xdp_frame *xdp_convert_zc_to_xdp_frame(struct xdp_buff *xdp)
xdpf->data = addr + metasize;
xdpf->len = totsize - metasize;
- xdpf->headroom = 0;
+ xdpf->headroom = metasize;
xdpf->metasize = metasize;
xdpf->frame_sz = PAGE_SIZE;
xdpf->mem_type = MEM_TYPE_PAGE_ORDER0;
--
2.55.0
^ permalink raw reply related [flat|nested] 3+ messages in thread
* Re: [PATCH net] xdp: fix zero-copy frame layout
2026-08-18 15:45 [PATCH net] xdp: fix zero-copy frame layout Weiming Shi
@ 2026-08-19 15:49 ` sashiko-bot
2026-08-22 20:20 ` patchwork-bot+netdevbpf
1 sibling, 0 replies; 3+ messages in thread
From: sashiko-bot @ 2026-08-19 15:49 UTC (permalink / raw)
To: Weiming Shi; +Cc: bpf
Thank you for your contribution! Sashiko AI review found 2 potential issue(s) to consider:
Pre-existing issues:
- [Critical] Double free of XSK buffer and memory leak of `xdp_frame` page on redirect enqueue error.
- [High] Silent truncation of fragmented AF_XDP (MEM_TYPE_XSK_BUFF_POOL) multi-buffer packets during redirect.
--
--- Patch [1]: [PATCH net] xdp: fix zero-copy frame layout ---
commit 300f3eb2043fb6dcf3006d467327612f861ccc98
Author: Weiming Shi <bestswngs@gmail.com>
xdp: fix zero-copy frame layout
xdp_convert_zc_to_xdp_frame() clones an XSK packet into an order-0 page
and advertises PAGE_SIZE as its frame size. It allows the copied frame
to occupy the page tail needed by skb_shared_info and records zero
headroom even when metadata separates the frame header from packet data.
> diff --git a/net/core/xdp.c b/net/core/xdp.c
> index 0194e69da339a..1d679e8fd6493 100644
> --- a/net/core/xdp.c
> +++ b/net/core/xdp.c
> @@ -585,7 +585,7 @@ struct xdp_frame *xdp_convert_zc_to_xdp_frame(struct xdp_buff *xdp)
> xdp->data - xdp->data_meta;
> totsize = xdp->data_end - xdp->data + metasize;
>
> - if (sizeof(*xdpf) + totsize > PAGE_SIZE)
> + if (sizeof(*xdpf) + totsize > SKB_WITH_OVERHEAD(PAGE_SIZE))
> return NULL;
[Severity: High]
This isn't a bug introduced by this patch, but does this function silently
drop fragments when an AF_XDP zero-copy buffer contains them?
Looking at xdp_convert_zc_to_xdp_frame() in net/core/xdp.c, totsize is
calculated using only xdp->data_end - xdp->data. It ignores
xdp_buff_has_frags(xdp), meaning it allocates an order-0 page and copies only
the linear data.
Any attached fragments in the tailroom's skb_shared_info seem to be ignored,
and while they are freed via xsk_buff_free(xdp), the resulting xdp_frame is
silently truncated.
>
> page = dev_alloc_page();
[ ... ]
> @@ -602,7 +602,7 @@ struct xdp_frame *xdp_convert_zc_to_xdp_frame(struct xdp_buff *xdp)
>
> xdpf->data = addr + metasize;
> xdpf->len = totsize - metasize;
> - xdpf->headroom = 0;
> + xdpf->headroom = metasize;
> xdpf->metasize = metasize;
> xdpf->frame_sz = PAGE_SIZE;
> xdpf->mem_type = MEM_TYPE_PAGE_ORDER0;
[Severity: Critical]
This is a pre-existing issue, but does freeing the zero-copy buffer at the end
of this function cause a double-free and memory leak if the subsequent enqueue
operation fails?
In net/core/xdp.c:xdp_convert_zc_to_xdp_frame(), the original buffer is
explicitly freed via xsk_buff_free(xdp) upon successful conversion. It then
returns the new xdp_frame to xdp_do_redirect():
net/core/filter.c:xdp_do_redirect() {
...
return __xdp_do_redirect_frame(ri, dev, xdp_convert_buff_to_frame(xdp),
xdp_prog);
}
If __xdp_do_redirect_frame() fails, it returns the error code without freeing
the xdp_frame parameter:
net/core/filter.c:__xdp_do_redirect_frame() {
...
err:
_trace_xdp_redirect_map_err(dev, xdp_prog, fwd, map_type, map_id, ri->tgt_index, err);
return err;
}
Since the pointer is not saved in xdp_do_redirect(), the newly allocated
page appears to be leaked.
Additionally, because the error propagates back to the calling driver, the
driver might assume the subsystem did not consume the packet and proceed to
free the original ZC buffer again, potentially causing a double-free in the
XSK pool.
--
Sashiko AI review · https://sashiko.dev/#/patchset/20260818154516.793517-1-bestswngs@gmail.com?part=1
^ permalink raw reply [flat|nested] 3+ messages in thread
* Re: [PATCH net] xdp: fix zero-copy frame layout
2026-08-18 15:45 [PATCH net] xdp: fix zero-copy frame layout Weiming Shi
2026-08-19 15:49 ` sashiko-bot
@ 2026-08-22 20:20 ` patchwork-bot+netdevbpf
1 sibling, 0 replies; 3+ messages in thread
From: patchwork-bot+netdevbpf @ 2026-08-22 20:20 UTC (permalink / raw)
To: Weiming Shi
Cc: ast, daniel, davem, kuba, hawk, john.fastabend, sdf, edumazet,
pabeni, horms, netdev, bpf, linux-kernel, bjorn, xmei5, stable
Hello:
This patch was applied to netdev/net.git (main)
by Jakub Kicinski <kuba@kernel.org>:
On Tue, 18 Aug 2026 23:45:15 +0800 you wrote:
> xdp_convert_zc_to_xdp_frame() clones an XSK packet into an order-0 page
> and advertises PAGE_SIZE as its frame size. It allows the copied frame
> to occupy the page tail needed by skb_shared_info and records zero
> headroom even when metadata separates the frame header from packet data.
> An AF_XDP zero-copy packet redirected through cpumap can therefore make
> the skb overlap skb_shared_info or place it beyond the allocated page.
>
> [...]
Here is the summary with links:
- [net] xdp: fix zero-copy frame layout
https://git.kernel.org/netdev/net/c/71283aaa6c65
You are awesome, thank you!
--
Deet-doot-dot, I am a bot.
https://korg.docs.kernel.org/patchwork/pwbot.html
^ permalink raw reply [flat|nested] 3+ messages in thread
end of thread, other threads:[~2026-08-22 20:21 UTC | newest]
Thread overview: 3+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2026-08-18 15:45 [PATCH net] xdp: fix zero-copy frame layout Weiming Shi
2026-08-19 15:49 ` sashiko-bot
2026-08-22 20:20 ` patchwork-bot+netdevbpf
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.