diff options
author | Craig Gallek <kraig@google.com> | 2017-10-19 15:00:29 -0400 |
---|---|---|
committer | Bruno Martins <bgcngm@gmail.com> | 2022-10-28 15:39:30 +0100 |
commit | fcf3e7bc7203450a675facc3b1af5c4e844a85a2 (patch) | |
tree | 75542b03242a3dc62cb960872c65ea2a1ad97fe7 /net/ipv4/udp.c | |
parent | df03c8cf024a20771245c3ebf783bde96e9bb708 (diff) |
soreuseport: fix initialization race
[ Upstream commit 1b5f962e71bfad6284574655c406597535c3ea7a ]
Syzkaller stumbled upon a way to trigger
WARNING: CPU: 1 PID: 13881 at net/core/sock_reuseport.c:41
reuseport_alloc+0x306/0x3b0 net/core/sock_reuseport.c:39
There are two initialization paths for the sock_reuseport structure in a
socket: Through the udp/tcp bind paths of SO_REUSEPORT sockets or through
SO_ATTACH_REUSEPORT_[CE]BPF before bind. The existing implementation
assumedthat the socket lock protected both of these paths when it actually
only protects the SO_ATTACH_REUSEPORT path. Syzkaller triggered this
double allocation by running these paths concurrently.
This patch moves the check for double allocation into the reuseport_alloc
function which is protected by a global spin lock.
Fixes: e32ea7e74727 ("soreuseport: fast reuseport UDP socket selection")
Fixes: c125e80b8868 ("soreuseport: fast reuseport TCP socket selection")
Signed-off-by: Craig Gallek <kraig@google.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
Change-Id: I16aa997b37285b6cc613ed6073acdd37b5ac3a2d
Diffstat (limited to 'net/ipv4/udp.c')
-rw-r--r-- | net/ipv4/udp.c | 5 |
1 files changed, 1 insertions, 4 deletions
diff --git a/net/ipv4/udp.c b/net/ipv4/udp.c index 766431c6e321..e271d94d632d 100644 --- a/net/ipv4/udp.c +++ b/net/ipv4/udp.c @@ -224,10 +224,7 @@ static int udp_reuseport_add_sock(struct sock *sk, struct udp_hslot *hslot, } } - /* Initial allocation may have already happened via setsockopt */ - if (!rcu_access_pointer(sk->sk_reuseport_cb)) - return reuseport_alloc(sk); - return 0; + return reuseport_alloc(sk); } /** |