rdma: Add API function to disconnect qpair

This is a wrapper over RDMA CM rdma_disconnect function
The wrapper is needed since in Mellanox Direct Verbs
(aka DV) we must move qpair to error state manually
before calling rdma_disconnect

Change-Id: Ia8623c6989e7679591f2da56bafa7f4262eeebf9
Signed-off-by: Alexey Marchuk <alexeymar@mellanox.com>
Reviewed-on: https://review.spdk.io/gerrit/c/spdk/spdk/+/1975
Tested-by: SPDK CI Jenkins <sys_sgci@intel.com>
Community-CI: Mellanox Build Bot
Community-CI: Broadcom CI
Reviewed-by: Ben Walker <benjamin.walker@intel.com>
Reviewed-by: Shuhei Matsumoto <shuhei.matsumoto.xt@hitachi.com>
Reviewed-by: Jim Harris <james.r.harris@intel.com>
Reviewed-by: Seth Howell <seth.howell@intel.com>
Reviewed-by: Jacek Kalwas <jacek.kalwas@intel.com>
This commit is contained in:
Alexey Marchuk 2020-04-22 13:06:09 +03:00 committed by Tomasz Zawadzki
parent b4a9d7d318
commit 63c8cea783
6 changed files with 29 additions and 3 deletions

View File

@ -62,9 +62,16 @@ struct spdk_rdma_qp *spdk_rdma_qp_create(struct rdma_cm_id *cm_id,
struct spdk_rdma_qp_init_attr *qp_attr);
/**
* Destory RDMA provider specific qpair
* Destroy RDMA provider specific qpair
* \param spdk_rdma_qp Pointer to qpair to be destroyed
*/
void spdk_rdma_qp_destroy(struct spdk_rdma_qp *spdk_rdma_qp);
/**
* Disconnect a connection and transition assoiciated qpair to error state.
* Generates RDMA_CM_EVENT_DISCONNECTED on both connection sides
* \param spdk_rdma_qp Pointer to qpair to be destroyed
*/
int spdk_rdma_qp_disconnect(struct spdk_rdma_qp *spdk_rdma_qp);
#endif /* SPDK_RDMA_H */

View File

@ -1672,7 +1672,7 @@ nvme_rdma_ctrlr_disconnect_qpair(struct spdk_nvme_ctrlr *ctrlr, struct spdk_nvme
}
if (rqpair->cm_id) {
rdma_disconnect(rqpair->cm_id);
spdk_rdma_qp_disconnect(rqpair->rdma_qp);
if (rctrlr != NULL) {
if (nvme_rdma_process_event(rqpair, rctrlr->cm_channel, RDMA_CM_EVENT_DISCONNECTED)) {
SPDK_DEBUGLOG(SPDK_LOG_NVME, "Target did not respond to qpair disconnect.\n");

View File

@ -3579,7 +3579,7 @@ nvmf_rdma_close_qpair(struct spdk_nvmf_qpair *qpair)
}
if (rqpair->cm_id) {
rdma_disconnect(rqpair->cm_id);
spdk_rdma_qp_disconnect(rqpair->rdma_qp);
}
rqpair->destruct_poller = SPDK_POLLER_REGISTER(nvmf_rdma_destroy_defunct_qpair, (void *)rqpair,

View File

@ -85,3 +85,20 @@ spdk_rdma_qp_destroy(struct spdk_rdma_qp *spdk_rdma_qp)
free(spdk_rdma_qp);
}
int
spdk_rdma_qp_disconnect(struct spdk_rdma_qp *spdk_rdma_qp)
{
int rc = 0;
assert(spdk_rdma_qp != NULL);
if (spdk_rdma_qp->cm_id) {
rc = rdma_disconnect(spdk_rdma_qp->cm_id);
if (rc) {
SPDK_ERRLOG("rdma_disconnect failed, errno %s (%d)\n", spdk_strerror(errno), errno);
}
}
return rc;
}

View File

@ -4,6 +4,7 @@
# Public functions
spdk_rdma_qp_create;
spdk_rdma_qp_destroy;
spdk_rdma_qp_disconnect;
local: *;
};

View File

@ -39,3 +39,4 @@
DEFINE_STUB(spdk_rdma_qp_create, struct spdk_rdma_qp *, (struct rdma_cm_id *cm_id,
struct spdk_rdma_qp_init_attr *qp_attr), NULL);
DEFINE_STUB_V(spdk_rdma_qp_destroy, (struct spdk_rdma_qp *spdk_rdma_qp));
DEFINE_STUB(spdk_rdma_qp_disconnect, int, (struct spdk_rdma_qp *spdk_rdma_qp), 0);