From: Eric Dumazet Date: Thu, 26 Feb 2026 08:29:22 +0000 (+0000) Subject: netfilter: nft_meta: no longer acquire sk_callback_lock in nft_meta_get_eval_skugid() X-Git-Url: http://git.ipfire.org/gitweb.cgi?a=commitdiff_plain;h=afc2125de7414be3a31f5c09724c0375a57f5eae;p=thirdparty%2Fkernel%2Flinux.git netfilter: nft_meta: no longer acquire sk_callback_lock in nft_meta_get_eval_skugid() After commit 983512f3a87f ("net: Drop the lock in skb_may_tx_timestamp()") from Sebastian Andrzej Siewior, apply the same logic in nft_meta_get_eval_skugid() to avoid touching sk->sk_callback_lock. Signed-off-by: Eric Dumazet Signed-off-by: Florian Westphal --- diff --git a/net/netfilter/nft_meta.c b/net/netfilter/nft_meta.c index 983158274c68d..d0df6cf374d1a 100644 --- a/net/netfilter/nft_meta.c +++ b/net/netfilter/nft_meta.c @@ -131,33 +131,36 @@ nft_meta_get_eval_skugid(enum nft_meta_keys key, u32 *dest, const struct nft_pktinfo *pkt) { - struct sock *sk = skb_to_full_sk(pkt->skb); - struct socket *sock; + const struct sock *sk = skb_to_full_sk(pkt->skb); + const struct socket *sock; + const struct file *file; if (!sk || !sk_fullsock(sk) || !net_eq(nft_net(pkt), sock_net(sk))) return false; - read_lock_bh(&sk->sk_callback_lock); - sock = sk->sk_socket; - if (!sock || !sock->file) { - read_unlock_bh(&sk->sk_callback_lock); + /* The sk pointer remains valid as long as the skb is. The sk_socket and + * file pointer may become NULL if the socket is closed. Both structures + * (including file->cred) are RCU freed which means they can be accessed + * within a RCU read section. + */ + sock = READ_ONCE(sk->sk_socket); + file = sock ? READ_ONCE(sock->file) : NULL; + if (!file) return false; - } switch (key) { case NFT_META_SKUID: *dest = from_kuid_munged(sock_net(sk)->user_ns, - sock->file->f_cred->fsuid); + file->f_cred->fsuid); break; case NFT_META_SKGID: *dest = from_kgid_munged(sock_net(sk)->user_ns, - sock->file->f_cred->fsgid); + file->f_cred->fsgid); break; default: break; } - read_unlock_bh(&sk->sk_callback_lock); return true; }