Skip to content

Commit 91b493f

Browse files
Paolo Abenigregkh
authored andcommitted
mptcp: don't always assume copied data in mptcp_cleanup_rbuf()
commit 551844f26da2a9f76c0a698baaffa631d1178645 upstream. Under some corner cases the MPTCP protocol can end-up invoking mptcp_cleanup_rbuf() when no data has been copied, but such helper assumes the opposite condition. Explicitly drop such assumption and performs the costly call only when strictly needed - before releasing the msk socket lock. Fixes: fd89767 ("mptcp: be careful on MPTCP-level ack.") Cc: [email protected] Signed-off-by: Paolo Abeni <[email protected]> Reviewed-by: Mat Martineau <[email protected]> Signed-off-by: Matthieu Baerts (NGI0) <[email protected]> Link: https://patch.msgid.link/[email protected] Signed-off-by: Jakub Kicinski <[email protected]> Signed-off-by: Greg Kroah-Hartman <[email protected]>
1 parent cbdb6a4 commit 91b493f

File tree

1 file changed

+9
-9
lines changed

1 file changed

+9
-9
lines changed

net/mptcp/protocol.c

Lines changed: 9 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -538,13 +538,13 @@ static void mptcp_send_ack(struct mptcp_sock *msk)
538538
mptcp_subflow_send_ack(mptcp_subflow_tcp_sock(subflow));
539539
}
540540

541-
static void mptcp_subflow_cleanup_rbuf(struct sock *ssk)
541+
static void mptcp_subflow_cleanup_rbuf(struct sock *ssk, int copied)
542542
{
543543
bool slow;
544544

545545
slow = lock_sock_fast(ssk);
546546
if (tcp_can_send_ack(ssk))
547-
tcp_cleanup_rbuf(ssk, 1);
547+
tcp_cleanup_rbuf(ssk, copied);
548548
unlock_sock_fast(ssk, slow);
549549
}
550550

@@ -561,22 +561,22 @@ static bool mptcp_subflow_could_cleanup(const struct sock *ssk, bool rx_empty)
561561
(ICSK_ACK_PUSHED2 | ICSK_ACK_PUSHED)));
562562
}
563563

564-
static void mptcp_cleanup_rbuf(struct mptcp_sock *msk)
564+
static void mptcp_cleanup_rbuf(struct mptcp_sock *msk, int copied)
565565
{
566566
int old_space = READ_ONCE(msk->old_wspace);
567567
struct mptcp_subflow_context *subflow;
568568
struct sock *sk = (struct sock *)msk;
569569
int space = __mptcp_space(sk);
570570
bool cleanup, rx_empty;
571571

572-
cleanup = (space > 0) && (space >= (old_space << 1));
573-
rx_empty = !__mptcp_rmem(sk);
572+
cleanup = (space > 0) && (space >= (old_space << 1)) && copied;
573+
rx_empty = !__mptcp_rmem(sk) && copied;
574574

575575
mptcp_for_each_subflow(msk, subflow) {
576576
struct sock *ssk = mptcp_subflow_tcp_sock(subflow);
577577

578578
if (cleanup || mptcp_subflow_could_cleanup(ssk, rx_empty))
579-
mptcp_subflow_cleanup_rbuf(ssk);
579+
mptcp_subflow_cleanup_rbuf(ssk, copied);
580580
}
581581
}
582582

@@ -2195,9 +2195,6 @@ static int mptcp_recvmsg(struct sock *sk, struct msghdr *msg, size_t len,
21952195

21962196
copied += bytes_read;
21972197

2198-
/* be sure to advertise window change */
2199-
mptcp_cleanup_rbuf(msk);
2200-
22012198
if (skb_queue_empty(&msk->receive_queue) && __mptcp_move_skbs(msk))
22022199
continue;
22032200

@@ -2249,13 +2246,16 @@ static int mptcp_recvmsg(struct sock *sk, struct msghdr *msg, size_t len,
22492246
}
22502247

22512248
pr_debug("block timeout %ld\n", timeo);
2249+
mptcp_cleanup_rbuf(msk, copied);
22522250
err = sk_wait_data(sk, &timeo, NULL);
22532251
if (err < 0) {
22542252
err = copied ? : err;
22552253
goto out_err;
22562254
}
22572255
}
22582256

2257+
mptcp_cleanup_rbuf(msk, copied);
2258+
22592259
out_err:
22602260
if (cmsg_flags && copied >= 0) {
22612261
if (cmsg_flags & MPTCP_CMSG_TS)

0 commit comments

Comments
 (0)