public inbox for netdev@vger.kernel.org
 help / color / mirror / Atom feed
* [PATCH] selftests/bpf: Reject malformed IPv4/IPv6 skb test input
@ 2026-03-29 12:50 Sun Jian
  2026-03-29 13:24 ` bot+bpf-ci
  0 siblings, 1 reply; 2+ messages in thread
From: Sun Jian @ 2026-03-29 12:50 UTC (permalink / raw)
  To: ast, daniel, andrii
  Cc: martin.lau, eddyz87, song, yonghong.song, john.fastabend, kpsingh,
	sdf, haoluo, jolsa, davem, edumazet, kuba, pabeni, horms, bpf,
	netdev, linux-kernel, Sun Jian, syzbot+619b9ef527f510a57cfc

bpf_prog_test_run_skb() derives skb->protocol from the Ethernet header
through eth_type_trans(), but it does not verify that the provided
linear input is long enough to contain the corresponding L3 base
header.

This can construct an inconsistent skb for test_run: the packet can be
recognized as IPv6 while skb_headlen() still only covers ETH_HLEN
bytes. In that case, helpers such as bpf_skb_adjust_room() may compute
offsets based on the inferred protocol and operate on bytes beyond the
initialized linear data, which can trigger KMSAN.

Reject such malformed IPv4/IPv6 skb test input early by checking that
the linear head covers both the Ethernet header and the corresponding
IPv4/IPv6 base header before running the program.

Reported-by: syzbot+619b9ef527f510a57cfc@syzkaller.appspotmail.com
Closes: https://syzkaller.appspot.com/bug?extid=619b9ef527f510a57cfc
Signed-off-by: Sun Jian <sun.jian.kdev@gmail.com>
---
 net/bpf/test_run.c | 19 +++++++++++++++++++
 1 file changed, 19 insertions(+)

diff --git a/net/bpf/test_run.c b/net/bpf/test_run.c
index 178c4738e63b..65cfb408f52b 100644
--- a/net/bpf/test_run.c
+++ b/net/bpf/test_run.c
@@ -1118,6 +1118,25 @@ int bpf_prog_test_run_skb(struct bpf_prog *prog, const union bpf_attr *kattr,
 	skb->protocol = eth_type_trans(skb, dev);
 	skb_reset_network_header(skb);
 
+	switch (skb->protocol) {
+	case htons(ETH_P_IP):
+		if (skb_headlen(skb) < ETH_HLEN + sizeof(struct iphdr)) {
+			ret = -EINVAL;
+			goto out;
+		}
+		break;
+#if IS_ENABLED(CONFIG_IPV6)
+	case htons(ETH_P_IPV6):
+		if (skb_headlen(skb) < ETH_HLEN + sizeof(struct ipv6hdr)) {
+			ret = -EINVAL;
+			goto out;
+		}
+		break;
+#endif
+	default:
+		break;
+	}
+
 	switch (skb->protocol) {
 	case htons(ETH_P_IP):
 		sk->sk_family = AF_INET;

base-commit: cbfffcca2bf0622b601b7eaf477aa29035169184
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 2+ messages in thread

* Re: [PATCH] selftests/bpf: Reject malformed IPv4/IPv6 skb test input
  2026-03-29 12:50 [PATCH] selftests/bpf: Reject malformed IPv4/IPv6 skb test input Sun Jian
@ 2026-03-29 13:24 ` bot+bpf-ci
  0 siblings, 0 replies; 2+ messages in thread
From: bot+bpf-ci @ 2026-03-29 13:24 UTC (permalink / raw)
  To: sun.jian.kdev, ast, daniel, andrii
  Cc: martin.lau, eddyz87, song, yonghong.song, john.fastabend, kpsingh,
	sdf, haoluo, jolsa, davem, edumazet, kuba, pabeni, horms, bpf,
	netdev, linux-kernel, sun.jian.kdev, syzbot+619b9ef527f510a57cfc,
	ast, andrii, daniel, martin.lau, eddyz87, yonghong.song, clm,
	ihor.solodrai

[-- Attachment #1: Type: text/plain, Size: 1930 bytes --]

> diff --git a/net/bpf/test_run.c b/net/bpf/test_run.c
> index 4cd6b3ea1815..92888af89743 100644
> --- a/net/bpf/test_run.c
> +++ b/net/bpf/test_run.c
> @@ -1135,6 +1135,25 @@ int bpf_prog_test_run_skb(struct bpf_prog *prog, const union bpf_attr *kattr,
>  	skb->protocol = eth_type_trans(skb, dev);
>  	skb_reset_network_header(skb);
>
> +	switch (skb->protocol) {
> +	case htons(ETH_P_IP):
> +		if (skb_headlen(skb) < ETH_HLEN + sizeof(struct iphdr)) {

Should this threshold be sizeof(struct iphdr) rather than
ETH_HLEN + sizeof(struct iphdr)?

eth_type_trans() calls eth_skb_pull_mac() which does
skb_pull_inline(skb, ETH_HLEN), advancing skb->data past the
Ethernet header and reducing skb->len by ETH_HLEN. After that
pull, skb_headlen() no longer includes the Ethernet header bytes.

The existing code just below this new block uses the post-pull
value directly:

    if (sizeof(struct iphdr) <= skb_headlen(skb)) {
        sk->sk_rcv_saddr = ip_hdr(skb)->saddr;

With the current check, a 34-byte input (ETH_HLEN + sizeof(iphdr))
gives skb_headlen() == 20 after the pull, which fails the
20 < 14 + 20 comparison and is rejected even though it contains a
complete Ethernet and IPv4 header. The same issue applies to the
IPv6 case below.

> +			ret = -EINVAL;
> +			goto out;
> +		}
> +		break;
> +#if IS_ENABLED(CONFIG_IPV6)
> +	case htons(ETH_P_IPV6):
> +		if (skb_headlen(skb) < ETH_HLEN + sizeof(struct ipv6hdr)) {
> +			ret = -EINVAL;
> +			goto out;
> +		}
> +		break;
> +#endif

[ ... ]

This patch fixes a bug that has existed since bpf_prog_test_run_skb()
was first introduced. Should it carry a Fixes: tag?

Fixes: 1cf1cae963c2 ("bpf: introduce BPF_PROG_TEST_RUN command")


---
AI reviewed your patch. Please fix the bug or email reply why it's not a bug.
See: https://github.com/kernel-patches/vmtest/blob/master/ci/claude/README.md

CI run summary: https://github.com/kernel-patches/bpf/actions/runs/23709695537

^ permalink raw reply	[flat|nested] 2+ messages in thread

end of thread, other threads:[~2026-03-29 13:24 UTC | newest]

Thread overview: 2+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2026-03-29 12:50 [PATCH] selftests/bpf: Reject malformed IPv4/IPv6 skb test input Sun Jian
2026-03-29 13:24 ` bot+bpf-ci

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox