From: Serhat Kumral <serhatkumral1@gmail.com>
To: Jason Gunthorpe <jgg@ziepe.ca>, Leon Romanovsky <leon@kernel.org>,
Zhu Yanjun <yanjun.zhu@linux.dev>
Cc: Zhu Yanjun <zyjzyj2000@gmail.com>,
David Ahern <dsahern@kernel.org>,
linux-rdma@vger.kernel.org, linux-kernel@vger.kernel.org,
syzbot+8c9eede336e3a843750e@syzkaller.appspotmail.com,
Serhat Kumral <serhatkumral1@gmail.com>
Subject: [PATCH v2 1/2] RDMA/rxe: drive UDP tunnel socket lifetime from the GID table
Date: Thu, 10 Sep 2026 13:49:05 +0300 [thread overview]
Message-ID: <20260910104906.19681-1-serhatkumral1@gmail.com> (raw)
rxe creates the shared per-netns UDP tunnel sockets in rxe_newlink() and
releases them from dellink, the NETDEV_UNREGISTER notifier and a pernet
exit hook, with driver side bookkeeping deciding when the last user is
gone. Keeping that in sync with the core GID table has been a recurring
source of lifetime bugs, most recently a refcount underflow /
use-after-free reported by syzkaller when those paths raced.
Implement add_gid/del_gid and key the sockets off the GID entries
instead: the first RoCEv2 entry of an address family in a netns creates
the wildcard socket, the last one releases it. The core pairs every
installed GID entry with one del_gid, so the counts have a single owner
and cannot underflow.
The per-netns state is a small global list keyed by netns; no pernet
storage and no pernet hook are needed. rxe_ns.[ch], the sk_refcnt magic
in rxe_net_del() and the .dellink hook are gone.
One behavior change: the core does not propagate add_gid errors, so a
busy port 4791 or a failed allocation no longer fails "rdma link add",
it leaves the GID entry missing.
Suggested-by: Jason Gunthorpe <jgg@ziepe.ca>
Fixes: f1327abd6abe ("RDMA/rxe: Support RDMA link creation and destruction per net namespace")
Reported-by: syzbot+8c9eede336e3a843750e@syzkaller.appspotmail.com
Closes: https://syzkaller.appspot.com/bug?extid=8c9eede336e3a843750e
Assisted-by: Claude:claude-fable-5
Signed-off-by: Serhat Kumral <serhatkumral1@gmail.com>
---
v2:
- Dropped backstop.
v1:https://lore.kernel.org/linux-rdma/20260718142642.102924-1-serhatkumral1@gmail.com/
drivers/infiniband/sw/rxe/Makefile | 3 +-
drivers/infiniband/sw/rxe/rxe.c | 26 +--
drivers/infiniband/sw/rxe/rxe_net.c | 289 +++++++++++++++-----------
drivers/infiniband/sw/rxe/rxe_net.h | 5 +-
drivers/infiniband/sw/rxe/rxe_ns.c | 124 -----------
drivers/infiniband/sw/rxe/rxe_ns.h | 26 ---
drivers/infiniband/sw/rxe/rxe_verbs.c | 2 +
7 files changed, 171 insertions(+), 304 deletions(-)
delete mode 100644 drivers/infiniband/sw/rxe/rxe_ns.c
delete mode 100644 drivers/infiniband/sw/rxe/rxe_ns.h
diff --git a/drivers/infiniband/sw/rxe/Makefile b/drivers/infiniband/sw/rxe/Makefile
index e097c1ca1874..18ff60542744 100644
--- a/drivers/infiniband/sw/rxe/Makefile
+++ b/drivers/infiniband/sw/rxe/Makefile
@@ -23,7 +23,6 @@ rdma_rxe-y := \
rxe_task.o \
rxe_net.o \
rxe_hw_counters.o \
- rxe_mad.o \
- rxe_ns.o
+ rxe_mad.o
rdma_rxe-$(CONFIG_INFINIBAND_ON_DEMAND_PAGING) += rxe_odp.o
diff --git a/drivers/infiniband/sw/rxe/rxe.c b/drivers/infiniband/sw/rxe/rxe.c
index af39209d0fcf..66d5986dac99 100644
--- a/drivers/infiniband/sw/rxe/rxe.c
+++ b/drivers/infiniband/sw/rxe/rxe.c
@@ -9,7 +9,6 @@
#include "rxe.h"
#include "rxe_loc.h"
#include "rxe_net.h"
-#include "rxe_ns.h"
MODULE_AUTHOR("Bob Pearson, Frank Zago, John Groves, Kamal Heib");
MODULE_DESCRIPTION("Soft RDMA transport");
@@ -202,8 +201,6 @@ void rxe_set_mtu(struct rxe_dev *rxe, unsigned int ndev_mtu)
port->mtu_cap = ib_mtu_enum_to_int(mtu);
}
-static struct rdma_link_ops rxe_link_ops;
-
/* called by ifc layer to create new rxe device.
* The caller should allocate memory for rxe by calling ib_alloc_device.
*/
@@ -212,7 +209,6 @@ int rxe_add(struct rxe_dev *rxe, unsigned int mtu, const char *ibdev_name,
{
rxe_init(rxe, ndev);
rxe_set_mtu(rxe, mtu);
- rxe->ib_dev.link_ops = &rxe_link_ops;
return rxe_register_device(rxe, ibdev_name, ndev);
}
@@ -236,10 +232,6 @@ static int rxe_newlink(const char *ibdev_name, struct net_device *ndev)
goto err;
}
- err = rxe_net_init(ndev);
- if (err)
- return err;
-
err = rxe_net_add(ibdev_name, ndev);
if (err) {
rxe_err("failed to add %s\n", ndev->name);
@@ -249,17 +241,9 @@ static int rxe_newlink(const char *ibdev_name, struct net_device *ndev)
return err;
}
-static int rxe_dellink(struct ib_device *dev)
-{
- rxe_net_del(dev);
-
- return 0;
-}
-
static struct rdma_link_ops rxe_link_ops = {
.type = "rxe",
.newlink = rxe_newlink,
- .dellink = rxe_dellink,
};
static int __init rxe_module_init(void)
@@ -270,21 +254,15 @@ static int __init rxe_module_init(void)
if (err)
return err;
- err = rxe_namespace_init();
- if (err)
- goto err_destroy_wq;
-
err = rxe_register_notifier();
if (err)
- goto err_namespace_exit;
+ goto err_destroy_wq;
rdma_link_register(&rxe_link_ops);
pr_info("loaded\n");
return 0;
-err_namespace_exit:
- rxe_namespace_exit();
err_destroy_wq:
rxe_destroy_wq();
return err;
@@ -297,8 +275,6 @@ static void __exit rxe_module_exit(void)
rxe_net_exit();
rxe_destroy_wq();
- rxe_namespace_exit();
-
pr_info("unloaded\n");
}
diff --git a/drivers/infiniband/sw/rxe/rxe_net.c b/drivers/infiniband/sw/rxe/rxe_net.c
index 53daaf4c1eb2..fa1cf49c13e3 100644
--- a/drivers/infiniband/sw/rxe/rxe_net.c
+++ b/drivers/infiniband/sw/rxe/rxe_net.c
@@ -17,11 +17,6 @@
#include "rxe.h"
#include "rxe_net.h"
#include "rxe_loc.h"
-#include "rxe_ns.h"
-
-#ifndef SK_REF_FOR_TUNNEL
-#define SK_REF_FOR_TUNNEL 2
-#endif
#ifdef CONFIG_DEBUG_LOCK_ALLOC
/*
@@ -81,9 +76,9 @@ static inline void rxe_reclassify_recv_socket(struct socket *sock)
* from being called and 'rmmod rdma_rxe'
* is refused because of the references.
*
- * For the global sockets in recv_sockets,
- * we are sure that rxe_net_exit() will call
- * rxe_release_udp_tunnel -> udp_tunnel_sock_release.
+ * For the shared tunnel sockets, the last
+ * rxe_del_gid() calls udp_tunnel_sock_release().
+ * All GID entries are removed before module exit.
*
* So we don't need the additional reference to
* our own (THIS_MODULE).
@@ -141,7 +136,7 @@ static struct dst_entry *rxe_find_route6(struct rxe_qp *qp,
memcpy(&fl6.daddr, daddr, sizeof(*daddr));
fl6.flowi6_proto = IPPROTO_UDP;
- ndst = ip6_dst_lookup_flow(net, rxe_ns_pernet_sk6(net), &fl6, NULL);
+ ndst = ip6_dst_lookup_flow(net, NULL, &fl6, NULL);
if (IS_ERR(ndst)) {
rxe_dbg_qp(qp, "no route to %pI6\n", daddr);
return NULL;
@@ -288,10 +283,165 @@ static struct socket *rxe_setup_udp_tunnel(struct net *net, __be16 port,
return sock;
}
-static void rxe_release_udp_tunnel(struct sock *sk)
+/*
+ * The wildcard tunnel sockets are shared by every RoCEv2 GID entry in
+ * a netns. The first entry of an address family creates its socket and
+ * the last del_gid releases it. The GID table pairs each successful
+ * add_gid with one del_gid, so only these callbacks own the counts.
+ *
+ * GID removal can outlive netns teardown. Keep the state in a global
+ * list instead of pernet storage; the sockets' passive net references
+ * keep the net pointer valid as a list key until the sockets are released.
+ */
+struct rxe_ns_sock {
+ struct list_head node;
+ struct net *net;
+ struct socket *sk4;
+ struct socket *sk6;
+ int nr4;
+ int nr6;
+};
+
+static DEFINE_MUTEX(rxe_ns_lock);
+static LIST_HEAD(rxe_ns_list);
+
+static struct rxe_ns_sock *rxe_ns_find(struct net *net)
+{
+ struct rxe_ns_sock *ns;
+
+ lockdep_assert_held(&rxe_ns_lock);
+
+ list_for_each_entry(ns, &rxe_ns_list, node)
+ if (ns->net == net)
+ return ns;
+
+ return NULL;
+}
+
+int rxe_add_gid(const struct ib_gid_attr *attr, void **context)
+{
+ bool ipv6 = rdma_gid_attr_network_type(attr) == RDMA_NETWORK_IPV6;
+ __be16 port = htons(ROCE_V2_UDP_DPORT);
+ struct net_device *ndev;
+ struct rxe_ns_sock *ns;
+ struct socket *sock;
+ struct net *net;
+ int err = 0;
+
+ *context = NULL;
+
+ /* Only RoCEv2 GIDs use a UDP tunnel socket. */
+ if (attr->gid_type != IB_GID_TYPE_ROCE_UDP_ENCAP)
+ return 0;
+
+ /*
+ * Hold the netns across the socket setup; this also fails
+ * instead of binding a new socket in a netns that is already
+ * being dismantled.
+ */
+ rcu_read_lock();
+ ndev = rcu_dereference(attr->ndev);
+ net = ndev ? maybe_get_net(dev_net_rcu(ndev)) : NULL;
+ rcu_read_unlock();
+ if (!net)
+ return -ENODEV;
+
+ mutex_lock(&rxe_ns_lock);
+ ns = rxe_ns_find(net);
+ if (!ns) {
+ ns = kzalloc_obj(*ns);
+ if (!ns) {
+ err = -ENOMEM;
+ goto out_unlock;
+ }
+ ns->net = net;
+ list_add(&ns->node, &rxe_ns_list);
+ }
+
+ if (ipv6) {
+ if (!ns->nr6) {
+ sock = rxe_setup_udp_tunnel(net, port, true);
+ if (IS_ERR(sock)) {
+ err = PTR_ERR(sock);
+ /*
+ * No IPv6 support: leave this GID entry
+ * without a socket and without a count;
+ * rxe_del_gid() skips a NULL context.
+ */
+ if (err == -EAFNOSUPPORT ||
+ err == -EPFNOSUPPORT)
+ err = 0;
+ goto out_free;
+ }
+ ns->sk6 = sock;
+ }
+ ns->nr6++;
+ } else {
+ if (!ns->nr4) {
+ sock = rxe_setup_udp_tunnel(net, port, false);
+ if (IS_ERR(sock)) {
+ err = PTR_ERR(sock);
+ goto out_free;
+ }
+ ns->sk4 = sock;
+ }
+ ns->nr4++;
+ }
+ mutex_unlock(&rxe_ns_lock);
+
+ put_net(net);
+ *context = ns;
+ return 0;
+
+out_free:
+ if (!ns->nr4 && !ns->nr6) {
+ list_del(&ns->node);
+ kfree(ns);
+ }
+out_unlock:
+ mutex_unlock(&rxe_ns_lock);
+ put_net(net);
+ return err;
+}
+
+int rxe_del_gid(const struct ib_gid_attr *attr, void **context)
{
- if (sk)
- udp_tunnel_sock_release(sk);
+ bool ipv6 = rdma_gid_attr_network_type(attr) == RDMA_NETWORK_IPV6;
+ struct rxe_ns_sock *ns = *context;
+ struct socket *sock = NULL;
+
+ if (!ns)
+ return 0;
+
+ *context = NULL;
+
+ mutex_lock(&rxe_ns_lock);
+ if (ipv6) {
+ if (!WARN_ON_ONCE(!ns->nr6) && !--ns->nr6) {
+ sock = ns->sk6;
+ ns->sk6 = NULL;
+ }
+ } else {
+ if (!WARN_ON_ONCE(!ns->nr4) && !--ns->nr4) {
+ sock = ns->sk4;
+ ns->sk4 = NULL;
+ }
+ }
+ /*
+ * Release under the lock: a concurrent rxe_add_gid() must not
+ * see a zero count while the old socket still holds the port,
+ * or its bind() fails with -EADDRINUSE.
+ */
+ if (sock)
+ udp_tunnel_sock_release(sock->sk);
+
+ if (!ns->nr4 && !ns->nr6) {
+ list_del(&ns->node);
+ kfree(ns);
+ }
+ mutex_unlock(&rxe_ns_lock);
+
+ return 0;
}
static void prepare_udp_hdr(struct sk_buff *skb, __be16 src_port,
@@ -631,42 +781,6 @@ int rxe_net_add(const char *ibdev_name, struct net_device *ndev)
return 0;
}
-static void rxe_sock_put(struct sock *sk,
- void (*set_sk)(struct net *, struct sock *),
- struct net *net)
-{
- if (refcount_read(&sk->sk_refcnt) > SK_REF_FOR_TUNNEL) {
- __sock_put(sk);
- } else {
- rxe_release_udp_tunnel(sk);
- sk = NULL;
- set_sk(net, sk);
- }
-}
-
-void rxe_net_del(struct ib_device *dev)
-{
- struct net_device *ndev;
- struct sock *sk;
- struct net *net;
-
- ndev = ib_device_get_netdev(dev, 1);
- if (!ndev)
- return;
-
- net = dev_net(ndev);
-
- sk = rxe_ns_pernet_sk4(net);
- if (sk)
- rxe_sock_put(sk, rxe_ns_pernet_set_sk4, net);
-
- sk = rxe_ns_pernet_sk6(net);
- if (sk)
- rxe_sock_put(sk, rxe_ns_pernet_set_sk6, net);
-
- dev_put(ndev);
-}
-
static void rxe_port_event(struct rxe_dev *rxe,
enum ib_event_type event)
{
@@ -723,7 +837,6 @@ static int rxe_notify(struct notifier_block *not_blk,
switch (event) {
case NETDEV_UNREGISTER:
ib_unregister_device_queued(&rxe->ib_dev);
- rxe_net_del(&rxe->ib_dev);
break;
case NETDEV_CHANGEMTU:
rxe_dbg_dev(rxe, "%s changed mtu to %d\n", ndev->name, ndev->mtu);
@@ -753,56 +866,6 @@ static struct notifier_block rxe_net_notifier = {
.notifier_call = rxe_notify,
};
-static int rxe_net_ipv4_init(struct net *net)
-{
- struct sock *sk;
- struct socket *sock;
-
- sk = rxe_ns_pernet_sk4(net);
- if (sk) {
- sock_hold(sk);
- return 0;
- }
-
- sock = rxe_setup_udp_tunnel(net, htons(ROCE_V2_UDP_DPORT), false);
- if (IS_ERR(sock)) {
- pr_err("Failed to create IPv4 UDP tunnel\n");
- return -1;
- }
- rxe_ns_pernet_set_sk4(net, sock->sk);
-
- return 0;
-}
-
-static int rxe_net_ipv6_init(struct net *net)
-{
-#if IS_ENABLED(CONFIG_IPV6)
- struct sock *sk;
- struct socket *sock;
-
- sk = rxe_ns_pernet_sk6(net);
- if (sk) {
- sock_hold(sk);
- return 0;
- }
-
- sock = rxe_setup_udp_tunnel(net, htons(ROCE_V2_UDP_DPORT), true);
- if (PTR_ERR(sock) == -EAFNOSUPPORT) {
- pr_warn("IPv6 is not supported, can not create a UDPv6 socket\n");
- return 0;
- }
-
- if (IS_ERR(sock)) {
- pr_err("Failed to create IPv6 UDP tunnel\n");
- return -1;
- }
-
- rxe_ns_pernet_set_sk6(net, sock->sk);
-
-#endif
- return 0;
-}
-
int rxe_register_notifier(void)
{
int err;
@@ -819,31 +882,7 @@ int rxe_register_notifier(void)
void rxe_net_exit(void)
{
unregister_netdevice_notifier(&rxe_net_notifier);
-}
-
-int rxe_net_init(struct net_device *ndev)
-{
- struct net *net;
- struct sock *sk;
- int err;
-
- net = dev_net(ndev);
- err = rxe_net_ipv4_init(net);
- if (err)
- return err;
-
- err = rxe_net_ipv6_init(net);
- if (err)
- goto err_out;
-
- return 0;
-
-err_out:
- /* If ipv6 error, release ipv4 resource */
- sk = rxe_ns_pernet_sk4(net);
- if (sk)
- rxe_sock_put(sk, rxe_ns_pernet_set_sk4, net);
-
- return err;
+ /* All devices and thus all GID entries are gone by now. */
+ WARN_ON(!list_empty(&rxe_ns_list));
}
diff --git a/drivers/infiniband/sw/rxe/rxe_net.h b/drivers/infiniband/sw/rxe/rxe_net.h
index 56249677d692..b564ff5c83f3 100644
--- a/drivers/infiniband/sw/rxe/rxe_net.h
+++ b/drivers/infiniband/sw/rxe/rxe_net.h
@@ -12,10 +12,11 @@
#include <linux/module.h>
int rxe_net_add(const char *ibdev_name, struct net_device *ndev);
-void rxe_net_del(struct ib_device *dev);
+
+int rxe_add_gid(const struct ib_gid_attr *attr, void **context);
+int rxe_del_gid(const struct ib_gid_attr *attr, void **context);
int rxe_register_notifier(void);
-int rxe_net_init(struct net_device *ndev);
void rxe_net_exit(void);
#endif /* RXE_NET_H */
diff --git a/drivers/infiniband/sw/rxe/rxe_ns.c b/drivers/infiniband/sw/rxe/rxe_ns.c
deleted file mode 100644
index 64621c89f8bf..000000000000
--- a/drivers/infiniband/sw/rxe/rxe_ns.c
+++ /dev/null
@@ -1,124 +0,0 @@
-/* SPDX-License-Identifier: GPL-2.0 OR Linux-OpenIB */
-
-#include <net/sock.h>
-#include <net/netns/generic.h>
-#include <net/net_namespace.h>
-#include <linux/module.h>
-#include <linux/skbuff.h>
-#include <linux/pid_namespace.h>
-#include <net/udp_tunnel.h>
-
-#include "rxe_ns.h"
-
-/*
- * Per network namespace data
- */
-struct rxe_ns_sock {
- struct sock __rcu *rxe_sk4;
- struct sock __rcu *rxe_sk6;
-};
-
-/*
- * Index to store custom data for each network namespace.
- */
-static unsigned int rxe_pernet_id;
-
-/*
- * Called for every existing and added network namespaces
- */
-static int rxe_ns_init(struct net *net)
-{
- /* defer socket create in the namespace to the first
- * device create.
- */
-
- return 0;
-}
-
-static void rxe_ns_exit(struct net *net)
-{
- /* called when the network namespace is removed
- */
- struct rxe_ns_sock *ns_sk = net_generic(net, rxe_pernet_id);
- struct sock *sk;
-
- rcu_read_lock();
- sk = rcu_dereference(ns_sk->rxe_sk4);
- rcu_read_unlock();
- if (sk) {
- rcu_assign_pointer(ns_sk->rxe_sk4, NULL);
- udp_tunnel_sock_release(sk);
- }
-
-#if IS_ENABLED(CONFIG_IPV6)
- rcu_read_lock();
- sk = rcu_dereference(ns_sk->rxe_sk6);
- rcu_read_unlock();
- if (sk) {
- rcu_assign_pointer(ns_sk->rxe_sk6, NULL);
- udp_tunnel_sock_release(sk);
- }
-#endif
-}
-
-/*
- * callback to make the module network namespace aware
- */
-static struct pernet_operations rxe_net_ops = {
- .init = rxe_ns_init,
- .exit = rxe_ns_exit,
- .id = &rxe_pernet_id,
- .size = sizeof(struct rxe_ns_sock),
-};
-
-struct sock *rxe_ns_pernet_sk4(struct net *net)
-{
- struct rxe_ns_sock *ns_sk = net_generic(net, rxe_pernet_id);
- struct sock *sk;
-
- rcu_read_lock();
- sk = rcu_dereference(ns_sk->rxe_sk4);
- rcu_read_unlock();
-
- return sk;
-}
-
-void rxe_ns_pernet_set_sk4(struct net *net, struct sock *sk)
-{
- struct rxe_ns_sock *ns_sk = net_generic(net, rxe_pernet_id);
-
- rcu_assign_pointer(ns_sk->rxe_sk4, sk);
- synchronize_rcu();
-}
-
-#if IS_ENABLED(CONFIG_IPV6)
-struct sock *rxe_ns_pernet_sk6(struct net *net)
-{
- struct rxe_ns_sock *ns_sk = net_generic(net, rxe_pernet_id);
- struct sock *sk;
-
- rcu_read_lock();
- sk = rcu_dereference(ns_sk->rxe_sk6);
- rcu_read_unlock();
-
- return sk;
-}
-
-void rxe_ns_pernet_set_sk6(struct net *net, struct sock *sk)
-{
- struct rxe_ns_sock *ns_sk = net_generic(net, rxe_pernet_id);
-
- rcu_assign_pointer(ns_sk->rxe_sk6, sk);
- synchronize_rcu();
-}
-#endif /* IPV6 */
-
-int rxe_namespace_init(void)
-{
- return register_pernet_subsys(&rxe_net_ops);
-}
-
-void rxe_namespace_exit(void)
-{
- unregister_pernet_subsys(&rxe_net_ops);
-}
diff --git a/drivers/infiniband/sw/rxe/rxe_ns.h b/drivers/infiniband/sw/rxe/rxe_ns.h
deleted file mode 100644
index 4da2709e6b71..000000000000
--- a/drivers/infiniband/sw/rxe/rxe_ns.h
+++ /dev/null
@@ -1,26 +0,0 @@
-/* SPDX-License-Identifier: GPL-2.0 OR Linux-OpenIB */
-
-#ifndef RXE_NS_H
-#define RXE_NS_H
-
-struct sock *rxe_ns_pernet_sk4(struct net *net);
-void rxe_ns_pernet_set_sk4(struct net *net, struct sock *sk);
-
-#if IS_ENABLED(CONFIG_IPV6)
-void rxe_ns_pernet_set_sk6(struct net *net, struct sock *sk);
-struct sock *rxe_ns_pernet_sk6(struct net *net);
-#else /* IPv6 */
-static inline struct sock *rxe_ns_pernet_sk6(struct net *net)
-{
- return NULL;
-}
-
-static inline void rxe_ns_pernet_set_sk6(struct net *net, struct sock *sk)
-{
-}
-#endif /* IPv6 */
-
-int rxe_namespace_init(void);
-void rxe_namespace_exit(void);
-
-#endif /* RXE_NS_H */
diff --git a/drivers/infiniband/sw/rxe/rxe_verbs.c b/drivers/infiniband/sw/rxe/rxe_verbs.c
index 96c7716057fe..278da342ca1e 100644
--- a/drivers/infiniband/sw/rxe/rxe_verbs.c
+++ b/drivers/infiniband/sw/rxe/rxe_verbs.c
@@ -1460,6 +1460,7 @@ static const struct ib_device_ops rxe_dev_ops = {
.driver_id = RDMA_DRIVER_RXE,
.uverbs_abi_ver = RXE_UVERBS_ABI_VERSION,
+ .add_gid = rxe_add_gid,
.alloc_hw_port_stats = rxe_ib_alloc_hw_port_stats,
.alloc_mr = rxe_alloc_mr,
.alloc_mw = rxe_alloc_mw,
@@ -1475,6 +1476,7 @@ static const struct ib_device_ops rxe_dev_ops = {
.dealloc_mw = rxe_dealloc_mw,
.dealloc_pd = rxe_dealloc_pd,
.dealloc_ucontext = rxe_dealloc_ucontext,
+ .del_gid = rxe_del_gid,
.dereg_mr = rxe_dereg_mr,
.destroy_ah = rxe_destroy_ah,
.destroy_cq = rxe_destroy_cq,
base-commit: cee9395acd8043be0644b25c34bfa86623f2b935
--
2.53.0
next reply other threads:[~2026-09-10 10:49 UTC|newest]
Thread overview: 2+ messages / expand[flat|nested] mbox.gz Atom feed top
2026-09-10 10:49 Serhat Kumral [this message]
2026-09-10 10:49 ` [PATCH v2 2/2] RDMA/nldev: remove the unused dellink link op Serhat Kumral
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20260910104906.19681-1-serhatkumral1@gmail.com \
--to=serhatkumral1@gmail.com \
--cc=dsahern@kernel.org \
--cc=jgg@ziepe.ca \
--cc=leon@kernel.org \
--cc=linux-kernel@vger.kernel.org \
--cc=linux-rdma@vger.kernel.org \
--cc=syzbot+8c9eede336e3a843750e@syzkaller.appspotmail.com \
--cc=yanjun.zhu@linux.dev \
--cc=zyjzyj2000@gmail.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox
all inboxes | Powered by JetHome®