From: Geliang Tang <tanggeliang@kylinos.cn>
This patch adds support for the SO_REUSEADDR socket option in MPTCP by
introducing a new mptcp_sock_set_reuseaddr() function. The implementation:
1. Exposes the function in include/net/mptcp.h for external use
2. Provides the actual implementation in protocol.c that:
- Locks the MPTCP master socket
- Retrieves the first subflow socket
- Sets SK_CAN_REUSE flag on the subflow
- Properly handles locking and error cases
The function follows the same pattern as other MPTCP socket option
helpers, maintaining proper locking semantics while allowing address
reuse on the underlying TCP subflows. This enables MPTCP sockets to
bind to addresses that are already in use, which is particularly useful
for:
- Server applications that need to restart quickly
- Applications using well-known ports
- Multi-homed scenarios where the same port may be used across interfaces
Co-Developed-by: Hui Zhu <zhuhui@kylinos.cn>
Signed-off-by: Hui Zhu <zhuhui@kylinos.cn>
Co-Developed-by: Gang Yan <yangang@kylinos.cn>
Signed-off-by: Gang Yan <yangang@kylinos.cn>
Co-Developed-by: zhenwei pi <zhenwei.pi@linux.dev>
Signed-off-by: zhenwei pi <zhenwei.pi@linux.dev>
Signed-off-by: Geliang Tang <tanggeliang@kylinos.cn>
---
include/net/mptcp.h | 4 ++++
net/mptcp/protocol.c | 15 +++++++++++++++
2 files changed, 19 insertions(+)
diff --git a/include/net/mptcp.h b/include/net/mptcp.h
index f275eae0d32f..3488f3506a8e 100644
--- a/include/net/mptcp.h
+++ b/include/net/mptcp.h
@@ -239,6 +239,8 @@ static inline __be32 mptcp_reset_option(const struct sk_buff *skb)
void mptcp_active_detect_blackhole(struct sock *sk, bool expired);
void mptcp_sock_set_nodelay(struct sock *sk);
+
+void mptcp_sock_set_reuseaddr(struct sock *sk);
#else
static inline void mptcp_init(void)
@@ -327,6 +329,8 @@ static inline __be32 mptcp_reset_option(const struct sk_buff *skb) { return hto
static inline void mptcp_active_detect_blackhole(struct sock *sk, bool expired) { }
static void mptcp_sock_set_nodelay(struct sock *sk) { }
+
+static void mptcp_sock_set_reuseaddr(struct sock *sk) { }
#endif /* CONFIG_MPTCP */
#if IS_ENABLED(CONFIG_MPTCP_IPV6)
diff --git a/net/mptcp/protocol.c b/net/mptcp/protocol.c
index b2285b651ebc..34aa3f13e5c1 100644
--- a/net/mptcp/protocol.c
+++ b/net/mptcp/protocol.c
@@ -3714,6 +3714,21 @@ void mptcp_sock_set_nodelay(struct sock *sk)
}
EXPORT_SYMBOL(mptcp_sock_set_nodelay);
+void mptcp_sock_set_reuseaddr(struct sock *sk)
+{
+ struct mptcp_sock *msk = mptcp_sk(sk);
+ struct sock *ssk;
+
+ lock_sock(sk);
+ ssk = __mptcp_nmpc_sk(msk);
+ if (IS_ERR(ssk))
+ goto unlock;
+ ssk->sk_reuse = SK_CAN_REUSE;
+unlock:
+ release_sock(sk);
+}
+EXPORT_SYMBOL(mptcp_sock_set_reuseaddr);
+
bool mptcp_finish_join(struct sock *ssk)
{
struct mptcp_subflow_context *subflow = mptcp_subflow_ctx(ssk);
--
2.43.0