From adfa9f6dc75d4c541beeb3269442552f7cbf5d7a Mon Sep 17 00:00:00 2001 From: Ziye Yang Date: Wed, 18 Apr 2018 14:16:39 +0800 Subject: [PATCH] nvmf: disconnect other connections if admin qpair disconnects. Also this patch make each io qpair recycled by its own thread. Change-Id: I386e411f5d4cee4629054e4cce8d1f4401ec49c8 Signed-off-by: Ziye Yang Reviewed-on: https://review.gerrithub.io/407743 Reviewed-by: Ben Walker Reviewed-by: Daniel Verkamp Tested-by: SPDK Automated Test System --- lib/nvmf/ctrlr.c | 49 ++++++++++++++++++++++++++++++++++++------------ 1 file changed, 37 insertions(+), 12 deletions(-) diff --git a/lib/nvmf/ctrlr.c b/lib/nvmf/ctrlr.c index 0aa8193c10..b558a75a4a 100644 --- a/lib/nvmf/ctrlr.c +++ b/lib/nvmf/ctrlr.c @@ -275,23 +275,13 @@ end: } static void -ctrlr_delete_qpair(void *ctx) +_ctrlr_destruct_check(void *ctx) { - struct spdk_nvmf_qpair *qpair = ctx; - struct spdk_nvmf_ctrlr *ctrlr = qpair->ctrlr; + struct spdk_nvmf_ctrlr *ctrlr = ctx; assert(ctrlr != NULL); assert(ctrlr->num_qpairs > 0); - /* Defer the admin qpair deletion since there are still io qpairs */ - if ((ctrlr->num_qpairs > 1) && (qpair == ctrlr->admin_qpair)) { - spdk_thread_send_msg(qpair->group->thread, ctrlr_delete_qpair, qpair); - return; - } - ctrlr->num_qpairs--; - TAILQ_REMOVE(&ctrlr->qpairs, qpair, link); - spdk_nvmf_transport_qpair_fini(qpair); - if (ctrlr->num_qpairs == 0) { assert(ctrlr->subsys != NULL); assert(ctrlr->subsys->thread != NULL); @@ -299,6 +289,41 @@ ctrlr_delete_qpair(void *ctx) } } +static void +nvmf_qpair_fini(void *ctx) +{ + struct spdk_nvmf_qpair *qpair = ctx; + struct spdk_nvmf_ctrlr *ctrlr = qpair->ctrlr; + struct spdk_thread *admin_thread = ctrlr->admin_qpair->group->thread; + + spdk_nvmf_transport_qpair_fini(qpair); + spdk_thread_send_msg(admin_thread, _ctrlr_destruct_check, ctrlr); +} + +static void +ctrlr_delete_qpair(void *ctx) +{ + struct spdk_nvmf_qpair *qpair = ctx, *_qpair, *tmp; + struct spdk_nvmf_ctrlr *ctrlr = qpair->ctrlr; + + assert(ctrlr != NULL); + + /* Delete all io qpairs if receving the admin qpair disconnect event early */ + if ((ctrlr->num_qpairs > 1) && (qpair == ctrlr->admin_qpair)) { + TAILQ_FOREACH_SAFE(_qpair, &ctrlr->qpairs, link, tmp) { + if (_qpair != qpair) { + ctrlr_delete_qpair(_qpair); + } + } + + spdk_thread_send_msg(qpair->group->thread, ctrlr_delete_qpair, qpair); + return; + } + + TAILQ_REMOVE(&ctrlr->qpairs, qpair, link); + spdk_thread_send_msg(qpair->group->thread, nvmf_qpair_fini, qpair); +} + static void _spdk_nvmf_ctrlr_add_io_qpair(void *ctx) {