All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH v2 0/4] Add duplicate_connect option for ctlr connect requests
@ 2017-10-20 23:17 James Smart
  2017-10-20 23:17 ` [PATCH v2 1/4] nvme: add duplicate_connect option James Smart
                   ` (3 more replies)
  0 siblings, 4 replies; 10+ messages in thread
From: James Smart @ 2017-10-20 23:17 UTC (permalink / raw)


This patch adds a duplicate_connect option option to those supported by
fabric connection requests. When set to true (1), duplicate connections
are allowed. When set to false (0), duplicate connections are rejected.

The option is set in the fabrics layer and acted upon by each transport.

This patch set came about as of this prior patch review:
http://lists.infradead.org/pipermail/linux-nvme/2017-September/012783.html

---
v2:
 split compare for hostnqn, hostid, subnqn to a helper function
 duplicate_connection converted to a boolean option (presence means true)

James Smart (4):
  nvme: add duplicate_connect option
  nvme: add helper to compare options to controller
  nvme_fc: add support for duplicate_connect option
  RFC: nvme-rdma: add support for duplicate_connect option

 drivers/nvme/host/fabrics.c |  7 +++-
 drivers/nvme/host/fabrics.h | 14 ++++++++
 drivers/nvme/host/fc.c      | 33 ++++++++++++++++++
 drivers/nvme/host/rdma.c    | 82 +++++++++++++++++++++++++++++++++++++++++++++
 4 files changed, 135 insertions(+), 1 deletion(-)

-- 
2.13.1

^ permalink raw reply	[flat|nested] 10+ messages in thread

* [PATCH v2 1/4] nvme: add duplicate_connect option
  2017-10-20 23:17 [PATCH v2 0/4] Add duplicate_connect option for ctlr connect requests James Smart
@ 2017-10-20 23:17 ` James Smart
  2017-10-23  8:21   ` Johannes Thumshirn
  2017-10-20 23:17 ` [PATCH v2 2/4] nvme: add helper to compare options to controller James Smart
                   ` (2 subsequent siblings)
  3 siblings, 1 reply; 10+ messages in thread
From: James Smart @ 2017-10-20 23:17 UTC (permalink / raw)


Add the "duplicate_connect" boolean option (presence means true).
Default is false.

When false, the transport should validate whether a new controller request
is targeted for the same host transport addressing and target transport
addressing as an existing controller. If so, the new controller request
should be rejected.

When true, the callee is explicitly requesting a duplicate controller
connection to be made and the new request should be attempted.

Signed-off-by: James Smart <james.smart at broadcom.com>

--
v2:
 duplicate_connect option converted to a boolean
---
 drivers/nvme/host/fabrics.c | 7 ++++++-
 drivers/nvme/host/fabrics.h | 2 ++
 2 files changed, 8 insertions(+), 1 deletion(-)

diff --git a/drivers/nvme/host/fabrics.c b/drivers/nvme/host/fabrics.c
index 8bca36a46924..4a83137b0268 100644
--- a/drivers/nvme/host/fabrics.c
+++ b/drivers/nvme/host/fabrics.c
@@ -548,6 +548,7 @@ static const match_table_t opt_tokens = {
 	{ NVMF_OPT_HOSTNQN,		"hostnqn=%s"		},
 	{ NVMF_OPT_HOST_TRADDR,		"host_traddr=%s"	},
 	{ NVMF_OPT_HOST_ID,		"hostid=%s"		},
+	{ NVMF_OPT_DUP_CONNECT,		"duplicate_connect"	},
 	{ NVMF_OPT_ERR,			NULL			}
 };
 
@@ -566,6 +567,7 @@ static int nvmf_parse_options(struct nvmf_ctrl_options *opts,
 	opts->nr_io_queues = num_online_cpus();
 	opts->reconnect_delay = NVMF_DEF_RECONNECT_DELAY;
 	opts->kato = NVME_DEFAULT_KATO;
+	opts->duplicate_connect = false;
 
 	options = o = kstrdup(buf, GFP_KERNEL);
 	if (!options)
@@ -742,6 +744,9 @@ static int nvmf_parse_options(struct nvmf_ctrl_options *opts,
 				goto out;
 			}
 			break;
+		case NVMF_OPT_DUP_CONNECT:
+			opts->duplicate_connect = true;
+			break;
 		default:
 			pr_warn("unknown parameter or missing value '%s' in ctrl creation request\n",
 				p);
@@ -823,7 +828,7 @@ EXPORT_SYMBOL_GPL(nvmf_free_options);
 #define NVMF_REQUIRED_OPTS	(NVMF_OPT_TRANSPORT | NVMF_OPT_NQN)
 #define NVMF_ALLOWED_OPTS	(NVMF_OPT_QUEUE_SIZE | NVMF_OPT_NR_IO_QUEUES | \
 				 NVMF_OPT_KATO | NVMF_OPT_HOSTNQN | \
-				 NVMF_OPT_HOST_ID)
+				 NVMF_OPT_HOST_ID | NVMF_OPT_DUP_CONNECT)
 
 static struct nvme_ctrl *
 nvmf_create_ctrl(struct device *dev, const char *buf, size_t count)
diff --git a/drivers/nvme/host/fabrics.h b/drivers/nvme/host/fabrics.h
index bf33663218cd..a7590cc59ba2 100644
--- a/drivers/nvme/host/fabrics.h
+++ b/drivers/nvme/host/fabrics.h
@@ -57,6 +57,7 @@ enum {
 	NVMF_OPT_HOST_TRADDR	= 1 << 10,
 	NVMF_OPT_CTRL_LOSS_TMO	= 1 << 11,
 	NVMF_OPT_HOST_ID	= 1 << 12,
+	NVMF_OPT_DUP_CONNECT	= 1 << 13,
 };
 
 /**
@@ -96,6 +97,7 @@ struct nvmf_ctrl_options {
 	unsigned int		nr_io_queues;
 	unsigned int		reconnect_delay;
 	bool			discovery_nqn;
+	bool			duplicate_connect;
 	unsigned int		kato;
 	struct nvmf_host	*host;
 	int			max_reconnects;
-- 
2.13.1

^ permalink raw reply related	[flat|nested] 10+ messages in thread

* [PATCH v2 2/4] nvme: add helper to compare options to controller
  2017-10-20 23:17 [PATCH v2 0/4] Add duplicate_connect option for ctlr connect requests James Smart
  2017-10-20 23:17 ` [PATCH v2 1/4] nvme: add duplicate_connect option James Smart
@ 2017-10-20 23:17 ` James Smart
  2017-10-23  8:31   ` Johannes Thumshirn
  2017-10-20 23:17 ` [PATCH v2 3/4] nvme_fc: add support for duplicate_connect option James Smart
  2017-10-20 23:17 ` [PATCH v2 4/4] nvme-rdma: " James Smart
  3 siblings, 1 reply; 10+ messages in thread
From: James Smart @ 2017-10-20 23:17 UTC (permalink / raw)


Adds a helper function that compares the host and subsytem
specified in a connect options list vs a controller.

Signed-off-by: James Smart <james.smart at broadcom.com>
---
 drivers/nvme/host/fabrics.h | 12 ++++++++++++
 1 file changed, 12 insertions(+)

diff --git a/drivers/nvme/host/fabrics.h b/drivers/nvme/host/fabrics.h
index a7590cc59ba2..42232e731f19 100644
--- a/drivers/nvme/host/fabrics.h
+++ b/drivers/nvme/host/fabrics.h
@@ -133,6 +133,18 @@ struct nvmf_transport_ops {
 					struct nvmf_ctrl_options *opts);
 };
 
+static inline bool
+nvmf_ctlr_matches_baseopts(struct nvme_ctrl *ctrl,
+			struct nvmf_ctrl_options *opts)
+{
+	if (strcmp(opts->subsysnqn, ctrl->opts->subsysnqn) ||
+	    strcmp(opts->host->nqn, ctrl->opts->host->nqn) ||
+	    memcmp(&opts->host->id, &ctrl->opts->host->id, sizeof(uuid_t)))
+		return false;
+
+	return true;
+}
+
 int nvmf_reg_read32(struct nvme_ctrl *ctrl, u32 off, u32 *val);
 int nvmf_reg_read64(struct nvme_ctrl *ctrl, u32 off, u64 *val);
 int nvmf_reg_write32(struct nvme_ctrl *ctrl, u32 off, u32 val);
-- 
2.13.1

^ permalink raw reply related	[flat|nested] 10+ messages in thread

* [PATCH v2 3/4] nvme_fc: add support for duplicate_connect option
  2017-10-20 23:17 [PATCH v2 0/4] Add duplicate_connect option for ctlr connect requests James Smart
  2017-10-20 23:17 ` [PATCH v2 1/4] nvme: add duplicate_connect option James Smart
  2017-10-20 23:17 ` [PATCH v2 2/4] nvme: add helper to compare options to controller James Smart
@ 2017-10-20 23:17 ` James Smart
  2017-10-23  9:27   ` Johannes Thumshirn
  2017-10-23  9:28   ` Johannes Thumshirn
  2017-10-20 23:17 ` [PATCH v2 4/4] nvme-rdma: " James Smart
  3 siblings, 2 replies; 10+ messages in thread
From: James Smart @ 2017-10-20 23:17 UTC (permalink / raw)


Adds support for the duplicate_connect option. When set to true,
checks whether there's an existing controller via the same host port
and target port for the same host (hostnqn, hostid) to the same
subsystem. Fails the connection request if an existing controller.

Signed-off-by: James Smart <james.smart at broadcom.com>
---
 drivers/nvme/host/fc.c | 33 +++++++++++++++++++++++++++++++++
 1 file changed, 33 insertions(+)

diff --git a/drivers/nvme/host/fc.c b/drivers/nvme/host/fc.c
index 0d0e898912ad..90dd01811dfb 100644
--- a/drivers/nvme/host/fc.c
+++ b/drivers/nvme/host/fc.c
@@ -2785,6 +2785,33 @@ static const struct blk_mq_ops nvme_fc_admin_mq_ops = {
 };
 
 
+/*
+ * Fails a controller request if it matches an existing controller
+ * (association) with the same tuple:
+ * <Host NQN, Host ID, local FC port, remote FC port, SUBSYS NQN>
+ *
+ * The ports don't need to be compared as they are intrinsically
+ * already matched by the port pointers supplied.
+ */
+static bool
+nvme_fc_existing_controller(struct nvme_fc_rport *rport,
+		struct nvmf_ctrl_options *opts)
+{
+	struct nvme_fc_ctrl *ctrl;
+	unsigned long flags;
+	bool found = false;
+
+	spin_lock_irqsave(&rport->lock, flags);
+	list_for_each_entry(ctrl, &rport->ctrl_list, ctrl_list) {
+		found = nvmf_ctlr_matches_baseopts(&ctrl->ctrl, opts);
+		if (found)
+			break;
+	}
+	spin_unlock_irqrestore(&rport->lock, flags);
+
+	return found;
+}
+
 static struct nvme_ctrl *
 nvme_fc_init_ctrl(struct device *dev, struct nvmf_ctrl_options *opts,
 	struct nvme_fc_lport *lport, struct nvme_fc_rport *rport)
@@ -2799,6 +2826,12 @@ nvme_fc_init_ctrl(struct device *dev, struct nvmf_ctrl_options *opts,
 		goto out_fail;
 	}
 
+	if (!opts->duplicate_connect &&
+	    nvme_fc_existing_controller(rport, opts)) {
+		ret = -EALREADY;
+		goto out_fail;
+	}
+
 	ctrl = kzalloc(sizeof(*ctrl), GFP_KERNEL);
 	if (!ctrl) {
 		ret = -ENOMEM;
-- 
2.13.1

^ permalink raw reply related	[flat|nested] 10+ messages in thread

* [PATCH v2 4/4] nvme-rdma: add support for duplicate_connect option
  2017-10-20 23:17 [PATCH v2 0/4] Add duplicate_connect option for ctlr connect requests James Smart
                   ` (2 preceding siblings ...)
  2017-10-20 23:17 ` [PATCH v2 3/4] nvme_fc: add support for duplicate_connect option James Smart
@ 2017-10-20 23:17 ` James Smart
  2017-10-23  9:30   ` Johannes Thumshirn
  3 siblings, 1 reply; 10+ messages in thread
From: James Smart @ 2017-10-20 23:17 UTC (permalink / raw)


Adds support for the duplicate_connect option. When set to true,
checks whether there's an existing controller via the same target
address (traddr), target port (trsvcid), and if specified, host
address (host_traddr). Fails the connection request if there is
an existing controller.

Signed-off-by: James Smart <james.smart at broadcom.com>
---
 drivers/nvme/host/rdma.c | 82 ++++++++++++++++++++++++++++++++++++++++++++++++
 1 file changed, 82 insertions(+)

diff --git a/drivers/nvme/host/rdma.c b/drivers/nvme/host/rdma.c
index a5577e06a620..523881444fee 100644
--- a/drivers/nvme/host/rdma.c
+++ b/drivers/nvme/host/rdma.c
@@ -1848,6 +1848,83 @@ static const struct nvme_ctrl_ops nvme_rdma_ctrl_ops = {
 	.reinit_request		= nvme_rdma_reinit_request,
 };
 
+static inline bool
+__nvme_rdma_options_match(struct nvme_rdma_ctrl *ctrl,
+	struct nvmf_ctrl_options *opts)
+{
+	char *stdport = __stringify(NVME_RDMA_IP_PORT);
+
+
+	if (!nvmf_ctlr_matches_baseopts(&ctrl->ctrl, opts) ||
+	    strcmp(opts->traddr, ctrl->ctrl.opts->traddr))
+		return false;
+
+	if (opts->mask & NVMF_OPT_TRSVCID &&
+	    ctrl->ctrl.opts->mask & NVMF_OPT_TRSVCID) {
+		if (strcmp(opts->trsvcid, ctrl->ctrl.opts->trsvcid))
+			return false;
+	} else if (opts->mask & NVMF_OPT_TRSVCID) {
+		if (strcmp(opts->trsvcid, stdport))
+			return false;
+	} else if (ctrl->ctrl.opts->mask & NVMF_OPT_TRSVCID) {
+		if (strcmp(stdport, ctrl->ctrl.opts->trsvcid))
+			return false;
+	}
+	/* else, it's a match as both have stdport. Fall to next checks */
+
+	/*
+	 * checking the local address is rough. In most cases, one
+	 * is not specified and the host port is selected by the stack.
+	 *
+	 * Assume no match if:
+	 *  local address is specified and address is not the same
+	 *  local address is not specified but remote is, or vice versa
+	 *    (admin using specific host_traddr when it matters).
+	 */
+	if (opts->mask & NVMF_OPT_HOST_TRADDR &&
+	    ctrl->ctrl.opts->mask & NVMF_OPT_HOST_TRADDR) {
+		if (strcmp(opts->host_traddr, ctrl->ctrl.opts->host_traddr))
+			return false;
+	} else if (opts->mask & NVMF_OPT_HOST_TRADDR ||
+		   ctrl->ctrl.opts->mask & NVMF_OPT_HOST_TRADDR)
+		return false;
+	/*
+	 * if neither controller had an host port specified, assume it's
+	 * a match as everything else matched.
+	 */
+
+	return true;
+}
+
+/*
+ * Fails a connection request if it matches an existing controller
+ * (association) with the same tuple:
+ * <Host NQN, Host ID, local address, remote address, remote port, SUBSYS NQN>
+ *
+ * if local address is not specified in the request, it will match an
+ * existing controller with all the other parameters the same and no
+ * local port address specified as well.
+ *
+ * The ports don't need to be compared as they are intrinsically
+ * already matched by the port pointers supplied.
+ */
+static bool
+nvme_rdma_existing_controller(struct nvmf_ctrl_options *opts)
+{
+	struct nvme_rdma_ctrl *ctrl;
+	bool found = false;
+
+	mutex_lock(&nvme_rdma_ctrl_mutex);
+	list_for_each_entry(ctrl, &nvme_rdma_ctrl_list, list) {
+		found = __nvme_rdma_options_match(ctrl, opts);
+		if (found)
+			break;
+	}
+	mutex_unlock(&nvme_rdma_ctrl_mutex);
+
+	return found;
+}
+
 static struct nvme_ctrl *nvme_rdma_create_ctrl(struct device *dev,
 		struct nvmf_ctrl_options *opts)
 {
@@ -1884,6 +1961,11 @@ static struct nvme_ctrl *nvme_rdma_create_ctrl(struct device *dev,
 		}
 	}
 
+	if (!opts->duplicate_connect && nvme_rdma_existing_controller(opts)) {
+		ret = -EALREADY;
+		goto out_free_ctrl;
+	}
+
 	ret = nvme_init_ctrl(&ctrl->ctrl, dev, &nvme_rdma_ctrl_ops,
 				0 /* no quirks, we're perfect! */);
 	if (ret)
-- 
2.13.1

^ permalink raw reply related	[flat|nested] 10+ messages in thread

* [PATCH v2 1/4] nvme: add duplicate_connect option
  2017-10-20 23:17 ` [PATCH v2 1/4] nvme: add duplicate_connect option James Smart
@ 2017-10-23  8:21   ` Johannes Thumshirn
  0 siblings, 0 replies; 10+ messages in thread
From: Johannes Thumshirn @ 2017-10-23  8:21 UTC (permalink / raw)


Looks good,
Reviewed-by: Johannes Thumshirn <jthumshirn at suse.de>
-- 
Johannes Thumshirn                                          Storage
jthumshirn at suse.de                                +49 911 74053 689
SUSE LINUX GmbH, Maxfeldstr. 5, 90409 N?rnberg
GF: Felix Imend?rffer, Jane Smithard, Graham Norton
HRB 21284 (AG N?rnberg)
Key fingerprint = EC38 9CAB C2C4 F25D 8600 D0D0 0393 969D 2D76 0850

^ permalink raw reply	[flat|nested] 10+ messages in thread

* [PATCH v2 2/4] nvme: add helper to compare options to controller
  2017-10-20 23:17 ` [PATCH v2 2/4] nvme: add helper to compare options to controller James Smart
@ 2017-10-23  8:31   ` Johannes Thumshirn
  0 siblings, 0 replies; 10+ messages in thread
From: Johannes Thumshirn @ 2017-10-23  8:31 UTC (permalink / raw)


Looks good,
Reviewed-by: Johannes Thumshirn <jthumshirn at suse.de>
-- 
Johannes Thumshirn                                          Storage
jthumshirn at suse.de                                +49 911 74053 689
SUSE LINUX GmbH, Maxfeldstr. 5, 90409 N?rnberg
GF: Felix Imend?rffer, Jane Smithard, Graham Norton
HRB 21284 (AG N?rnberg)
Key fingerprint = EC38 9CAB C2C4 F25D 8600 D0D0 0393 969D 2D76 0850

^ permalink raw reply	[flat|nested] 10+ messages in thread

* [PATCH v2 3/4] nvme_fc: add support for duplicate_connect option
  2017-10-20 23:17 ` [PATCH v2 3/4] nvme_fc: add support for duplicate_connect option James Smart
@ 2017-10-23  9:27   ` Johannes Thumshirn
  2017-10-23  9:28   ` Johannes Thumshirn
  1 sibling, 0 replies; 10+ messages in thread
From: Johannes Thumshirn @ 2017-10-23  9:27 UTC (permalink / raw)


Looks good,
Reviewed-by: Johannes Thumshirn <jthumshirn at suse.de>
-- 
Johannes Thumshirn                                          Storage
jthumshirn at suse.de                                +49 911 74053 689
SUSE LINUX GmbH, Maxfeldstr. 5, 90409 N?rnberg
GF: Felix Imend?rffer, Jane Smithard, Graham Norton
HRB 21284 (AG N?rnberg)
Key fingerprint = EC38 9CAB C2C4 F25D 8600 D0D0 0393 969D 2D76 0850

^ permalink raw reply	[flat|nested] 10+ messages in thread

* [PATCH v2 3/4] nvme_fc: add support for duplicate_connect option
  2017-10-20 23:17 ` [PATCH v2 3/4] nvme_fc: add support for duplicate_connect option James Smart
  2017-10-23  9:27   ` Johannes Thumshirn
@ 2017-10-23  9:28   ` Johannes Thumshirn
  1 sibling, 0 replies; 10+ messages in thread
From: Johannes Thumshirn @ 2017-10-23  9:28 UTC (permalink / raw)


Looks good,
Reviewed-by: Johannes Thumshirn <jthumshirn at suse.de>
-- 
Johannes Thumshirn                                          Storage
jthumshirn at suse.de                                +49 911 74053 689
SUSE LINUX GmbH, Maxfeldstr. 5, 90409 N?rnberg
GF: Felix Imend?rffer, Jane Smithard, Graham Norton
HRB 21284 (AG N?rnberg)
Key fingerprint = EC38 9CAB C2C4 F25D 8600 D0D0 0393 969D 2D76 0850

^ permalink raw reply	[flat|nested] 10+ messages in thread

* [PATCH v2 4/4] nvme-rdma: add support for duplicate_connect option
  2017-10-20 23:17 ` [PATCH v2 4/4] nvme-rdma: " James Smart
@ 2017-10-23  9:30   ` Johannes Thumshirn
  0 siblings, 0 replies; 10+ messages in thread
From: Johannes Thumshirn @ 2017-10-23  9:30 UTC (permalink / raw)


Looks good,
Reviewed-by: Johannes Thumshirn <jthumshirn at suse.de>
-- 
Johannes Thumshirn                                          Storage
jthumshirn at suse.de                                +49 911 74053 689
SUSE LINUX GmbH, Maxfeldstr. 5, 90409 N?rnberg
GF: Felix Imend?rffer, Jane Smithard, Graham Norton
HRB 21284 (AG N?rnberg)
Key fingerprint = EC38 9CAB C2C4 F25D 8600 D0D0 0393 969D 2D76 0850

^ permalink raw reply	[flat|nested] 10+ messages in thread

end of thread, other threads:[~2017-10-23  9:30 UTC | newest]

Thread overview: 10+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2017-10-20 23:17 [PATCH v2 0/4] Add duplicate_connect option for ctlr connect requests James Smart
2017-10-20 23:17 ` [PATCH v2 1/4] nvme: add duplicate_connect option James Smart
2017-10-23  8:21   ` Johannes Thumshirn
2017-10-20 23:17 ` [PATCH v2 2/4] nvme: add helper to compare options to controller James Smart
2017-10-23  8:31   ` Johannes Thumshirn
2017-10-20 23:17 ` [PATCH v2 3/4] nvme_fc: add support for duplicate_connect option James Smart
2017-10-23  9:27   ` Johannes Thumshirn
2017-10-23  9:28   ` Johannes Thumshirn
2017-10-20 23:17 ` [PATCH v2 4/4] nvme-rdma: " James Smart
2017-10-23  9:30   ` Johannes Thumshirn

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.