Skip to content

Commit

Permalink
mptcp: add userspace pm addr entry refcount
Browse files Browse the repository at this point in the history
This patch adds the refcount of addree entry in userspace PM. Add a new
counter 'refcnt' in struct mptcp_pm_addr_entry, initiated to 1.

Increase this counter when an address is announced or a subflow is created
in mptcp_pm_nl_announce_doit() and mptcp_pm_nl_subflow_create_doit(). And
decrease it when an address is removed or a subflow is closed in
mptcp_pm_nl_remove_doit() and mptcp_userspace_pm_delete_local_addr(). If
the counter reaches to 1, free this entry.

Closes: multipath-tcp/mptcp_net-next#403
Fixes: 24430f8 ("mptcp: add address into userspace pm list")
Signed-off-by: Geliang Tang <[email protected]>
  • Loading branch information
geliangtang authored and intel-lab-lkp committed Nov 17, 2023
1 parent 8808bc8 commit 7a0a8cb
Show file tree
Hide file tree
Showing 2 changed files with 25 additions and 10 deletions.
33 changes: 23 additions & 10 deletions net/mptcp/pm_userspace.c
Original file line number Diff line number Diff line change
Expand Up @@ -84,6 +84,7 @@ static int mptcp_userspace_pm_append_new_local_addr(struct mptcp_sock *msk,
__set_bit(e->addr.id, pernet->id_bitmap);
list_add_tail_rcu(&e->list, &msk->pm.userspace_pm_local_addr_list);
msk->pm.local_addr_used++;
refcount_set(&e->refcnt, 1);
ret = e->addr.id;
goto append_err;
}
Expand All @@ -109,12 +110,11 @@ static int mptcp_userspace_pm_delete_local_addr(struct mptcp_sock *msk,

entry = mptcp_userspace_pm_get_entry(msk, &addr->addr, false, false);
if (entry) {
/* TODO: a refcount is needed because the entry can
* be used multiple times (e.g. fullmesh mode).
*/
list_del_rcu(&entry->list);
kfree(entry);
msk->pm.local_addr_used--;
if (!refcount_dec_not_one(&entry->refcnt)) {
list_del_rcu(&entry->list);
kfree(entry);
msk->pm.local_addr_used--;
}
return 0;
}

Expand Down Expand Up @@ -215,6 +215,11 @@ int mptcp_pm_nl_announce_doit(struct sk_buff *skb, struct genl_info *info)
spin_lock_bh(&msk->pm.lock);

if (mptcp_pm_alloc_anno_list(msk, &addr_val.addr)) {
struct mptcp_pm_addr_entry *entry;

entry = mptcp_userspace_pm_get_entry(msk, &addr_val.addr, false, false);
if (entry && !refcount_inc_not_zero(&entry->refcnt))
pr_debug("userspace pm uninitialized entry");
msk->pm.add_addr_signaled++;
mptcp_pm_announce_addr(msk, &addr_val.addr, false);
mptcp_pm_nl_addr_send_ack(msk);
Expand Down Expand Up @@ -320,8 +325,10 @@ int mptcp_pm_nl_remove_doit(struct sk_buff *skb, struct genl_info *info)

mptcp_pm_remove_addrs(msk, &free_list);

list_del_rcu(&match->list);
kfree(match);
if (!refcount_dec_not_one(&match->refcnt)) {
list_del_rcu(&match->list);
kfree(match);
}

release_sock(sk);

Expand Down Expand Up @@ -407,10 +414,16 @@ int mptcp_pm_nl_subflow_create_doit(struct sk_buff *skb, struct genl_info *info)
release_sock(sk);

spin_lock_bh(&msk->pm.lock);
if (err)
if (err) {
mptcp_userspace_pm_delete_local_addr(msk, &local);
else
} else {
struct mptcp_pm_addr_entry *entry;

entry = mptcp_userspace_pm_get_entry(msk, &addr_l, false, false);
if (entry && !refcount_inc_not_zero(&entry->refcnt))
pr_debug("userspace pm uninitialized entry");
msk->pm.subflows++;
}
spin_unlock_bh(&msk->pm.lock);

create_err:
Expand Down
2 changes: 2 additions & 0 deletions net/mptcp/protocol.h
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@
#define __MPTCP_PROTOCOL_H

#include <linux/random.h>
#include <linux/refcount.h>
#include <net/tcp.h>
#include <net/inet_connection_sock.h>
#include <uapi/linux/mptcp.h>
Expand Down Expand Up @@ -244,6 +245,7 @@ struct mptcp_pm_addr_entry {
u8 flags;
int ifindex;
struct socket *lsk;
refcount_t refcnt;
};

struct mptcp_data_frag {
Expand Down

0 comments on commit 7a0a8cb

Please sign in to comment.