All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH mptcp-next v2 00/10] BPF path manager, part 6
@ 2025-03-14  2:45 Geliang Tang
  2025-03-14  2:45 ` [PATCH mptcp-next v2 01/10] mptcp: pm: drop redundant MPTCP_MIB_ADDADDRDROP Geliang Tang
                   ` (10 more replies)
  0 siblings, 11 replies; 12+ messages in thread
From: Geliang Tang @ 2025-03-14  2:45 UTC (permalink / raw)
  To: mptcp; +Cc: Geliang Tang

From: Geliang Tang <tanggeliang@kylinos.cn>

v2:
- address Matt's comments in v1.
- add add_addr_received and rm_addr_received interfaces.
- drop subflow_check_next interface.
- add a "required" or "optional" comment for a group of interfaces in
  struct mptcp_pm_ops.

v1:
- https://patchwork.kernel.org/project/mptcp/cover/cover.1741685260.git.tanggeliang@kylinos.cn/

New interfaces for struct mptcp_pm_ops.

Geliang Tang (10):
  mptcp: pm: drop redundant MPTCP_MIB_ADDADDRDROP
  Squash to "mptcp: pm: add get_local_id() interface"
  mptcp: pm: add established() interface
  mptcp: pm: add subflow_established() interface
  mptcp: pm: add allow_new_subflow() interface
  mptcp: pm: add accept_new_subflow() interface
  mptcp: pm: add add_addr_received() interface
  mptcp: pm: add add_addr_echo() interface
  mptcp: pm: add rm_addr_received() interface
  mptcp: pm: drop is_userspace in subflow_check_next

 include/net/mptcp.h      |  16 ++++++
 net/mptcp/pm.c           | 112 +++++++++++++++++----------------------
 net/mptcp/pm_kernel.c    |  74 ++++++++++++++++++++++----
 net/mptcp/pm_userspace.c |  27 ++++++++++
 net/mptcp/protocol.h     |   4 ++
 net/mptcp/subflow.c      |   4 +-
 6 files changed, 161 insertions(+), 76 deletions(-)

-- 
2.45.2


^ permalink raw reply	[flat|nested] 12+ messages in thread

* [PATCH mptcp-next v2 01/10] mptcp: pm: drop redundant MPTCP_MIB_ADDADDRDROP
  2025-03-14  2:45 [PATCH mptcp-next v2 00/10] BPF path manager, part 6 Geliang Tang
@ 2025-03-14  2:45 ` Geliang Tang
  2025-03-14  2:45 ` [PATCH mptcp-next v2 02/10] Squash to "mptcp: pm: add get_local_id() interface" Geliang Tang
                   ` (9 subsequent siblings)
  10 siblings, 0 replies; 12+ messages in thread
From: Geliang Tang @ 2025-03-14  2:45 UTC (permalink / raw)
  To: mptcp; +Cc: Geliang Tang

From: Geliang Tang <tanggeliang@kylinos.cn>

MPTCP_MIB_ADDADDRDROP MIB counter is incremented from both the in-kernel PM
and the userspace PM. This can be called only once to reduce redundant
code.

Signed-off-by: Geliang Tang <tanggeliang@kylinos.cn>
---
 net/mptcp/pm.c | 8 ++++++--
 1 file changed, 6 insertions(+), 2 deletions(-)

diff --git a/net/mptcp/pm.c b/net/mptcp/pm.c
index ba7424582ebf..4895318b94cc 100644
--- a/net/mptcp/pm.c
+++ b/net/mptcp/pm.c
@@ -592,6 +592,7 @@ void mptcp_pm_add_addr_received(const struct sock *ssk,
 	struct mptcp_subflow_context *subflow = mptcp_subflow_ctx(ssk);
 	struct mptcp_sock *msk = mptcp_sk(subflow->conn);
 	struct mptcp_pm_data *pm = &msk->pm;
+	int ret = 0;
 
 	pr_debug("msk=%p remote_id=%d accept=%d\n", msk, addr->id,
 		 READ_ONCE(pm->accept_addr));
@@ -605,7 +606,7 @@ void mptcp_pm_add_addr_received(const struct sock *ssk,
 			mptcp_pm_announce_addr(msk, addr, true);
 			mptcp_pm_add_addr_send_ack(msk);
 		} else {
-			__MPTCP_INC_STATS(sock_net((struct sock *)msk), MPTCP_MIB_ADDADDRDROP);
+			ret = -EINVAL;
 		}
 	/* id0 should not have a different address */
 	} else if ((addr->id == 0 && !mptcp_pm_is_init_remote_addr(msk, addr)) ||
@@ -615,9 +616,12 @@ void mptcp_pm_add_addr_received(const struct sock *ssk,
 	} else if (mptcp_pm_schedule_work(msk, MPTCP_PM_ADD_ADDR_RECEIVED)) {
 		pm->remote = *addr;
 	} else {
-		__MPTCP_INC_STATS(sock_net((struct sock *)msk), MPTCP_MIB_ADDADDRDROP);
+		ret = -EINVAL;
 	}
 
+	if (ret)
+		__MPTCP_INC_STATS(sock_net((struct sock *)msk), MPTCP_MIB_ADDADDRDROP);
+
 	spin_unlock_bh(&pm->lock);
 }
 
-- 
2.45.2


^ permalink raw reply related	[flat|nested] 12+ messages in thread

* [PATCH mptcp-next v2 02/10] Squash to "mptcp: pm: add get_local_id() interface"
  2025-03-14  2:45 [PATCH mptcp-next v2 00/10] BPF path manager, part 6 Geliang Tang
  2025-03-14  2:45 ` [PATCH mptcp-next v2 01/10] mptcp: pm: drop redundant MPTCP_MIB_ADDADDRDROP Geliang Tang
@ 2025-03-14  2:45 ` Geliang Tang
  2025-03-14  2:45 ` [PATCH mptcp-next v2 03/10] mptcp: pm: add established() interface Geliang Tang
                   ` (8 subsequent siblings)
  10 siblings, 0 replies; 12+ messages in thread
From: Geliang Tang @ 2025-03-14  2:45 UTC (permalink / raw)
  To: mptcp; +Cc: Geliang Tang

From: Geliang Tang <tanggeliang@kylinos.cn>

Add /* required */ comment for get_local_id and get_priority.

Signed-off-by: Geliang Tang <tanggeliang@kylinos.cn>
---
 include/net/mptcp.h | 1 +
 1 file changed, 1 insertion(+)

diff --git a/include/net/mptcp.h b/include/net/mptcp.h
index 6a08ac862bbe..9f28ef550e10 100644
--- a/include/net/mptcp.h
+++ b/include/net/mptcp.h
@@ -118,6 +118,7 @@ struct mptcp_sched_ops {
 #define MPTCP_PM_BUF_MAX	(MPTCP_PM_NAME_MAX * MPTCP_PM_MAX)
 
 struct mptcp_pm_ops {
+	/* required */
 	int (*get_local_id)(struct mptcp_sock *msk,
 			    struct mptcp_pm_addr_entry *skc);
 	bool (*get_priority)(struct mptcp_sock *msk,
-- 
2.45.2


^ permalink raw reply related	[flat|nested] 12+ messages in thread

* [PATCH mptcp-next v2 03/10] mptcp: pm: add established() interface
  2025-03-14  2:45 [PATCH mptcp-next v2 00/10] BPF path manager, part 6 Geliang Tang
  2025-03-14  2:45 ` [PATCH mptcp-next v2 01/10] mptcp: pm: drop redundant MPTCP_MIB_ADDADDRDROP Geliang Tang
  2025-03-14  2:45 ` [PATCH mptcp-next v2 02/10] Squash to "mptcp: pm: add get_local_id() interface" Geliang Tang
@ 2025-03-14  2:45 ` Geliang Tang
  2025-03-14  2:45 ` [PATCH mptcp-next v2 04/10] mptcp: pm: add subflow_established() interface Geliang Tang
                   ` (7 subsequent siblings)
  10 siblings, 0 replies; 12+ messages in thread
From: Geliang Tang @ 2025-03-14  2:45 UTC (permalink / raw)
  To: mptcp; +Cc: Geliang Tang

From: Geliang Tang <tanggeliang@kylinos.cn>

This patch adds a .established interface for struct mptcp_pm_ops, and
calls pm->ops->established in from mptcp_pm_worker(). Then get rid of
the corresponding code from __mptcp_pm_kernel_worker().

Signed-off-by: Geliang Tang <tanggeliang@kylinos.cn>
---
 include/net/mptcp.h   | 3 +++
 net/mptcp/pm.c        | 7 ++++++-
 net/mptcp/pm_kernel.c | 7 ++-----
 3 files changed, 11 insertions(+), 6 deletions(-)

diff --git a/include/net/mptcp.h b/include/net/mptcp.h
index 9f28ef550e10..d7410f08399e 100644
--- a/include/net/mptcp.h
+++ b/include/net/mptcp.h
@@ -124,6 +124,9 @@ struct mptcp_pm_ops {
 	bool (*get_priority)(struct mptcp_sock *msk,
 			     struct mptcp_addr_info *skc);
 
+	/* optional */
+	void (*established)(struct mptcp_sock *msk);
+
 	char			name[MPTCP_PM_NAME_MAX];
 	struct module		*owner;
 	struct list_head	list;
diff --git a/net/mptcp/pm.c b/net/mptcp/pm.c
index 4895318b94cc..3dcece1c6fef 100644
--- a/net/mptcp/pm.c
+++ b/net/mptcp/pm.c
@@ -516,7 +516,8 @@ void mptcp_pm_fully_established(struct mptcp_sock *msk, const struct sock *ssk)
 	 * be sure to serve this event only once.
 	 */
 	if (READ_ONCE(pm->work_pending) &&
-	    !(pm->status & BIT(MPTCP_PM_ALREADY_ESTABLISHED)))
+	    !(pm->status & BIT(MPTCP_PM_ALREADY_ESTABLISHED)) &&
+	    pm->ops->established)
 		mptcp_pm_schedule_work(msk, MPTCP_PM_ESTABLISHED);
 
 	if ((pm->status & BIT(MPTCP_PM_ALREADY_ESTABLISHED)) == 0)
@@ -964,6 +965,10 @@ void mptcp_pm_worker(struct mptcp_sock *msk)
 		pm->status &= ~BIT(MPTCP_PM_RM_ADDR_RECEIVED);
 		mptcp_pm_rm_addr_recv(msk);
 	}
+	if (pm->status & BIT(MPTCP_PM_ESTABLISHED)) {
+		pm->status &= ~BIT(MPTCP_PM_ESTABLISHED);
+		pm->ops->established(msk);
+	}
 	__mptcp_pm_kernel_worker(msk);
 
 	spin_unlock_bh(&msk->pm.lock);
diff --git a/net/mptcp/pm_kernel.c b/net/mptcp/pm_kernel.c
index 7ec81d5195d4..1234066b5bcc 100644
--- a/net/mptcp/pm_kernel.c
+++ b/net/mptcp/pm_kernel.c
@@ -367,7 +367,7 @@ static void mptcp_pm_create_subflow_or_signal_addr(struct mptcp_sock *msk)
 	mptcp_pm_nl_check_work_pending(msk);
 }
 
-static void mptcp_pm_nl_fully_established(struct mptcp_sock *msk)
+static void mptcp_pm_kernel_established(struct mptcp_sock *msk)
 {
 	mptcp_pm_create_subflow_or_signal_addr(msk);
 }
@@ -1348,10 +1348,6 @@ void __mptcp_pm_kernel_worker(struct mptcp_sock *msk)
 		pm->status &= ~BIT(MPTCP_PM_ADD_ADDR_RECEIVED);
 		mptcp_pm_nl_add_addr_received(msk);
 	}
-	if (pm->status & BIT(MPTCP_PM_ESTABLISHED)) {
-		pm->status &= ~BIT(MPTCP_PM_ESTABLISHED);
-		mptcp_pm_nl_fully_established(msk);
-	}
 	if (pm->status & BIT(MPTCP_PM_SUBFLOW_ESTABLISHED)) {
 		pm->status &= ~BIT(MPTCP_PM_SUBFLOW_ESTABLISHED);
 		mptcp_pm_nl_subflow_established(msk);
@@ -1422,6 +1418,7 @@ static void mptcp_pm_kernel_init(struct mptcp_sock *msk)
 struct mptcp_pm_ops mptcp_pm_kernel = {
 	.get_local_id		= mptcp_pm_kernel_get_local_id,
 	.get_priority		= mptcp_pm_kernel_get_priority,
+	.established		= mptcp_pm_kernel_established,
 	.init			= mptcp_pm_kernel_init,
 	.name			= "kernel",
 	.owner			= THIS_MODULE,
-- 
2.45.2


^ permalink raw reply related	[flat|nested] 12+ messages in thread

* [PATCH mptcp-next v2 04/10] mptcp: pm: add subflow_established() interface
  2025-03-14  2:45 [PATCH mptcp-next v2 00/10] BPF path manager, part 6 Geliang Tang
                   ` (2 preceding siblings ...)
  2025-03-14  2:45 ` [PATCH mptcp-next v2 03/10] mptcp: pm: add established() interface Geliang Tang
@ 2025-03-14  2:45 ` Geliang Tang
  2025-03-14  2:45 ` [PATCH mptcp-next v2 05/10] mptcp: pm: add allow_new_subflow() interface Geliang Tang
                   ` (6 subsequent siblings)
  10 siblings, 0 replies; 12+ messages in thread
From: Geliang Tang @ 2025-03-14  2:45 UTC (permalink / raw)
  To: mptcp; +Cc: Geliang Tang

From: Geliang Tang <tanggeliang@kylinos.cn>

This patch adds a .subflow_established interface for struct mptcp_pm_ops,
and calls pm->ops->subflow_established in from mptcp_pm_worker(). Then
get rid of the corresponding code from __mptcp_pm_kernel_worker().

Signed-off-by: Geliang Tang <tanggeliang@kylinos.cn>
---
 include/net/mptcp.h   |  1 +
 net/mptcp/pm.c        | 11 +++++++++--
 net/mptcp/pm_kernel.c |  7 ++-----
 3 files changed, 12 insertions(+), 7 deletions(-)

diff --git a/include/net/mptcp.h b/include/net/mptcp.h
index d7410f08399e..4ac936e4ce0d 100644
--- a/include/net/mptcp.h
+++ b/include/net/mptcp.h
@@ -126,6 +126,7 @@ struct mptcp_pm_ops {
 
 	/* optional */
 	void (*established)(struct mptcp_sock *msk);
+	void (*subflow_established)(struct mptcp_sock *msk);
 
 	char			name[MPTCP_PM_NAME_MAX];
 	struct module		*owner;
diff --git a/net/mptcp/pm.c b/net/mptcp/pm.c
index 3dcece1c6fef..b90134152b92 100644
--- a/net/mptcp/pm.c
+++ b/net/mptcp/pm.c
@@ -544,7 +544,7 @@ void mptcp_pm_subflow_established(struct mptcp_sock *msk)
 
 	pr_debug("msk=%p\n", msk);
 
-	if (!READ_ONCE(pm->work_pending))
+	if (!READ_ONCE(pm->work_pending) || !pm->ops->subflow_established)
 		return;
 
 	spin_lock_bh(&pm->lock);
@@ -571,6 +571,9 @@ void mptcp_pm_subflow_check_next(struct mptcp_sock *msk,
 		return;
 	}
 
+	if (!pm->ops->subflow_established)
+		return;
+
 	if (!READ_ONCE(pm->work_pending) && !update_subflows)
 		return;
 
@@ -633,7 +636,7 @@ void mptcp_pm_add_addr_echoed(struct mptcp_sock *msk,
 
 	pr_debug("msk=%p\n", msk);
 
-	if (!READ_ONCE(pm->work_pending))
+	if (!READ_ONCE(pm->work_pending) || !pm->ops->subflow_established)
 		return;
 
 	spin_lock_bh(&pm->lock);
@@ -969,6 +972,10 @@ void mptcp_pm_worker(struct mptcp_sock *msk)
 		pm->status &= ~BIT(MPTCP_PM_ESTABLISHED);
 		pm->ops->established(msk);
 	}
+	if (pm->status & BIT(MPTCP_PM_SUBFLOW_ESTABLISHED)) {
+		pm->status &= ~BIT(MPTCP_PM_SUBFLOW_ESTABLISHED);
+		pm->ops->subflow_established(msk);
+	}
 	__mptcp_pm_kernel_worker(msk);
 
 	spin_unlock_bh(&msk->pm.lock);
diff --git a/net/mptcp/pm_kernel.c b/net/mptcp/pm_kernel.c
index 1234066b5bcc..e21fefc0aca9 100644
--- a/net/mptcp/pm_kernel.c
+++ b/net/mptcp/pm_kernel.c
@@ -372,7 +372,7 @@ static void mptcp_pm_kernel_established(struct mptcp_sock *msk)
 	mptcp_pm_create_subflow_or_signal_addr(msk);
 }
 
-static void mptcp_pm_nl_subflow_established(struct mptcp_sock *msk)
+static void mptcp_pm_kernel_subflow_established(struct mptcp_sock *msk)
 {
 	mptcp_pm_create_subflow_or_signal_addr(msk);
 }
@@ -1348,10 +1348,6 @@ void __mptcp_pm_kernel_worker(struct mptcp_sock *msk)
 		pm->status &= ~BIT(MPTCP_PM_ADD_ADDR_RECEIVED);
 		mptcp_pm_nl_add_addr_received(msk);
 	}
-	if (pm->status & BIT(MPTCP_PM_SUBFLOW_ESTABLISHED)) {
-		pm->status &= ~BIT(MPTCP_PM_SUBFLOW_ESTABLISHED);
-		mptcp_pm_nl_subflow_established(msk);
-	}
 }
 
 static int __net_init pm_nl_init_net(struct net *net)
@@ -1419,6 +1415,7 @@ struct mptcp_pm_ops mptcp_pm_kernel = {
 	.get_local_id		= mptcp_pm_kernel_get_local_id,
 	.get_priority		= mptcp_pm_kernel_get_priority,
 	.established		= mptcp_pm_kernel_established,
+	.subflow_established	= mptcp_pm_kernel_subflow_established,
 	.init			= mptcp_pm_kernel_init,
 	.name			= "kernel",
 	.owner			= THIS_MODULE,
-- 
2.45.2


^ permalink raw reply related	[flat|nested] 12+ messages in thread

* [PATCH mptcp-next v2 05/10] mptcp: pm: add allow_new_subflow() interface
  2025-03-14  2:45 [PATCH mptcp-next v2 00/10] BPF path manager, part 6 Geliang Tang
                   ` (3 preceding siblings ...)
  2025-03-14  2:45 ` [PATCH mptcp-next v2 04/10] mptcp: pm: add subflow_established() interface Geliang Tang
@ 2025-03-14  2:45 ` Geliang Tang
  2025-03-14  2:45 ` [PATCH mptcp-next v2 06/10] mptcp: pm: add accept_new_subflow() interface Geliang Tang
                   ` (5 subsequent siblings)
  10 siblings, 0 replies; 12+ messages in thread
From: Geliang Tang @ 2025-03-14  2:45 UTC (permalink / raw)
  To: mptcp; +Cc: Geliang Tang

From: Geliang Tang <tanggeliang@kylinos.cn>

The helper mptcp_pm_is_userspace() is used to distinguish userspace PM
operations from in-kernel PM in mptcp_pm_allow_new_subflow(). It seems
reasonable to add a mandatory .allow_new_subflow interface for struct
mptcp_pm_ops.

Signed-off-by: Geliang Tang <tanggeliang@kylinos.cn>
---
 include/net/mptcp.h      |  3 +++
 net/mptcp/pm.c           | 36 +++---------------------------------
 net/mptcp/pm_kernel.c    | 27 +++++++++++++++++++++++++++
 net/mptcp/pm_userspace.c | 14 ++++++++++++++
 4 files changed, 47 insertions(+), 33 deletions(-)

diff --git a/include/net/mptcp.h b/include/net/mptcp.h
index 4ac936e4ce0d..e15d6b5680f6 100644
--- a/include/net/mptcp.h
+++ b/include/net/mptcp.h
@@ -128,6 +128,9 @@ struct mptcp_pm_ops {
 	void (*established)(struct mptcp_sock *msk);
 	void (*subflow_established)(struct mptcp_sock *msk);
 
+	/* required */
+	bool (*allow_new_subflow)(struct mptcp_sock *msk);
+
 	char			name[MPTCP_PM_NAME_MAX];
 	struct module		*owner;
 	struct list_head	list;
diff --git a/net/mptcp/pm.c b/net/mptcp/pm.c
index b90134152b92..03152a1a157e 100644
--- a/net/mptcp/pm.c
+++ b/net/mptcp/pm.c
@@ -452,38 +452,7 @@ void mptcp_pm_new_connection(struct mptcp_sock *msk, const struct sock *ssk, int
 
 bool mptcp_pm_allow_new_subflow(struct mptcp_sock *msk)
 {
-	struct mptcp_pm_data *pm = &msk->pm;
-	unsigned int subflows_max;
-	int ret = 0;
-
-	if (mptcp_pm_is_userspace(msk)) {
-		if (mptcp_userspace_pm_active(msk)) {
-			spin_lock_bh(&pm->lock);
-			pm->subflows++;
-			spin_unlock_bh(&pm->lock);
-			return true;
-		}
-		return false;
-	}
-
-	subflows_max = mptcp_pm_get_subflows_max(msk);
-
-	pr_debug("msk=%p subflows=%d max=%d allow=%d\n", msk, pm->subflows,
-		 subflows_max, READ_ONCE(pm->accept_subflow));
-
-	/* try to avoid acquiring the lock below */
-	if (!READ_ONCE(pm->accept_subflow))
-		return false;
-
-	spin_lock_bh(&pm->lock);
-	if (READ_ONCE(pm->accept_subflow)) {
-		ret = pm->subflows < subflows_max;
-		if (ret && ++pm->subflows == subflows_max)
-			WRITE_ONCE(pm->accept_subflow, false);
-	}
-	spin_unlock_bh(&pm->lock);
-
-	return ret;
+	return msk->pm.ops->allow_new_subflow(msk);
 }
 
 /* return true if the new status bit is currently cleared, that is, this event
@@ -1063,7 +1032,8 @@ struct mptcp_pm_ops *mptcp_pm_find(const char *name)
 
 int mptcp_pm_validate(struct mptcp_pm_ops *pm_ops)
 {
-	if (!pm_ops->get_local_id || !pm_ops->get_priority) {
+	if (!pm_ops->get_local_id || !pm_ops->get_priority ||
+	    !pm_ops->allow_new_subflow) {
 		pr_err("%s does not implement required ops\n", pm_ops->name);
 		return -EINVAL;
 	}
diff --git a/net/mptcp/pm_kernel.c b/net/mptcp/pm_kernel.c
index e21fefc0aca9..eb498b17e67f 100644
--- a/net/mptcp/pm_kernel.c
+++ b/net/mptcp/pm_kernel.c
@@ -1391,6 +1391,32 @@ static struct pernet_operations mptcp_pm_pernet_ops = {
 	.size = sizeof(struct pm_nl_pernet),
 };
 
+static bool mptcp_pm_kernel_allow_new_subflow(struct mptcp_sock *msk)
+{
+	struct mptcp_pm_data *pm = &msk->pm;
+	unsigned int subflows_max;
+	int ret = 0;
+
+	subflows_max = mptcp_pm_get_subflows_max(msk);
+
+	pr_debug("msk=%p subflows=%d max=%d allow=%d\n", msk, pm->subflows,
+		 subflows_max, READ_ONCE(pm->accept_subflow));
+
+	/* try to avoid acquiring the lock below */
+	if (!READ_ONCE(pm->accept_subflow))
+		return false;
+
+	spin_lock_bh(&pm->lock);
+	if (READ_ONCE(pm->accept_subflow)) {
+		ret = pm->subflows < subflows_max;
+		if (ret && ++pm->subflows == subflows_max)
+			WRITE_ONCE(pm->accept_subflow, false);
+	}
+	spin_unlock_bh(&pm->lock);
+
+	return ret;
+}
+
 static void mptcp_pm_kernel_init(struct mptcp_sock *msk)
 {
 	bool subflows_allowed = !!mptcp_pm_get_subflows_max(msk);
@@ -1416,6 +1442,7 @@ struct mptcp_pm_ops mptcp_pm_kernel = {
 	.get_priority		= mptcp_pm_kernel_get_priority,
 	.established		= mptcp_pm_kernel_established,
 	.subflow_established	= mptcp_pm_kernel_subflow_established,
+	.allow_new_subflow	= mptcp_pm_kernel_allow_new_subflow,
 	.init			= mptcp_pm_kernel_init,
 	.name			= "kernel",
 	.owner			= THIS_MODULE,
diff --git a/net/mptcp/pm_userspace.c b/net/mptcp/pm_userspace.c
index 7fc19b844384..3a9962ac77b2 100644
--- a/net/mptcp/pm_userspace.c
+++ b/net/mptcp/pm_userspace.c
@@ -683,6 +683,19 @@ int mptcp_userspace_pm_get_addr(u8 id, struct mptcp_pm_addr_entry *addr,
 	return ret;
 }
 
+static bool mptcp_pm_userspace_allow_new_subflow(struct mptcp_sock *msk)
+{
+	struct mptcp_pm_data *pm = &msk->pm;
+
+	if (mptcp_userspace_pm_active(msk)) {
+		spin_lock_bh(&pm->lock);
+		pm->subflows++;
+		spin_unlock_bh(&pm->lock);
+		return true;
+	}
+	return false;
+}
+
 static void mptcp_pm_userspace_release(struct mptcp_sock *msk)
 {
 	mptcp_userspace_pm_free_local_addr_list(msk);
@@ -691,6 +704,7 @@ static void mptcp_pm_userspace_release(struct mptcp_sock *msk)
 static struct mptcp_pm_ops mptcp_pm_userspace = {
 	.get_local_id		= mptcp_pm_userspace_get_local_id,
 	.get_priority		= mptcp_pm_userspace_get_priority,
+	.allow_new_subflow	= mptcp_pm_userspace_allow_new_subflow,
 	.release		= mptcp_pm_userspace_release,
 	.name			= "userspace",
 	.owner			= THIS_MODULE,
-- 
2.45.2


^ permalink raw reply related	[flat|nested] 12+ messages in thread

* [PATCH mptcp-next v2 06/10] mptcp: pm: add accept_new_subflow() interface
  2025-03-14  2:45 [PATCH mptcp-next v2 00/10] BPF path manager, part 6 Geliang Tang
                   ` (4 preceding siblings ...)
  2025-03-14  2:45 ` [PATCH mptcp-next v2 05/10] mptcp: pm: add allow_new_subflow() interface Geliang Tang
@ 2025-03-14  2:45 ` Geliang Tang
  2025-03-14  2:45 ` [PATCH mptcp-next v2 07/10] mptcp: pm: add add_addr_received() interface Geliang Tang
                   ` (4 subsequent siblings)
  10 siblings, 0 replies; 12+ messages in thread
From: Geliang Tang @ 2025-03-14  2:45 UTC (permalink / raw)
  To: mptcp; +Cc: Geliang Tang

From: Geliang Tang <tanggeliang@kylinos.cn>

The helper mptcp_pm_is_userspace() is used to distinguish userspace PM
operations from in-kernel PM in mptcp_can_accept_new_subflow(). It seems
reasonable to add a mandatory .accept_new_subflow interface for struct
mptcp_pm_ops.

Signed-off-by: Geliang Tang <tanggeliang@kylinos.cn>
---
 include/net/mptcp.h      | 1 +
 net/mptcp/pm.c           | 2 +-
 net/mptcp/pm_kernel.c    | 6 ++++++
 net/mptcp/pm_userspace.c | 6 ++++++
 net/mptcp/subflow.c      | 4 +---
 5 files changed, 15 insertions(+), 4 deletions(-)

diff --git a/include/net/mptcp.h b/include/net/mptcp.h
index e15d6b5680f6..de9838ea37c4 100644
--- a/include/net/mptcp.h
+++ b/include/net/mptcp.h
@@ -130,6 +130,7 @@ struct mptcp_pm_ops {
 
 	/* required */
 	bool (*allow_new_subflow)(struct mptcp_sock *msk);
+	bool (*accept_new_subflow)(const struct mptcp_sock *msk);
 
 	char			name[MPTCP_PM_NAME_MAX];
 	struct module		*owner;
diff --git a/net/mptcp/pm.c b/net/mptcp/pm.c
index 03152a1a157e..7ae706669c80 100644
--- a/net/mptcp/pm.c
+++ b/net/mptcp/pm.c
@@ -1033,7 +1033,7 @@ struct mptcp_pm_ops *mptcp_pm_find(const char *name)
 int mptcp_pm_validate(struct mptcp_pm_ops *pm_ops)
 {
 	if (!pm_ops->get_local_id || !pm_ops->get_priority ||
-	    !pm_ops->allow_new_subflow) {
+	    !pm_ops->allow_new_subflow || !pm_ops->accept_new_subflow) {
 		pr_err("%s does not implement required ops\n", pm_ops->name);
 		return -EINVAL;
 	}
diff --git a/net/mptcp/pm_kernel.c b/net/mptcp/pm_kernel.c
index eb498b17e67f..38542d62767d 100644
--- a/net/mptcp/pm_kernel.c
+++ b/net/mptcp/pm_kernel.c
@@ -1417,6 +1417,11 @@ static bool mptcp_pm_kernel_allow_new_subflow(struct mptcp_sock *msk)
 	return ret;
 }
 
+static bool mptcp_pm_kernel_accept_new_subflow(const struct mptcp_sock *msk)
+{
+	return READ_ONCE(msk->pm.accept_subflow);
+}
+
 static void mptcp_pm_kernel_init(struct mptcp_sock *msk)
 {
 	bool subflows_allowed = !!mptcp_pm_get_subflows_max(msk);
@@ -1443,6 +1448,7 @@ struct mptcp_pm_ops mptcp_pm_kernel = {
 	.established		= mptcp_pm_kernel_established,
 	.subflow_established	= mptcp_pm_kernel_subflow_established,
 	.allow_new_subflow	= mptcp_pm_kernel_allow_new_subflow,
+	.accept_new_subflow	= mptcp_pm_kernel_accept_new_subflow,
 	.init			= mptcp_pm_kernel_init,
 	.name			= "kernel",
 	.owner			= THIS_MODULE,
diff --git a/net/mptcp/pm_userspace.c b/net/mptcp/pm_userspace.c
index 3a9962ac77b2..4cd9a84477c8 100644
--- a/net/mptcp/pm_userspace.c
+++ b/net/mptcp/pm_userspace.c
@@ -696,6 +696,11 @@ static bool mptcp_pm_userspace_allow_new_subflow(struct mptcp_sock *msk)
 	return false;
 }
 
+static bool mptcp_pm_userspace_accept_new_subflow(const struct mptcp_sock *msk)
+{
+	return mptcp_userspace_pm_active(msk);
+}
+
 static void mptcp_pm_userspace_release(struct mptcp_sock *msk)
 {
 	mptcp_userspace_pm_free_local_addr_list(msk);
@@ -705,6 +710,7 @@ static struct mptcp_pm_ops mptcp_pm_userspace = {
 	.get_local_id		= mptcp_pm_userspace_get_local_id,
 	.get_priority		= mptcp_pm_userspace_get_priority,
 	.allow_new_subflow	= mptcp_pm_userspace_allow_new_subflow,
+	.accept_new_subflow	= mptcp_pm_userspace_accept_new_subflow,
 	.release		= mptcp_pm_userspace_release,
 	.name			= "userspace",
 	.owner			= THIS_MODULE,
diff --git a/net/mptcp/subflow.c b/net/mptcp/subflow.c
index efe8d86496db..defef7aa5b28 100644
--- a/net/mptcp/subflow.c
+++ b/net/mptcp/subflow.c
@@ -61,9 +61,7 @@ static void subflow_generate_hmac(u64 key1, u64 key2, u32 nonce1, u32 nonce2,
 static bool mptcp_can_accept_new_subflow(const struct mptcp_sock *msk)
 {
 	return mptcp_is_fully_established((void *)msk) &&
-		((mptcp_pm_is_userspace(msk) &&
-		  mptcp_userspace_pm_active(msk)) ||
-		 READ_ONCE(msk->pm.accept_subflow));
+		msk->pm.ops->accept_new_subflow(msk);
 }
 
 /* validate received token and create truncated hmac and nonce for SYN-ACK */
-- 
2.45.2


^ permalink raw reply related	[flat|nested] 12+ messages in thread

* [PATCH mptcp-next v2 07/10] mptcp: pm: add add_addr_received() interface
  2025-03-14  2:45 [PATCH mptcp-next v2 00/10] BPF path manager, part 6 Geliang Tang
                   ` (5 preceding siblings ...)
  2025-03-14  2:45 ` [PATCH mptcp-next v2 06/10] mptcp: pm: add accept_new_subflow() interface Geliang Tang
@ 2025-03-14  2:45 ` Geliang Tang
  2025-03-14  2:45 ` [PATCH mptcp-next v2 08/10] mptcp: pm: add add_addr_echo() interface Geliang Tang
                   ` (3 subsequent siblings)
  10 siblings, 0 replies; 12+ messages in thread
From: Geliang Tang @ 2025-03-14  2:45 UTC (permalink / raw)
  To: mptcp; +Cc: Geliang Tang

From: Geliang Tang <tanggeliang@kylinos.cn>

This patch adds an optional .add_addr_received interface for struct
mptcp_pm_ops and invokes it in mptcp_pm_add_addr_received(). A new helper
mptcp_pm_add_addr_recv() is added to allow the MPTCP_PM_ADD_ADDR_RECEIVED
worker can be invoke from the in-kernel PM.

Signed-off-by: Geliang Tang <tanggeliang@kylinos.cn>
---
 include/net/mptcp.h   |  4 ++++
 net/mptcp/pm.c        | 10 +++++++---
 net/mptcp/pm_kernel.c | 12 ++++++++++++
 net/mptcp/protocol.h  |  1 +
 4 files changed, 24 insertions(+), 3 deletions(-)

diff --git a/include/net/mptcp.h b/include/net/mptcp.h
index de9838ea37c4..37a84b4c661e 100644
--- a/include/net/mptcp.h
+++ b/include/net/mptcp.h
@@ -132,6 +132,10 @@ struct mptcp_pm_ops {
 	bool (*allow_new_subflow)(struct mptcp_sock *msk);
 	bool (*accept_new_subflow)(const struct mptcp_sock *msk);
 
+	/* optional */
+	int (*add_addr_received)(struct mptcp_sock *msk,
+				 const struct mptcp_addr_info *addr);
+
 	char			name[MPTCP_PM_NAME_MAX];
 	struct module		*owner;
 	struct list_head	list;
diff --git a/net/mptcp/pm.c b/net/mptcp/pm.c
index 7ae706669c80..522dd2df4097 100644
--- a/net/mptcp/pm.c
+++ b/net/mptcp/pm.c
@@ -559,6 +559,11 @@ void mptcp_pm_subflow_check_next(struct mptcp_sock *msk,
 	spin_unlock_bh(&pm->lock);
 }
 
+bool mptcp_pm_add_addr_recv(struct mptcp_sock *msk)
+{
+	return mptcp_pm_schedule_work(msk, MPTCP_PM_ADD_ADDR_RECEIVED);
+}
+
 void mptcp_pm_add_addr_received(const struct sock *ssk,
 				const struct mptcp_addr_info *addr)
 {
@@ -586,10 +591,9 @@ void mptcp_pm_add_addr_received(const struct sock *ssk,
 		   (addr->id > 0 && !READ_ONCE(pm->accept_addr))) {
 		mptcp_pm_announce_addr(msk, addr, true);
 		mptcp_pm_add_addr_send_ack(msk);
-	} else if (mptcp_pm_schedule_work(msk, MPTCP_PM_ADD_ADDR_RECEIVED)) {
-		pm->remote = *addr;
 	} else {
-		ret = -EINVAL;
+		ret = pm->ops->add_addr_received ?
+		      pm->ops->add_addr_received(msk, addr) : -EINVAL;
 	}
 
 	if (ret)
diff --git a/net/mptcp/pm_kernel.c b/net/mptcp/pm_kernel.c
index 38542d62767d..6a5d6d374b0d 100644
--- a/net/mptcp/pm_kernel.c
+++ b/net/mptcp/pm_kernel.c
@@ -1422,6 +1422,17 @@ static bool mptcp_pm_kernel_accept_new_subflow(const struct mptcp_sock *msk)
 	return READ_ONCE(msk->pm.accept_subflow);
 }
 
+static int mptcp_pm_kernel_add_addr_received(struct mptcp_sock *msk,
+					     const struct mptcp_addr_info *addr)
+{
+	if (mptcp_pm_add_addr_recv(msk)) {
+		msk->pm.remote = *addr;
+		return 0;
+	}
+
+	return -EINVAL;
+}
+
 static void mptcp_pm_kernel_init(struct mptcp_sock *msk)
 {
 	bool subflows_allowed = !!mptcp_pm_get_subflows_max(msk);
@@ -1449,6 +1460,7 @@ struct mptcp_pm_ops mptcp_pm_kernel = {
 	.subflow_established	= mptcp_pm_kernel_subflow_established,
 	.allow_new_subflow	= mptcp_pm_kernel_allow_new_subflow,
 	.accept_new_subflow	= mptcp_pm_kernel_accept_new_subflow,
+	.add_addr_received	= mptcp_pm_kernel_add_addr_received,
 	.init			= mptcp_pm_kernel_init,
 	.name			= "kernel",
 	.owner			= THIS_MODULE,
diff --git a/net/mptcp/protocol.h b/net/mptcp/protocol.h
index d9ca3a19a218..d65fe3748427 100644
--- a/net/mptcp/protocol.h
+++ b/net/mptcp/protocol.h
@@ -1013,6 +1013,7 @@ void mptcp_pm_subflow_established(struct mptcp_sock *msk);
 bool mptcp_pm_nl_check_work_pending(struct mptcp_sock *msk);
 void mptcp_pm_subflow_check_next(struct mptcp_sock *msk,
 				 const struct mptcp_subflow_context *subflow);
+bool mptcp_pm_add_addr_recv(struct mptcp_sock *msk);
 void mptcp_pm_add_addr_received(const struct sock *ssk,
 				const struct mptcp_addr_info *addr);
 void mptcp_pm_add_addr_echoed(struct mptcp_sock *msk,
-- 
2.45.2


^ permalink raw reply related	[flat|nested] 12+ messages in thread

* [PATCH mptcp-next v2 08/10] mptcp: pm: add add_addr_echo() interface
  2025-03-14  2:45 [PATCH mptcp-next v2 00/10] BPF path manager, part 6 Geliang Tang
                   ` (6 preceding siblings ...)
  2025-03-14  2:45 ` [PATCH mptcp-next v2 07/10] mptcp: pm: add add_addr_received() interface Geliang Tang
@ 2025-03-14  2:45 ` Geliang Tang
  2025-03-14  2:45 ` [PATCH mptcp-next v2 09/10] mptcp: pm: add rm_addr_received() interface Geliang Tang
                   ` (2 subsequent siblings)
  10 siblings, 0 replies; 12+ messages in thread
From: Geliang Tang @ 2025-03-14  2:45 UTC (permalink / raw)
  To: mptcp; +Cc: Geliang Tang

From: Geliang Tang <tanggeliang@kylinos.cn>

The helper mptcp_pm_is_userspace() is used to distinguish userspace PM
operations from in-kernel PM in mptcp_pm_add_addr_received(). It seems
reasonable to add a mandatory .add_addr_echo interface for struct
mptcp_pm_ops.

Signed-off-by: Geliang Tang <tanggeliang@kylinos.cn>
---
 include/net/mptcp.h      |  2 ++
 net/mptcp/pm.c           | 18 +++++-------------
 net/mptcp/pm_kernel.c    |  9 +++++++++
 net/mptcp/pm_userspace.c |  7 +++++++
 net/mptcp/protocol.h     |  2 ++
 5 files changed, 25 insertions(+), 13 deletions(-)

diff --git a/include/net/mptcp.h b/include/net/mptcp.h
index 37a84b4c661e..90fda6d1468c 100644
--- a/include/net/mptcp.h
+++ b/include/net/mptcp.h
@@ -131,6 +131,8 @@ struct mptcp_pm_ops {
 	/* required */
 	bool (*allow_new_subflow)(struct mptcp_sock *msk);
 	bool (*accept_new_subflow)(const struct mptcp_sock *msk);
+	bool (*add_addr_echo)(struct mptcp_sock *msk,
+			      const struct mptcp_addr_info *addr);
 
 	/* optional */
 	int (*add_addr_received)(struct mptcp_sock *msk,
diff --git a/net/mptcp/pm.c b/net/mptcp/pm.c
index 522dd2df4097..d5cb7c60d177 100644
--- a/net/mptcp/pm.c
+++ b/net/mptcp/pm.c
@@ -104,8 +104,8 @@ void mptcp_remote_address(const struct sock_common *skc,
 #endif
 }
 
-static bool mptcp_pm_is_init_remote_addr(struct mptcp_sock *msk,
-					 const struct mptcp_addr_info *remote)
+bool mptcp_pm_is_init_remote_addr(struct mptcp_sock *msk,
+				  const struct mptcp_addr_info *remote)
 {
 	struct mptcp_addr_info mpc_remote;
 
@@ -579,16 +579,7 @@ void mptcp_pm_add_addr_received(const struct sock *ssk,
 
 	spin_lock_bh(&pm->lock);
 
-	if (mptcp_pm_is_userspace(msk)) {
-		if (mptcp_userspace_pm_active(msk)) {
-			mptcp_pm_announce_addr(msk, addr, true);
-			mptcp_pm_add_addr_send_ack(msk);
-		} else {
-			ret = -EINVAL;
-		}
-	/* id0 should not have a different address */
-	} else if ((addr->id == 0 && !mptcp_pm_is_init_remote_addr(msk, addr)) ||
-		   (addr->id > 0 && !READ_ONCE(pm->accept_addr))) {
+	if (pm->ops->add_addr_echo(msk, addr)) {
 		mptcp_pm_announce_addr(msk, addr, true);
 		mptcp_pm_add_addr_send_ack(msk);
 	} else {
@@ -1037,7 +1028,8 @@ struct mptcp_pm_ops *mptcp_pm_find(const char *name)
 int mptcp_pm_validate(struct mptcp_pm_ops *pm_ops)
 {
 	if (!pm_ops->get_local_id || !pm_ops->get_priority ||
-	    !pm_ops->allow_new_subflow || !pm_ops->accept_new_subflow) {
+	    !pm_ops->allow_new_subflow || !pm_ops->accept_new_subflow ||
+	    !pm_ops->add_addr_echo) {
 		pr_err("%s does not implement required ops\n", pm_ops->name);
 		return -EINVAL;
 	}
diff --git a/net/mptcp/pm_kernel.c b/net/mptcp/pm_kernel.c
index 6a5d6d374b0d..74838e2c66ba 100644
--- a/net/mptcp/pm_kernel.c
+++ b/net/mptcp/pm_kernel.c
@@ -1422,6 +1422,14 @@ static bool mptcp_pm_kernel_accept_new_subflow(const struct mptcp_sock *msk)
 	return READ_ONCE(msk->pm.accept_subflow);
 }
 
+static bool mptcp_pm_kernel_add_addr_echo(struct mptcp_sock *msk,
+					  const struct mptcp_addr_info *addr)
+{
+	/* id0 should not have a different address */
+	return (addr->id == 0 && !mptcp_pm_is_init_remote_addr(msk, addr)) ||
+	       (addr->id > 0 && !READ_ONCE(msk->pm.accept_addr));
+}
+
 static int mptcp_pm_kernel_add_addr_received(struct mptcp_sock *msk,
 					     const struct mptcp_addr_info *addr)
 {
@@ -1460,6 +1468,7 @@ struct mptcp_pm_ops mptcp_pm_kernel = {
 	.subflow_established	= mptcp_pm_kernel_subflow_established,
 	.allow_new_subflow	= mptcp_pm_kernel_allow_new_subflow,
 	.accept_new_subflow	= mptcp_pm_kernel_accept_new_subflow,
+	.add_addr_echo		= mptcp_pm_kernel_add_addr_echo,
 	.add_addr_received	= mptcp_pm_kernel_add_addr_received,
 	.init			= mptcp_pm_kernel_init,
 	.name			= "kernel",
diff --git a/net/mptcp/pm_userspace.c b/net/mptcp/pm_userspace.c
index 4cd9a84477c8..6016d5669b9b 100644
--- a/net/mptcp/pm_userspace.c
+++ b/net/mptcp/pm_userspace.c
@@ -701,6 +701,12 @@ static bool mptcp_pm_userspace_accept_new_subflow(const struct mptcp_sock *msk)
 	return mptcp_userspace_pm_active(msk);
 }
 
+static bool mptcp_pm_userspace_add_addr_echo(struct mptcp_sock *msk,
+					     const struct mptcp_addr_info *addr)
+{
+	return mptcp_userspace_pm_active(msk);
+}
+
 static void mptcp_pm_userspace_release(struct mptcp_sock *msk)
 {
 	mptcp_userspace_pm_free_local_addr_list(msk);
@@ -711,6 +717,7 @@ static struct mptcp_pm_ops mptcp_pm_userspace = {
 	.get_priority		= mptcp_pm_userspace_get_priority,
 	.allow_new_subflow	= mptcp_pm_userspace_allow_new_subflow,
 	.accept_new_subflow	= mptcp_pm_userspace_accept_new_subflow,
+	.add_addr_echo		= mptcp_pm_userspace_add_addr_echo,
 	.release		= mptcp_pm_userspace_release,
 	.name			= "userspace",
 	.owner			= THIS_MODULE,
diff --git a/net/mptcp/protocol.h b/net/mptcp/protocol.h
index d65fe3748427..8663350fac2f 100644
--- a/net/mptcp/protocol.h
+++ b/net/mptcp/protocol.h
@@ -1013,6 +1013,8 @@ void mptcp_pm_subflow_established(struct mptcp_sock *msk);
 bool mptcp_pm_nl_check_work_pending(struct mptcp_sock *msk);
 void mptcp_pm_subflow_check_next(struct mptcp_sock *msk,
 				 const struct mptcp_subflow_context *subflow);
+bool mptcp_pm_is_init_remote_addr(struct mptcp_sock *msk,
+				  const struct mptcp_addr_info *remote);
 bool mptcp_pm_add_addr_recv(struct mptcp_sock *msk);
 void mptcp_pm_add_addr_received(const struct sock *ssk,
 				const struct mptcp_addr_info *addr);
-- 
2.45.2


^ permalink raw reply related	[flat|nested] 12+ messages in thread

* [PATCH mptcp-next v2 09/10] mptcp: pm: add rm_addr_received() interface
  2025-03-14  2:45 [PATCH mptcp-next v2 00/10] BPF path manager, part 6 Geliang Tang
                   ` (7 preceding siblings ...)
  2025-03-14  2:45 ` [PATCH mptcp-next v2 08/10] mptcp: pm: add add_addr_echo() interface Geliang Tang
@ 2025-03-14  2:45 ` Geliang Tang
  2025-03-14  2:45 ` [PATCH mptcp-next v2 10/10] mptcp: pm: drop is_userspace in subflow_check_next Geliang Tang
  2025-03-14  3:57 ` [PATCH mptcp-next v2 00/10] BPF path manager, part 6 MPTCP CI
  10 siblings, 0 replies; 12+ messages in thread
From: Geliang Tang @ 2025-03-14  2:45 UTC (permalink / raw)
  To: mptcp; +Cc: Geliang Tang

From: Geliang Tang <tanggeliang@kylinos.cn>

This patch adds an optional .rm_addr_received interface for struct
mptcp_pm_ops and invokes it in mptcp_pm_worker() without PM lock.
Since mptcp_subflow_shutdown() and mptcp_close_ssk() are sleepable
kfuncs, .rm_addr_received interface of BPF PM should be invoked by
__bpf_prog_enter_sleepable(), which can't be invoked under a lock.

Export mptcp_pm_rm_addr_recv() is to allow the MPTCP_PM_RM_ADDR_RECEIVED
worker can be invoke from the in-kernel PM.

With this, mptcp_pm_is_kernel() in mptcp_pm_rm_addr_or_subflow() can
be dropped.

Signed-off-by: Geliang Tang <tanggeliang@kylinos.cn>
---
 include/net/mptcp.h   |  1 +
 net/mptcp/pm.c        | 13 ++++++++++---
 net/mptcp/pm_kernel.c |  6 ++++++
 net/mptcp/protocol.h  |  1 +
 4 files changed, 18 insertions(+), 3 deletions(-)

diff --git a/include/net/mptcp.h b/include/net/mptcp.h
index 90fda6d1468c..bd8a20b9d02b 100644
--- a/include/net/mptcp.h
+++ b/include/net/mptcp.h
@@ -137,6 +137,7 @@ struct mptcp_pm_ops {
 	/* optional */
 	int (*add_addr_received)(struct mptcp_sock *msk,
 				 const struct mptcp_addr_info *addr);
+	void (*rm_addr_received)(struct mptcp_sock *msk);
 
 	char			name[MPTCP_PM_NAME_MAX];
 	struct module		*owner;
diff --git a/net/mptcp/pm.c b/net/mptcp/pm.c
index d5cb7c60d177..70611946dfbf 100644
--- a/net/mptcp/pm.c
+++ b/net/mptcp/pm.c
@@ -676,15 +676,17 @@ static void mptcp_pm_rm_addr_or_subflow(struct mptcp_sock *msk,
 
 		if (rm_type == MPTCP_MIB_RMADDR) {
 			__MPTCP_INC_STATS(sock_net(sk), rm_type);
-			if (removed && mptcp_pm_is_kernel(msk))
+			if (removed)
 				mptcp_pm_nl_rm_addr(msk, rm_id);
 		}
 	}
 }
 
-static void mptcp_pm_rm_addr_recv(struct mptcp_sock *msk)
+void mptcp_pm_rm_addr_recv(struct mptcp_sock *msk)
 {
+	spin_lock_bh(&msk->pm.lock);
 	mptcp_pm_rm_addr_or_subflow(msk, &msk->pm.rm_list_rx, MPTCP_MIB_RMADDR);
+	spin_unlock_bh(&msk->pm.lock);
 }
 
 void mptcp_pm_rm_subflow(struct mptcp_sock *msk,
@@ -704,6 +706,9 @@ void mptcp_pm_rm_addr_received(struct mptcp_sock *msk,
 	for (i = 0; i < rm_list->nr; i++)
 		mptcp_event_addr_removed(msk, rm_list->ids[i]);
 
+	if (!pm->ops->rm_addr_received)
+		return;
+
 	spin_lock_bh(&pm->lock);
 	if (mptcp_pm_schedule_work(msk, MPTCP_PM_RM_ADDR_RECEIVED))
 		pm->rm_list_rx = *rm_list;
@@ -930,7 +935,9 @@ void mptcp_pm_worker(struct mptcp_sock *msk)
 	}
 	if (pm->status & BIT(MPTCP_PM_RM_ADDR_RECEIVED)) {
 		pm->status &= ~BIT(MPTCP_PM_RM_ADDR_RECEIVED);
-		mptcp_pm_rm_addr_recv(msk);
+		spin_unlock_bh(&msk->pm.lock);
+		pm->ops->rm_addr_received(msk);
+		return;
 	}
 	if (pm->status & BIT(MPTCP_PM_ESTABLISHED)) {
 		pm->status &= ~BIT(MPTCP_PM_ESTABLISHED);
diff --git a/net/mptcp/pm_kernel.c b/net/mptcp/pm_kernel.c
index 74838e2c66ba..d04dd1cece09 100644
--- a/net/mptcp/pm_kernel.c
+++ b/net/mptcp/pm_kernel.c
@@ -1441,6 +1441,11 @@ static int mptcp_pm_kernel_add_addr_received(struct mptcp_sock *msk,
 	return -EINVAL;
 }
 
+static void mptcp_pm_kernel_rm_addr_received(struct mptcp_sock *msk)
+{
+	mptcp_pm_rm_addr_recv(msk);
+}
+
 static void mptcp_pm_kernel_init(struct mptcp_sock *msk)
 {
 	bool subflows_allowed = !!mptcp_pm_get_subflows_max(msk);
@@ -1470,6 +1475,7 @@ struct mptcp_pm_ops mptcp_pm_kernel = {
 	.accept_new_subflow	= mptcp_pm_kernel_accept_new_subflow,
 	.add_addr_echo		= mptcp_pm_kernel_add_addr_echo,
 	.add_addr_received	= mptcp_pm_kernel_add_addr_received,
+	.rm_addr_received	= mptcp_pm_kernel_rm_addr_received,
 	.init			= mptcp_pm_kernel_init,
 	.name			= "kernel",
 	.owner			= THIS_MODULE,
diff --git a/net/mptcp/protocol.h b/net/mptcp/protocol.h
index 8663350fac2f..d8b46f8ef8d3 100644
--- a/net/mptcp/protocol.h
+++ b/net/mptcp/protocol.h
@@ -1030,6 +1030,7 @@ void mptcp_pm_rm_subflow(struct mptcp_sock *msk,
 			 const struct mptcp_rm_list *rm_list);
 void mptcp_pm_rm_addr_received(struct mptcp_sock *msk,
 			       const struct mptcp_rm_list *rm_list);
+void mptcp_pm_rm_addr_recv(struct mptcp_sock *msk);
 void mptcp_pm_mp_prio_received(struct sock *sk, u8 bkup);
 void mptcp_pm_mp_fail_received(struct sock *sk, u64 fail_seq);
 int mptcp_pm_mp_prio_send_ack(struct mptcp_sock *msk,
-- 
2.45.2


^ permalink raw reply related	[flat|nested] 12+ messages in thread

* [PATCH mptcp-next v2 10/10] mptcp: pm: drop is_userspace in subflow_check_next
  2025-03-14  2:45 [PATCH mptcp-next v2 00/10] BPF path manager, part 6 Geliang Tang
                   ` (8 preceding siblings ...)
  2025-03-14  2:45 ` [PATCH mptcp-next v2 09/10] mptcp: pm: add rm_addr_received() interface Geliang Tang
@ 2025-03-14  2:45 ` Geliang Tang
  2025-03-14  3:57 ` [PATCH mptcp-next v2 00/10] BPF path manager, part 6 MPTCP CI
  10 siblings, 0 replies; 12+ messages in thread
From: Geliang Tang @ 2025-03-14  2:45 UTC (permalink / raw)
  To: mptcp; +Cc: Geliang Tang

From: Geliang Tang <tanggeliang@kylinos.cn>

In mptcp_pm_subflow_check_next(), instead of reducing "pm->subflows"
for the in-kernel PM in __mptcp_pm_close_subflow(), this patch moves
"pm->subflows--;" forward to let it be used by both the userspace PM
and the in-kernel PM. Then mptcp_pm_is_userspace() here can be dropped.

Signed-off-by: Geliang Tang <tanggeliang@kylinos.cn>
---
 net/mptcp/pm.c | 15 ++++++---------
 1 file changed, 6 insertions(+), 9 deletions(-)

diff --git a/net/mptcp/pm.c b/net/mptcp/pm.c
index 70611946dfbf..d504f9b31893 100644
--- a/net/mptcp/pm.c
+++ b/net/mptcp/pm.c
@@ -531,13 +531,10 @@ void mptcp_pm_subflow_check_next(struct mptcp_sock *msk,
 	bool update_subflows;
 
 	update_subflows = subflow->request_join || subflow->mp_join;
-	if (mptcp_pm_is_userspace(msk)) {
-		if (update_subflows) {
-			spin_lock_bh(&pm->lock);
-			pm->subflows--;
-			spin_unlock_bh(&pm->lock);
-		}
-		return;
+	if (update_subflows) {
+		spin_lock_bh(&pm->lock);
+		pm->subflows--;
+		spin_unlock_bh(&pm->lock);
 	}
 
 	if (!pm->ops->subflow_established)
@@ -547,8 +544,8 @@ void mptcp_pm_subflow_check_next(struct mptcp_sock *msk,
 		return;
 
 	spin_lock_bh(&pm->lock);
-	if (update_subflows)
-		__mptcp_pm_close_subflow(msk);
+	if (update_subflows && msk->pm.subflows < mptcp_pm_get_subflows_max(msk))
+		WRITE_ONCE(msk->pm.accept_subflow, true);
 
 	/* Even if this subflow is not really established, tell the PM to try
 	 * to pick the next ones, if possible.
-- 
2.45.2


^ permalink raw reply related	[flat|nested] 12+ messages in thread

* Re: [PATCH mptcp-next v2 00/10] BPF path manager, part 6
  2025-03-14  2:45 [PATCH mptcp-next v2 00/10] BPF path manager, part 6 Geliang Tang
                   ` (9 preceding siblings ...)
  2025-03-14  2:45 ` [PATCH mptcp-next v2 10/10] mptcp: pm: drop is_userspace in subflow_check_next Geliang Tang
@ 2025-03-14  3:57 ` MPTCP CI
  10 siblings, 0 replies; 12+ messages in thread
From: MPTCP CI @ 2025-03-14  3:57 UTC (permalink / raw)
  To: Geliang Tang; +Cc: mptcp

Hi Geliang,

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/13848993575

Initiator: Patchew Applier
Commits: https://github.com/multipath-tcp/mptcp_net-next/commits/b5c3186d7405
Patchwork: https://patchwork.kernel.org/project/mptcp/list/?series=943747


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-normal

For 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)

^ permalink raw reply	[flat|nested] 12+ messages in thread

end of thread, other threads:[~2025-03-14  3:57 UTC | newest]

Thread overview: 12+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2025-03-14  2:45 [PATCH mptcp-next v2 00/10] BPF path manager, part 6 Geliang Tang
2025-03-14  2:45 ` [PATCH mptcp-next v2 01/10] mptcp: pm: drop redundant MPTCP_MIB_ADDADDRDROP Geliang Tang
2025-03-14  2:45 ` [PATCH mptcp-next v2 02/10] Squash to "mptcp: pm: add get_local_id() interface" Geliang Tang
2025-03-14  2:45 ` [PATCH mptcp-next v2 03/10] mptcp: pm: add established() interface Geliang Tang
2025-03-14  2:45 ` [PATCH mptcp-next v2 04/10] mptcp: pm: add subflow_established() interface Geliang Tang
2025-03-14  2:45 ` [PATCH mptcp-next v2 05/10] mptcp: pm: add allow_new_subflow() interface Geliang Tang
2025-03-14  2:45 ` [PATCH mptcp-next v2 06/10] mptcp: pm: add accept_new_subflow() interface Geliang Tang
2025-03-14  2:45 ` [PATCH mptcp-next v2 07/10] mptcp: pm: add add_addr_received() interface Geliang Tang
2025-03-14  2:45 ` [PATCH mptcp-next v2 08/10] mptcp: pm: add add_addr_echo() interface Geliang Tang
2025-03-14  2:45 ` [PATCH mptcp-next v2 09/10] mptcp: pm: add rm_addr_received() interface Geliang Tang
2025-03-14  2:45 ` [PATCH mptcp-next v2 10/10] mptcp: pm: drop is_userspace in subflow_check_next Geliang Tang
2025-03-14  3:57 ` [PATCH mptcp-next v2 00/10] BPF path manager, part 6 MPTCP CI

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.