]> git.ipfire.org Git - thirdparty/kernel/stable-queue.git/commitdiff
5.17-stable patches
authorGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Wed, 25 May 2022 12:26:26 +0000 (14:26 +0200)
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Wed, 25 May 2022 12:26:26 +0000 (14:26 +0200)
added patches:
mptcp-do-tcp-fallback-on-early-dss-checksum-failure.patch

queue-5.17/mptcp-do-tcp-fallback-on-early-dss-checksum-failure.patch [new file with mode: 0644]

diff --git a/queue-5.17/mptcp-do-tcp-fallback-on-early-dss-checksum-failure.patch b/queue-5.17/mptcp-do-tcp-fallback-on-early-dss-checksum-failure.patch
new file mode 100644 (file)
index 0000000..0d1e3ed
--- /dev/null
@@ -0,0 +1,100 @@
+From ae66fb2ba6c3dcaf8b9612b65aa949a1a4bed150 Mon Sep 17 00:00:00 2001
+From: Mat Martineau <mathew.j.martineau@linux.intel.com>
+Date: Tue, 17 May 2022 11:02:12 -0700
+Subject: mptcp: Do TCP fallback on early DSS checksum failure
+
+From: Mat Martineau <mathew.j.martineau@linux.intel.com>
+
+commit ae66fb2ba6c3dcaf8b9612b65aa949a1a4bed150 upstream.
+
+RFC 8684 section 3.7 describes several opportunities for a MPTCP
+connection to "fall back" to regular TCP early in the connection
+process, before it has been confirmed that MPTCP options can be
+successfully propagated on all SYN, SYN/ACK, and data packets. If a peer
+acknowledges the first received data packet with a regular TCP header
+(no MPTCP options), fallback is allowed.
+
+If the recipient of that first data packet finds a MPTCP DSS checksum
+error, this provides an opportunity to fail gracefully with a TCP
+fallback rather than resetting the connection (as might happen if a
+checksum failure were detected later).
+
+This commit modifies the checksum failure code to attempt fallback on
+the initial subflow of a MPTCP connection, only if it's a failure in the
+first data mapping. In cases where the peer initiates the connection,
+requests checksums, is the first to send data, and the peer is sending
+incorrect checksums (see
+https://github.com/multipath-tcp/mptcp_net-next/issues/275), this allows
+the connection to proceed as TCP rather than reset.
+
+Fixes: dd8bcd1768ff ("mptcp: validate the data checksum")
+Acked-by: Paolo Abeni <pabeni@redhat.com>
+Signed-off-by: Mat Martineau <mathew.j.martineau@linux.intel.com>
+Signed-off-by: David S. Miller <davem@davemloft.net>
+[mathew.j.martineau: backport: Resolved bitfield conflict in protocol.h]
+Signed-off-by: Mat Martineau <mathew.j.martineau@linux.intel.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ net/mptcp/protocol.h |    3 ++-
+ net/mptcp/subflow.c  |   21 ++++++++++++++++++---
+ 2 files changed, 20 insertions(+), 4 deletions(-)
+
+--- a/net/mptcp/protocol.h
++++ b/net/mptcp/protocol.h
+@@ -442,7 +442,8 @@ struct mptcp_subflow_context {
+               rx_eof : 1,
+               can_ack : 1,        /* only after processing the remote a key */
+               disposable : 1,     /* ctx can be free at ulp release time */
+-              stale : 1;          /* unable to snd/rcv data, do not use for xmit */
++              stale : 1,          /* unable to snd/rcv data, do not use for xmit */
++              valid_csum_seen : 1;        /* at least one csum validated */
+       enum mptcp_data_avail data_avail;
+       u32     remote_nonce;
+       u64     thmac;
+--- a/net/mptcp/subflow.c
++++ b/net/mptcp/subflow.c
+@@ -913,11 +913,14 @@ static enum mapping_status validate_data
+                                subflow->map_data_csum);
+       if (unlikely(csum)) {
+               MPTCP_INC_STATS(sock_net(ssk), MPTCP_MIB_DATACSUMERR);
+-              subflow->send_mp_fail = 1;
+-              MPTCP_INC_STATS(sock_net(ssk), MPTCP_MIB_MPFAILTX);
++              if (subflow->mp_join || subflow->valid_csum_seen) {
++                      subflow->send_mp_fail = 1;
++                      MPTCP_INC_STATS(sock_net(ssk), MPTCP_MIB_MPFAILTX);
++              }
+               return subflow->mp_join ? MAPPING_INVALID : MAPPING_DUMMY;
+       }
++      subflow->valid_csum_seen = 1;
+       return MAPPING_OK;
+ }
+@@ -1099,6 +1102,18 @@ static void subflow_sched_work_if_closed
+       }
+ }
++static bool subflow_can_fallback(struct mptcp_subflow_context *subflow)
++{
++      struct mptcp_sock *msk = mptcp_sk(subflow->conn);
++
++      if (subflow->mp_join)
++              return false;
++      else if (READ_ONCE(msk->csum_enabled))
++              return !subflow->valid_csum_seen;
++      else
++              return !subflow->fully_established;
++}
++
+ static bool subflow_check_data_avail(struct sock *ssk)
+ {
+       struct mptcp_subflow_context *subflow = mptcp_subflow_ctx(ssk);
+@@ -1176,7 +1191,7 @@ fallback:
+               return true;
+       }
+-      if (subflow->mp_join || subflow->fully_established) {
++      if (!subflow_can_fallback(subflow)) {
+               /* fatal protocol error, close the socket.
+                * subflow_error_report() will introduce the appropriate barriers
+                */