Commit 71cd42e1 authored by Jacek Kalwas's avatar Jacek Kalwas Committed by Tomasz Zawadzki
Browse files

nvmf: association timer triggered on shutdown



After CC.EN transitions to ‘0’ (due to shutdown or reset), the
association between the host and controller shall be preserved for at
least 2 minutes. After this time, the association may be removed if
the controller has not been re-enabled.

Signed-off-by: default avatarJacek Kalwas <jacek.kalwas@intel.com>
Signed-off-by: default avatarDarek Stojaczyk <dariusz.stojaczyk@intel.com>
Change-Id: I4734600067fd4b7306b46f1325fdd5031e81c079
Reviewed-on: https://review.spdk.io/gerrit/c/spdk/spdk/+/2984


Community-CI: Mellanox Build Bot
Tested-by: default avatarSPDK CI Jenkins <sys_sgci@intel.com>
Reviewed-by: default avatarBen Walker <benjamin.walker@intel.com>
Reviewed-by: default avatarChangpeng Liu <changpeng.liu@intel.com>
parent b70fc69b
Loading
Loading
Loading
Loading
+1 −0
Original line number Diff line number Diff line
@@ -86,6 +86,7 @@ struct spdk_nvmf_transport_opts {
	uint32_t	sock_priority;
	int		acceptor_backlog;
	uint32_t	abort_timeout_sec;
	uint32_t	association_timeout;
};

struct spdk_nvmf_poll_group_stat {
+45 −0
Original line number Diff line number Diff line
@@ -102,6 +102,23 @@ nvmf_ctrlr_stop_keep_alive_timer(struct spdk_nvmf_ctrlr *ctrlr)
	spdk_poller_unregister(&ctrlr->keep_alive_poller);
}

static void
nvmf_ctrlr_stop_association_timer(struct spdk_nvmf_ctrlr *ctrlr)
{
	if (!ctrlr) {
		SPDK_ERRLOG("Controller is NULL\n");
		assert(false);
		return;
	}

	if (ctrlr->association_timer == NULL) {
		return;
	}

	SPDK_DEBUGLOG(SPDK_LOG_NVMF, "Stop association timer\n");
	spdk_poller_unregister(&ctrlr->association_timer);
}

static void
nvmf_ctrlr_disconnect_qpairs_done(struct spdk_io_channel_iter *i, int status)
{
@@ -403,7 +420,9 @@ _nvmf_ctrlr_destruct(void *ctx)
	struct spdk_nvmf_reservation_log *log, *log_tmp;

	nvmf_ctrlr_stop_keep_alive_timer(ctrlr);
	nvmf_ctrlr_stop_association_timer(ctrlr);
	spdk_bit_array_free(&ctrlr->qpair_mask);

	TAILQ_FOREACH_SAFE(log, &ctrlr->log_head, link, log_tmp) {
		TAILQ_REMOVE(&ctrlr->log_head, log, link);
		free(log);
@@ -720,6 +739,25 @@ nvmf_ctrlr_cmd_connect(struct spdk_nvmf_request *req)
	return _nvmf_ctrlr_connect(req);
}

static int
nvmf_ctrlr_association_remove(void *ctx)
{
	struct spdk_nvmf_ctrlr *ctrlr = ctx;
	int rc;

	SPDK_DEBUGLOG(SPDK_LOG_NVMF, "Disconnecting host from subsystem %s due to association timeout.\n",
		      ctrlr->subsys->subnqn);

	rc = spdk_nvmf_qpair_disconnect(ctrlr->admin_qpair, NULL, NULL);
	if (rc < 0) {
		SPDK_ERRLOG("Fail to disconnect admin ctrlr qpair\n");
		assert(false);
	}

	nvmf_ctrlr_stop_association_timer(ctrlr);
	return 1;
}

static void
nvmf_ctrlr_cc_shn_done(struct spdk_io_channel_iter *i, int status)
{
@@ -731,6 +769,11 @@ nvmf_ctrlr_cc_shn_done(struct spdk_io_channel_iter *i, int status)
	}

	ctrlr->vcprop.csts.bits.shst = SPDK_NVME_SHST_COMPLETE;

	/* After CC.EN transitions to 0 (due to shutdown or reset), the association
	 * between the host and controller shall be preserved for at least 2 minutes */
	ctrlr->association_timer = SPDK_POLLER_REGISTER(nvmf_ctrlr_association_remove, ctrlr,
				   ctrlr->admin_qpair->transport->opts.association_timeout);
}

static void
@@ -792,6 +835,8 @@ nvmf_prop_set_cc(struct spdk_nvmf_ctrlr *ctrlr, uint32_t value)
	if (diff.bits.en) {
		if (cc.bits.en) {
			SPDK_DEBUGLOG(SPDK_LOG_NVMF, "Property Set CC Enable!\n");
			nvmf_ctrlr_stop_association_timer(ctrlr);

			ctrlr->vcprop.cc.bits.en = 1;
			ctrlr->vcprop.csts.bits.rdy = 1;
		} else {
+2 −0
Original line number Diff line number Diff line
@@ -231,6 +231,8 @@ struct spdk_nvmf_ctrlr {
	uint64_t			last_keep_alive_tick;
	struct spdk_poller		*keep_alive_poller;

	struct spdk_poller		*association_timer;

	bool				dif_insert_or_strip;

	TAILQ_ENTRY(spdk_nvmf_ctrlr)	link;
+2 −0
Original line number Diff line number Diff line
@@ -44,6 +44,7 @@
#include "spdk/util.h"

#define MAX_MEMPOOL_NAME_LENGTH 40
#define NVMF_TRANSPORT_DEFAULT_ASSOCIATION_TIMEOUT 120000 /* ms */

struct nvmf_transport_ops_list_element {
	struct spdk_nvmf_transport_ops			ops;
@@ -499,6 +500,7 @@ spdk_nvmf_transport_opts_init(const char *transport_name,
		return false;
	}

	opts->association_timeout = NVMF_TRANSPORT_DEFAULT_ASSOCIATION_TIMEOUT;
	ops->opts_init(opts);
	return true;
}