nvmf/rdma: Send ibv async event to the correct thread
Since rqpair->qpair.group is set to NULL when we remove the qpair from poll group, we fail to send event to qpair's thread. This patch adds a pointer to io_chaneel to spdk_nvmf_rdma_qpair structure and a function to handle poll_group_remove transport operation. In this function we get io_channel from nvmf_tgt, this channel will be used to get a thread for sending async event notification. This also guarantees that the thread will be alive while we are destroying qpair. Change-Id: I1222be9f9004304ba0a90edf6d56d316d014efda Signed-off-by: Alexey Marchuk <alexeymar@mellanox.com> Reviewed-on: https://review.spdk.io/gerrit/c/spdk/spdk/+/3475 Community-CI: Mellanox Build Bot Tested-by: SPDK CI Jenkins <sys_sgci@intel.com> Reviewed-by: Jacek Kalwas <jacek.kalwas@intel.com> Reviewed-by: Seth Howell <seth.howell@intel.com> Reviewed-by: Ben Walker <benjamin.walker@intel.com> Reviewed-by: Jim Harris <james.r.harris@intel.com>
This commit is contained in:
parent
8991773390
commit
3d1d4fcf54
@ -403,6 +403,11 @@ struct spdk_nvmf_rdma_qpair {
|
||||
|
||||
struct spdk_poller *destruct_poller;
|
||||
|
||||
/*
|
||||
* io_channel which is used to destroy qpair when it is removed from poll group
|
||||
*/
|
||||
struct spdk_io_channel *destruct_channel;
|
||||
|
||||
/* List of ibv async events */
|
||||
STAILQ_HEAD(, spdk_nvmf_rdma_ibv_event_ctx) ibv_events;
|
||||
|
||||
@ -910,6 +915,11 @@ nvmf_rdma_qpair_destroy(struct spdk_nvmf_rdma_qpair *rqpair)
|
||||
|
||||
nvmf_rdma_qpair_clean_ibv_events(rqpair);
|
||||
|
||||
if (rqpair->destruct_channel) {
|
||||
spdk_put_io_channel(rqpair->destruct_channel);
|
||||
rqpair->destruct_channel = NULL;
|
||||
}
|
||||
|
||||
free(rqpair);
|
||||
}
|
||||
|
||||
@ -3076,22 +3086,36 @@ nvmf_rdma_send_qpair_async_event(struct spdk_nvmf_rdma_qpair *rqpair,
|
||||
spdk_nvmf_rdma_qpair_ibv_event fn)
|
||||
{
|
||||
struct spdk_nvmf_rdma_ibv_event_ctx *ctx;
|
||||
struct spdk_thread *thr = NULL;
|
||||
int rc;
|
||||
|
||||
if (!rqpair->qpair.group) {
|
||||
return EINVAL;
|
||||
if (rqpair->qpair.group) {
|
||||
thr = rqpair->qpair.group->thread;
|
||||
} else if (rqpair->destruct_channel) {
|
||||
thr = spdk_io_channel_get_thread(rqpair->destruct_channel);
|
||||
}
|
||||
|
||||
if (!thr) {
|
||||
SPDK_DEBUGLOG(SPDK_LOG_RDMA, "rqpair %p has no thread\n", rqpair);
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
ctx = calloc(1, sizeof(*ctx));
|
||||
if (!ctx) {
|
||||
return ENOMEM;
|
||||
return -ENOMEM;
|
||||
}
|
||||
|
||||
ctx->rqpair = rqpair;
|
||||
ctx->cb_fn = fn;
|
||||
STAILQ_INSERT_TAIL(&rqpair->ibv_events, ctx, link);
|
||||
|
||||
return spdk_thread_send_msg(rqpair->qpair.group->thread, nvmf_rdma_qpair_process_ibv_event,
|
||||
ctx);
|
||||
rc = spdk_thread_send_msg(thr, nvmf_rdma_qpair_process_ibv_event, ctx);
|
||||
if (rc) {
|
||||
STAILQ_REMOVE(&rqpair->ibv_events, ctx, spdk_nvmf_rdma_ibv_event_ctx, link);
|
||||
free(ctx);
|
||||
}
|
||||
|
||||
return rc;
|
||||
}
|
||||
|
||||
static void
|
||||
@ -3115,8 +3139,9 @@ nvmf_process_ib_event(struct spdk_nvmf_rdma_device *device)
|
||||
SPDK_ERRLOG("Fatal event received for rqpair %p\n", rqpair);
|
||||
spdk_trace_record(TRACE_RDMA_IBV_ASYNC_EVENT, 0, 0,
|
||||
(uintptr_t)rqpair->cm_id, event.event_type);
|
||||
if (nvmf_rdma_send_qpair_async_event(rqpair, nvmf_rdma_handle_qp_fatal)) {
|
||||
SPDK_ERRLOG("Failed to send QP_FATAL event for rqpair %p\n", rqpair);
|
||||
rc = nvmf_rdma_send_qpair_async_event(rqpair, nvmf_rdma_handle_qp_fatal);
|
||||
if (rc) {
|
||||
SPDK_WARNLOG("Failed to send QP_FATAL event. rqpair %p, err %d\n", rqpair, rc);
|
||||
nvmf_rdma_handle_qp_fatal(rqpair);
|
||||
}
|
||||
break;
|
||||
@ -3124,8 +3149,9 @@ nvmf_process_ib_event(struct spdk_nvmf_rdma_device *device)
|
||||
/* This event only occurs for shared receive queues. */
|
||||
rqpair = event.element.qp->qp_context;
|
||||
SPDK_DEBUGLOG(SPDK_LOG_RDMA, "Last WQE reached event received for rqpair %p\n", rqpair);
|
||||
if (nvmf_rdma_send_qpair_async_event(rqpair, nvmf_rdma_handle_last_wqe_reached)) {
|
||||
SPDK_ERRLOG("Failed to send LAST_WQE_REACHED event for rqpair %p\n", rqpair);
|
||||
rc = nvmf_rdma_send_qpair_async_event(rqpair, nvmf_rdma_handle_last_wqe_reached);
|
||||
if (rc) {
|
||||
SPDK_WARNLOG("Failed to send LAST_WQE_REACHED event. rqpair %p, err %d\n", rqpair, rc);
|
||||
rqpair->last_wqe_reached = true;
|
||||
}
|
||||
break;
|
||||
@ -3137,8 +3163,9 @@ nvmf_process_ib_event(struct spdk_nvmf_rdma_device *device)
|
||||
spdk_trace_record(TRACE_RDMA_IBV_ASYNC_EVENT, 0, 0,
|
||||
(uintptr_t)rqpair->cm_id, event.event_type);
|
||||
if (nvmf_rdma_update_ibv_state(rqpair) == IBV_QPS_ERR) {
|
||||
if (nvmf_rdma_send_qpair_async_event(rqpair, nvmf_rdma_handle_sq_drained)) {
|
||||
SPDK_ERRLOG("Failed to send SQ_DRAINED event for rqpair %p\n", rqpair);
|
||||
rc = nvmf_rdma_send_qpair_async_event(rqpair, nvmf_rdma_handle_sq_drained);
|
||||
if (rc) {
|
||||
SPDK_WARNLOG("Failed to send SQ_DRAINED event. rqpair %p, err %d\n", rqpair, rc);
|
||||
nvmf_rdma_handle_sq_drained(rqpair);
|
||||
}
|
||||
}
|
||||
@ -3510,6 +3537,30 @@ nvmf_rdma_poll_group_add(struct spdk_nvmf_transport_poll_group *group,
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int
|
||||
nvmf_rdma_poll_group_remove(struct spdk_nvmf_transport_poll_group *group,
|
||||
struct spdk_nvmf_qpair *qpair)
|
||||
{
|
||||
struct spdk_nvmf_rdma_qpair *rqpair;
|
||||
|
||||
rqpair = SPDK_CONTAINEROF(qpair, struct spdk_nvmf_rdma_qpair, qpair);
|
||||
assert(group->transport->tgt != NULL);
|
||||
|
||||
rqpair->destruct_channel = spdk_get_io_channel(group->transport->tgt);
|
||||
|
||||
if (!rqpair->destruct_channel) {
|
||||
SPDK_WARNLOG("failed to get io_channel, qpair %p\n", qpair);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Sanity check that we get io_channel on the correct thread */
|
||||
if (qpair->group) {
|
||||
assert(qpair->group->thread == spdk_io_channel_get_thread(rqpair->destruct_channel));
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int
|
||||
nvmf_rdma_request_free(struct spdk_nvmf_request *req)
|
||||
{
|
||||
@ -4225,6 +4276,7 @@ const struct spdk_nvmf_transport_ops spdk_nvmf_transport_rdma = {
|
||||
.get_optimal_poll_group = nvmf_rdma_get_optimal_poll_group,
|
||||
.poll_group_destroy = nvmf_rdma_poll_group_destroy,
|
||||
.poll_group_add = nvmf_rdma_poll_group_add,
|
||||
.poll_group_remove = nvmf_rdma_poll_group_remove,
|
||||
.poll_group_poll = nvmf_rdma_poll_group_poll,
|
||||
|
||||
.req_free = nvmf_rdma_request_free,
|
||||
|
Loading…
Reference in New Issue
Block a user