Skip to content

Commit 19a07a4

Browse files
CKI Backport BotHangbin Liu
authored andcommitted
ndisc: extend RCU protection in ndisc_send_skb()
JIRA: https://issues.redhat.com/browse/RHEL-115578 CVE: CVE-2025-21760 commit ed6ae1f Author: Eric Dumazet <edumazet@google.com> Date: Fri Feb 7 13:58:39 2025 +0000 ndisc: extend RCU protection in ndisc_send_skb() ndisc_send_skb() can be called without RTNL or RCU held. Acquire rcu_read_lock() earlier, so that we can use dev_net_rcu() and avoid a potential UAF. Fixes: 1762f7e ("[NETNS][IPV6] ndisc - make socket control per namespace") Signed-off-by: Eric Dumazet <edumazet@google.com> Reviewed-by: David Ahern <dsahern@kernel.org> Reviewed-by: Kuniyuki Iwashima <kuniyu@amazon.com> Link: https://patch.msgid.link/20250207135841.1948589-8-edumazet@google.com Signed-off-by: Jakub Kicinski <kuba@kernel.org> Signed-off-by: CKI Backport Bot <cki-ci-bot+cki-gitlab-backport-bot@redhat.com>
1 parent c1d0fce commit 19a07a4

File tree

1 file changed

+8
-4
lines changed

1 file changed

+8
-4
lines changed

net/ipv6/ndisc.c

Lines changed: 8 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -471,23 +471,28 @@ static void ip6_nd_hdr(struct sk_buff *skb,
471471
void ndisc_send_skb(struct sk_buff *skb, const struct in6_addr *daddr,
472472
const struct in6_addr *saddr)
473473
{
474+
struct icmp6hdr *icmp6h = icmp6_hdr(skb);
474475
struct dst_entry *dst = skb_dst(skb);
475-
struct net *net = dev_net(skb->dev);
476-
struct sock *sk = net->ipv6.ndisc_sk;
477476
struct inet6_dev *idev;
477+
struct net *net;
478+
struct sock *sk;
478479
int err;
479-
struct icmp6hdr *icmp6h = icmp6_hdr(skb);
480480
u8 type;
481481

482482
type = icmp6h->icmp6_type;
483483

484+
rcu_read_lock();
485+
486+
net = dev_net_rcu(skb->dev);
487+
sk = net->ipv6.ndisc_sk;
484488
if (!dst) {
485489
struct flowi6 fl6;
486490
int oif = skb->dev->ifindex;
487491

488492
icmpv6_flow_init(sk, &fl6, type, saddr, daddr, oif);
489493
dst = icmp6_dst_alloc(skb->dev, &fl6);
490494
if (IS_ERR(dst)) {
495+
rcu_read_unlock();
491496
kfree_skb(skb);
492497
return;
493498
}
@@ -502,7 +507,6 @@ void ndisc_send_skb(struct sk_buff *skb, const struct in6_addr *daddr,
502507

503508
ip6_nd_hdr(skb, saddr, daddr, READ_ONCE(inet6_sk(sk)->hop_limit), skb->len);
504509

505-
rcu_read_lock();
506510
idev = __in6_dev_get(dst->dev);
507511
IP6_INC_STATS(net, idev, IPSTATS_MIB_OUTREQUESTS);
508512

0 commit comments

Comments
 (0)