* [PATCH net] mpls: reload header after pskb_may_pull()
@ 2026-08-14 9:54 Qing Ming
2026-08-18 7:55 ` Simon Horman
2026-08-18 9:20 ` patchwork-bot+netdevbpf
0 siblings, 2 replies; 3+ messages in thread
From: Qing Ming @ 2026-08-14 9:54 UTC (permalink / raw)
To: David S. Miller, Eric Dumazet, Jakub Kicinski, Paolo Abeni
Cc: Simon Horman, Kuniyuki Iwashima, Guillaume Nault, Sabrina Dubroca,
David Ahern, Robert Shearman, netdev, linux-kernel, Qing Ming,
stable
mpls_select_multipath() calls mpls_multipath_hash() to choose a nexthop
when an MPLS route has multiple nexthops. While walking the MPLS label
stack, the hash routine caches hdr for the current label. After finding
the bottom-of-stack label, it calls pskb_may_pull() before reading the
inner IP header.
If an skb is constructed with the inner IP header in nonlinear data and
insufficient tailroom in the linear head, pskb_may_pull() calls
pskb_expand_head() to replace the skb head and free the old one. This
leaves hdr pointing to freed memory. The IPv6 path can invalidate hdr
again when it performs a second pull for the larger header.
The issue was found through static analysis. A reproducer sending a legal
Geneve packet through a bareudp/MPLS multipath setup triggered the same
KASAN report in 2 of 2 unpatched runs:
BUG: KASAN: slab-use-after-free in mpls_select_multipath
Read of size 1 at addr ffff88800ecc6e20 by task ksoftirqd/1/23
Call Trace:
mpls_select_multipath
mpls_forward
__netif_receive_skb_list_core
netif_receive_skb_list_internal
napi_complete_done
gro_cell_poll
__napi_poll
net_rx_action
Freed by task 23:
kfree
pskb_expand_head
__pskb_pull_tail
mpls_select_multipath
Reload hdr from the current skb head after each successful pull before
deriving the inner IPv4 or IPv6 header pointer.
Fixes: 9f427a0e474a ("net: mpls: Fix multipath selection for LSR use case")
Cc: stable@vger.kernel.org
Signed-off-by: Qing Ming <a0yami@mailbox.org>
---
net/mpls/af_mpls.c | 2 ++
1 file changed, 2 insertions(+)
diff --git a/net/mpls/af_mpls.c b/net/mpls/af_mpls.c
index 961be5054a03..17b78dcbf8ab 100644
--- a/net/mpls/af_mpls.c
+++ b/net/mpls/af_mpls.c
@@ -221,6 +221,7 @@ static u32 mpls_multipath_hash(struct mpls_route *rt, struct sk_buff *skb)
if (pskb_may_pull(skb, mpls_hdr_len + sizeof(struct iphdr))) {
const struct iphdr *v4hdr;
+ hdr = mpls_hdr(skb) + label_index;
v4hdr = (const struct iphdr *)(hdr + 1);
if (v4hdr->version == 4) {
hash = jhash_3words(ntohl(v4hdr->saddr),
@@ -231,6 +232,7 @@ static u32 mpls_multipath_hash(struct mpls_route *rt, struct sk_buff *skb)
sizeof(struct ipv6hdr))) {
const struct ipv6hdr *v6hdr;
+ hdr = mpls_hdr(skb) + label_index;
v6hdr = (const struct ipv6hdr *)(hdr + 1);
hash = __ipv6_addr_jhash(&v6hdr->saddr, hash);
hash = __ipv6_addr_jhash(&v6hdr->daddr, hash);
base-commit: 24ef02f934eeb48830cff6b739abc3c62b1d107b
--
2.53.0
^ permalink raw reply related [flat|nested] 3+ messages in thread* Re: [PATCH net] mpls: reload header after pskb_may_pull()
2026-08-14 9:54 [PATCH net] mpls: reload header after pskb_may_pull() Qing Ming
@ 2026-08-18 7:55 ` Simon Horman
2026-08-18 9:20 ` patchwork-bot+netdevbpf
1 sibling, 0 replies; 3+ messages in thread
From: Simon Horman @ 2026-08-18 7:55 UTC (permalink / raw)
To: Qing Ming
Cc: David S. Miller, Eric Dumazet, Jakub Kicinski, Paolo Abeni,
Kuniyuki Iwashima, Guillaume Nault, Sabrina Dubroca, David Ahern,
Robert Shearman, netdev, linux-kernel, stable
On Fri, Aug 14, 2026 at 05:54:04PM +0800, Qing Ming wrote:
> mpls_select_multipath() calls mpls_multipath_hash() to choose a nexthop
> when an MPLS route has multiple nexthops. While walking the MPLS label
> stack, the hash routine caches hdr for the current label. After finding
> the bottom-of-stack label, it calls pskb_may_pull() before reading the
> inner IP header.
>
> If an skb is constructed with the inner IP header in nonlinear data and
> insufficient tailroom in the linear head, pskb_may_pull() calls
> pskb_expand_head() to replace the skb head and free the old one. This
> leaves hdr pointing to freed memory. The IPv6 path can invalidate hdr
> again when it performs a second pull for the larger header.
>
> The issue was found through static analysis. A reproducer sending a legal
> Geneve packet through a bareudp/MPLS multipath setup triggered the same
> KASAN report in 2 of 2 unpatched runs:
>
> BUG: KASAN: slab-use-after-free in mpls_select_multipath
> Read of size 1 at addr ffff88800ecc6e20 by task ksoftirqd/1/23
>
> Call Trace:
> mpls_select_multipath
> mpls_forward
> __netif_receive_skb_list_core
> netif_receive_skb_list_internal
> napi_complete_done
> gro_cell_poll
> __napi_poll
> net_rx_action
>
> Freed by task 23:
> kfree
> pskb_expand_head
> __pskb_pull_tail
> mpls_select_multipath
>
> Reload hdr from the current skb head after each successful pull before
> deriving the inner IPv4 or IPv6 header pointer.
>
> Fixes: 9f427a0e474a ("net: mpls: Fix multipath selection for LSR use case")
> Cc: stable@vger.kernel.org
> Signed-off-by: Qing Ming <a0yami@mailbox.org>
Reviewed-by: Simon Horman <horms@kernel.org>
^ permalink raw reply [flat|nested] 3+ messages in thread* Re: [PATCH net] mpls: reload header after pskb_may_pull()
2026-08-14 9:54 [PATCH net] mpls: reload header after pskb_may_pull() Qing Ming
2026-08-18 7:55 ` Simon Horman
@ 2026-08-18 9:20 ` patchwork-bot+netdevbpf
1 sibling, 0 replies; 3+ messages in thread
From: patchwork-bot+netdevbpf @ 2026-08-18 9:20 UTC (permalink / raw)
To: Qing Ming
Cc: davem, edumazet, kuba, pabeni, horms, kuniyu, gnault, sd, dsahern,
rshearma, netdev, linux-kernel, stable
Hello:
This patch was applied to netdev/net.git (main)
by Paolo Abeni <pabeni@redhat.com>:
On Fri, 14 Aug 2026 17:54:04 +0800 you wrote:
> mpls_select_multipath() calls mpls_multipath_hash() to choose a nexthop
> when an MPLS route has multiple nexthops. While walking the MPLS label
> stack, the hash routine caches hdr for the current label. After finding
> the bottom-of-stack label, it calls pskb_may_pull() before reading the
> inner IP header.
>
> If an skb is constructed with the inner IP header in nonlinear data and
> insufficient tailroom in the linear head, pskb_may_pull() calls
> pskb_expand_head() to replace the skb head and free the old one. This
> leaves hdr pointing to freed memory. The IPv6 path can invalidate hdr
> again when it performs a second pull for the larger header.
>
> [...]
Here is the summary with links:
- [net] mpls: reload header after pskb_may_pull()
https://git.kernel.org/netdev/net/c/29e63b8d9fc1
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-18 9:20 UTC | newest]
Thread overview: 3+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2026-08-14 9:54 [PATCH net] mpls: reload header after pskb_may_pull() Qing Ming
2026-08-18 7:55 ` Simon Horman
2026-08-18 9:20 ` patchwork-bot+netdevbpf
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox