mptcp: fix a couple of races
Subsystems (3)
Paolo Abeni
maintainercover mptcp: fix a couple of races
The first patch addresses a division by zero issue reported by Eric, the second one solves a similar issue found by code inspection while investigating the former.
Paolo Abeni (2):
mptcp: error out earlier on disconnect
mptcp: cope racing subflow creation in mptcp_rcv_space_adjust
net/mptcp/protocol.c | 16 +++++++++++----- 1 file changed, 11 insertions(+), 5 deletions(-)
Signature · 1 line
2.45.2
Paolo Abeni
maintainerPATCH 1/2 mptcp: error out earlier on disconnect
Eric reported a division by zero splat in the MPTCP protocol:
Oops: divide error: 0000 [#1] PREEMPT SMP KASAN PTI CPU: 1 UID: 0 PID: 6094 Comm: syz-executor317 Not tainted 6.12.0-rc5-syzkaller-00291-g05b92660cdfe #0 Hardware name: Google Google Compute Engine/Google Compute Engine, BIOS Google 09/13/2024 RIP: 0010:__tcp_select_window+0x5b4/0x1310 net/ipv4/tcp_output.c:3163 Code: f6 44 01 e3 89 df e8 9b 75 09 f8 44 39 f3 0f 8d 11 ff ff ff e8
0d 74 09 f8 45 89 f4 e9 04 ff ff ff e8 00 74 09 f8 44 89 f0 99 <f7> 7c 24 14 41 29 d6 45 89 f4 e9 ec fe ff ff e8 e8 73 09 f8 48 89
RSP: 0018:ffffc900041f7930 EFLAGS: 00010293
RAX: 0000000000017e67 RBX: 0000000000017e67 RCX: ffffffff8983314b
RDX: 0000000000000000 RSI: ffffffff898331b0 RDI: 0000000000000004
RBP: 00000000005d6000 R08: 0000000000000004 R09: 0000000000017e67
R10: 0000000000003e80 R11: 0000000000000000 R12: 0000000000003e80
R13: ffff888031d9b440 R14: 0000000000017e67 R15: 00000000002eb000
FS: 00007feb5d7f16c0(0000) GS:ffff8880b8700000(0000) knlGS:0000000000000000
CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033
CR2: 00007feb5d8adbb8 CR3: 0000000074e4c000 CR4: 00000000003526f0
DR0: 0000000000000000 DR1: 0000000000000000 DR2: 0000000000000000
DR3: 0000000000000000 DR6: 00000000fffe0ff0 DR7: 0000000000000400
Call Trace: <TASK> __tcp_cleanup_rbuf+0x3e7/0x4b0 net/ipv4/tcp.c:1493 mptcp_rcv_space_adjust net/mptcp/protocol.c:2085 [inline] mptcp_recvmsg+0x2156/0x2600 net/mptcp/protocol.c:2289 inet_recvmsg+0x469/0x6a0 net/ipv4/af_inet.c:885 sock_recvmsg_nosec net/socket.c:1051 [inline] sock_recvmsg+0x1b2/0x250 net/socket.c:1073 __sys_recvfrom+0x1a5/0x2e0 net/socket.c:2265 __do_sys_recvfrom net/socket.c:2283 [inline] __se_sys_recvfrom net/socket.c:2279 [inline] __x64_sys_recvfrom+0xe0/0x1c0 net/socket.c:2279 do_syscall_x64 arch/x86/entry/common.c:52 [inline] do_syscall_64+0xcd/0x250 arch/x86/entry/common.c:83 entry_SYSCALL_64_after_hwframe+0x77/0x7f RIP: 0033:0x7feb5d857559 Code: 28 00 00 00 75 05 48 83 c4 28 c3 e8 51 18 00 00 90 48 89 f8 48
89 f7 48 89 d6 48 89 ca 4d 89 c2 4d 89 c8 4c 8b 4c 24 08 0f 05 <48> 3d 01 f0 ff ff 73 01 c3 48 c7 c1 b0 ff ff ff f7 d8 64 89 01 48
RSP: 002b:00007feb5d7f1208 EFLAGS: 00000246 ORIG_RAX: 000000000000002d
RAX: ffffffffffffffda RBX: 00007feb5d8e1318 RCX: 00007feb5d857559
RDX: 000000800000000e RSI: 0000000000000000 RDI: 0000000000000003
RBP: 00007feb5d8e1310 R08: 0000000000000000 R09: ffffffff81000000
R10: 0000000000000100 R11: 0000000000000246 R12: 00007feb5d8e131c
R13: 00007feb5d8ae074 R14: 000000800000000e R15: 00000000fffffdef
and provided a nice reproducer.
The root cause is the current bad handling of racing disconnect. After the blamed commit below, sk_wait_data() can return (with error) with the underlying socket disconnected and a zero rcv_mss.
Catch the error and return without performing any additional operations on the current socket.
--- net/mptcp/protocol.c | 13 +++++++++---- 1 file changed, 9 insertions(+), 4 deletions(-)
net/mptcp/protocol.c +9 -4
@@ -2205,7 +2205,7 @@ static int mptcp_recvmsg(struct sock *sk, struct msghdr *msg, size_t len, cmsg_flags =MPTCP_CMSG_INQ ;while (copied < len) { -int bytes_read; +int err, bytes_read; bytes_read =__mptcp_recvmsg_mskq (msk, msg, len - copied, flags, &tss, &cmsg_flags);if (unlikely (bytes_read <0 )) {
@@ -2267,9 +2267,16 @@ static int mptcp_recvmsg(struct sock *sk, struct msghdr *msg, size_t len, }pr_debug ("block timeout %ld\n" , timeo); -sk_wait_data (sk, &timeo,NULL ); +mptcp_rcv_space_adjust (msk, copied); + err =sk_wait_data (sk, &timeo,NULL ); +if (err <0 ) { + err = copied ? : err; + goto out_err; + } } +mptcp_rcv_space_adjust (msk, copied); + out_err:if (cmsg_flags && copied >=0 ) {if (cmsg_flags &MPTCP_CMSG_TS )
@@ -2285,8 +2292,6 @@ static int mptcp_recvmsg(struct sock *sk, struct msghdr *msg, size_t len,pr_debug ("msk=%p rx queue empty=%d:%d copied=%d\n" , msk,skb_queue_empty_lockless (&sk->sk_receive_queue),skb_queue_empty (&msk->receive_queue), copied); -if (!(flags &MSG_PEEK )) -mptcp_rcv_space_adjust (msk, copied);release_sock (sk);return copied;
Signature · 1 line
2.45.2
Paolo Abeni
maintainerPATCH 2/2 mptcp: cope racing subflow creation in mptcp_rcv_space_adjust
In reply to Paolo AbeniAdditional active subflows - i.e. created by the in kernel path manager - are included into the subflow list before starting the 3whs.
A racing recvmsg() spooling data received on an already established subflow would unconditionally call tcp_cleanup_rbuf() on all the current subflows, potentially hitting a divide by zero error on the newly created ones.
Explicitly check that the subflow is in a suitable state before invoking tcp_cleanup_rbuf().
--- net/mptcp/protocol.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-)
net/mptcp/protocol.c +2 -1
@@ -2082,7 +2082,8 @@ static void mptcp_rcv_space_adjust(struct mptcp_sock *msk, int copied) slow =lock_sock_fast (ssk);WRITE_ONCE (ssk->sk_rcvbuf, rcvbuf);WRITE_ONCE (tcp_sk (ssk)->window_clamp, window_clamp); -tcp_cleanup_rbuf (ssk,1 ); +if (tcp_can_send_ack (ssk)) +tcp_cleanup_rbuf (ssk,1 );unlock_sock_fast (ssk, slow); } }
Signature · 1 line
2.45.2
Hi Paolo,
Thank you for your modifications, that's great!
Our CI did some validations and here is its report:
- KVM Validation: normal: Success! ✅
- KVM Validation: debug: Success! ✅
- KVM Validation: btf-normal (only bpftest_all): Success! ✅
- KVM Validation: btf-debug (only bpftest_all): Success! ✅
- Task: https://github.com/multipath-tcp/mptcp_net-next/actions/runs/11741082429
Initiator: Patchew Applier
Commits: https://github.com/multipath-tcp/mptcp_net-next/commits/ea7fd41efff4
Patchwork: https://patchwork.kernel.org/project/mptcp/list/?series=907752
If there are some issues, you can reproduce them using the same environment as the one used by the CI thanks to a docker image, e.g.:
$ cd [kernel source code]
$ docker run -v "${PWD}:${PWD}:rw" -w "${PWD}" --privileged --rm -it \
--pull always mptcp/mptcp-upstream-virtme-docker:latest \
auto-normalFor more details:
https://github.com/multipath-tcp/mptcp-upstream-virtme-docker
Please note that despite all the efforts that have been already done to have a stable tests suite when executed on a public CI like here, it is possible some reported issues are not due to your modifications. Still, do not hesitate to help us improve that ;-)
Cheers,
MPTCP GH Action bot
Bot operated by Matthieu Baerts (NGI0 Core)
Hi Paolo,
Quoted 7 lines · Paolo Abeni
The first patch addresses a division by zero issue reported by Eric, the second one solves a similar issue found by code inspection while investigating the former.
Paolo Abeni (2):
mptcp: error out earlier on disconnect
mptcp: cope racing subflow creation inmptcp_rcv_space_adjust
Thank you for the patches! This looks good to me and can be applied in 'net' directly.
Cheers,
Matt
Signature · 1 line
Sponsored by the NGI0 Core fund.
Matthieu Baerts
maintainerHello,
(MPTCP ML only)
Quoted 7 lines · Matthieu Baerts
Hi Paolo,
Quoted 4 lines · Paolo Abeni
The first patch addresses a division by zero issue reported by Eric, the second one solves a similar issue found by code inspection while investigating the former.
Quoted 6 lines
Quoted 3 lines
Paolo Abeni (2):
mptcp: error out earlier on disconnect
mptcp: cope racing subflow creation inmptcp_rcv_space_adjustThank you for the patches! This looks good to me and can be applied in 'net' directly.
FYI, I also applied these patches in our tree, fixes for -net:
New patches for t/upstream-net and t/upstream:
- b189b3050a9d: mptcp: error out earlier on disconnect
- 8f738a68cd74: mptcp: cope racing subflow creation in mptcp_rcv_space_adjust
- Results: 3cb39141befa..3f011e8dae3c (export-net)
- Results: 2c114d530011..fe15020312c8 (export)
Tests are now in progress:
- export-net:
https://github.com/multipath-tcp/mptcp_net-next/commit/4ebfa44b9230463c69b57a0b2b0a91ec4b0ad10d/checks
- export:
https://github.com/multipath-tcp/mptcp_net-next/commit/95e17c17557397eafcd64d7af7e7e2c8f9b01025/checks
Cheers,
Matt
Signature · 1 line
Sponsored by the NGI0 Core fund.
This series was applied to netdev/net.git (main) by Jakub Kicinski <[email protected]>:
Hello:
This series was applied to netdev/net.git (main)
by Jakub Kicinski <[email protected]>:
Quoted 9 lines · On Fri, 8 Nov 2024 11:58:15 +0100 you wrote:
The first patch addresses a division by zero issue reported by Eric, the second one solves a similar issue found by code inspection while investigating the former.
Paolo Abeni (2):
mptcp: error out earlier on disconnect
mptcp: cope racing subflow creation inmptcp_rcv_space_adjust[...]
Here is the summary with links:
- [net,1/2] mptcp: error out earlier on disconnect
https://git.kernel.org/netdev/net/c/581302298524 - [net,2/2] mptcp: cope racing subflow creation in mptcp_rcv_space_adjust https://git.kernel.org/netdev/net/c/ce7356ae3594
You are awesome, thank you!
Signature · 2 lines
Deet-doot-dot, I am a bot. https://korg.docs.kernel.org/patchwork/pwbot.html