File 0012-Parse-dhchap_host_key-on-controller-level.patch of Package libnvme.27116

From: Hannes Reinecke <hare@suse.de>
Date: Thu, 25 Aug 2022 10:27:02 +0200
Subject: Parse dhchap_host_key on controller level
Git-commit: 6614a55722f501ceabe7f1892479b8b8c7239acb
References: bsc#1201501 bsc#1201700

The json config schema declares an 'dhchap_key' element representing
the dhchap host key on the controller level, but the implementation
was missing. Add the missing parsing elements and ensure to pick the
correct one (either host or controller setting) when creating the
nvme connect string.

Signed-off-by: Hannes Reinecke <hare@suse.de>
Acked-by: Daniel Wagner <dwagner@suse.de>
---
 libnvme/nvme.i     |    5 +++++
 src/nvme/fabrics.c |   12 ++++++++++--
 src/nvme/json.c    |   11 +++++++++++
 src/nvme/private.h |    1 +
 src/nvme/tree.c    |   25 +++++++++++++++++++++++++
 src/nvme/tree.h    |   15 +++++++++++++++
 6 files changed, 67 insertions(+), 2 deletions(-)

--- a/libnvme/nvme.i
+++ b/libnvme/nvme.i
@@ -314,6 +314,7 @@ struct nvme_ctrl {
   %immutable subsysnqn;
   %immutable traddr;
   %immutable trsvcid;
+  %immutable dhchap_host_key;
   %immutable dhchap_key;
   %immutable cntrltype;
   %immutable dctype;
@@ -333,6 +334,7 @@ struct nvme_ctrl {
   char *traddr;
   char *trsvcid;
   %extend {
+    char *dhchap_host_key:
     char *dhchap_key;
   }
   char *cntrltype;
@@ -670,6 +672,9 @@ struct nvme_ns {
   const char *nvme_ctrl_dhchap_key_get(struct nvme_ctrl *c) {
     return nvme_ctrl_get_dhchap_key(c);
   }
+  const char *nvme_ctrl_dhchap_host_key_get(struct nvme_ctrl *c) {
+    return nvme_ctrl_get_dhchap_host_key(c);
+  }
 %};
 
 %extend nvme_ns {
--- a/src/nvme/fabrics.c
+++ b/src/nvme/fabrics.c
@@ -446,6 +446,8 @@ static int build_options(nvme_host_t h,
 	hostnqn = nvme_host_get_hostnqn(h);
 	hostid = nvme_host_get_hostid(h);
 	hostkey = nvme_host_get_dhchap_key(h);
+	if (!hostkey)
+		hostkey = nvme_ctrl_get_dhchap_host_key(c);
 	ctrlkey = nvme_ctrl_get_dhchap_key(c);
 	if (add_argument(argstr, "transport", transport) ||
 	    add_argument(argstr, "traddr",
@@ -593,14 +595,20 @@ int nvmf_add_ctrl(nvme_host_t h, nvme_ct
 					nvme_ctrl_get_trsvcid(c),
 					NULL);
 		if (fc) {
+			const char *key;
+
 			cfg = merge_config(c, nvme_ctrl_get_config(fc));
 			/*
 			 * An authentication key might already been set
 			 * in @cfg, so ensure to update @c with the correct
 			 * controller key.
 			 */
-			if (fc->dhchap_ctrl_key)
-				nvme_ctrl_set_dhchap_key(c, fc->dhchap_ctrl_key);
+			key = nvme_ctrl_get_dhchap_host_key(fc);
+			if (key)
+				nvme_ctrl_set_dhchap_host_key(c, key);
+			key = nvme_ctrl_get_dhchap_key(fc);
+			if (key)
+				nvme_ctrl_set_dhchap_key(c, key);
 		}
 
 	}
--- a/src/nvme/json.c
+++ b/src/nvme/json.c
@@ -95,6 +95,9 @@ static void json_parse_port(nvme_subsyst
 	if (!c)
 		return;
 	json_update_attributes(c, port_obj);
+	attr_obj = json_object_object_get(port_obj, "dhchap_key");
+	if (attr_obj)
+		nvme_ctrl_set_dhchap_host_key(c, json_object_get_string(attr_obj));
 	attr_obj = json_object_object_get(port_obj, "dhchap_ctrl_key");
 	if (attr_obj)
 		nvme_ctrl_set_dhchap_key(c, json_object_get_string(attr_obj));
@@ -222,6 +225,10 @@ static void json_update_port(struct json
 	if (value)
 		json_object_object_add(port_obj, "trsvcid",
 				       json_object_new_string(value));
+	value = nvme_ctrl_get_dhchap_host_key(c);
+	if (value)
+		json_object_object_add(port_obj, "dhchap_key",
+				       json_object_new_string(value));
 	value = nvme_ctrl_get_dhchap_key(c);
 	if (value)
 		json_object_object_add(port_obj, "dhchap_ctrl_key",
@@ -364,6 +371,10 @@ static void json_dump_ctrl(struct json_o
 	if (value)
 		json_object_object_add(ctrl_obj, "trsvcid",
 				       json_object_new_string(value));
+	value = nvme_ctrl_get_dhchap_host_key(c);
+	if (value)
+		json_object_object_add(ctrl_obj, "dhchap_key",
+				       json_object_new_string(value));
 	value = nvme_ctrl_get_dhchap_key(c);
 	if (value)
 		json_object_object_add(ctrl_obj, "dhchap_ctrl_key",
--- a/src/nvme/private.h
+++ b/src/nvme/private.h
@@ -79,6 +79,7 @@ struct nvme_ctrl {
 	char *subsysnqn;
 	char *traddr;
 	char *trsvcid;
+	char *dhchap_key;
 	char *dhchap_ctrl_key;
 	char *cntrltype;
 	char *dctype;
--- a/src/nvme/tree.c
+++ b/src/nvme/tree.c
@@ -807,6 +807,21 @@ struct nvme_fabrics_config *nvme_ctrl_ge
 	return &c->cfg;
 }
 
+const char *nvme_ctrl_get_dhchap_host_key(nvme_ctrl_t c)
+{
+	return c->dhchap_key;
+}
+
+void nvme_ctrl_set_dhchap_host_key(nvme_ctrl_t c, const char *key)
+{
+	if (c->dhchap_key) {
+		free(c->dhchap_key);
+		c->dhchap_key = NULL;
+	}
+	if (key)
+		c->dhchap_key = strdup(key);
+}
+
 const char *nvme_ctrl_get_dhchap_key(nvme_ctrl_t c)
 {
 	return c->dhchap_ctrl_key;
@@ -894,6 +909,7 @@ void nvme_deconfigure_ctrl(nvme_ctrl_t c
 	FREE_CTRL_ATTR(c->queue_count);
 	FREE_CTRL_ATTR(c->serial);
 	FREE_CTRL_ATTR(c->sqsize);
+	FREE_CTRL_ATTR(c->dhchap_key);
 	FREE_CTRL_ATTR(c->dhchap_ctrl_key);
 	FREE_CTRL_ATTR(c->address);
 	FREE_CTRL_ATTR(c->dctype);
@@ -1135,6 +1151,7 @@ static int nvme_configure_ctrl(nvme_root
 			       const char *name)
 {
 	DIR *d;
+	char *host_key;
 
 	d = opendir(path);
 	if (!d) {
@@ -1155,6 +1172,14 @@ static int nvme_configure_ctrl(nvme_root
 	c->queue_count = nvme_get_ctrl_attr(c, "queue_count");
 	c->serial = nvme_get_ctrl_attr(c, "serial");
 	c->sqsize = nvme_get_ctrl_attr(c, "sqsize");
+	host_key = nvme_get_ctrl_attr(c, "dhchap_secret");
+	if (host_key && (!strcmp(c->s->h->dhchap_key, host_key) ||
+			 !strcmp("none", host_key))) {
+		free(host_key);
+		host_key = NULL;
+	}
+	if (host_key)
+		c->dhchap_key = host_key;
 	c->dhchap_ctrl_key = nvme_get_ctrl_attr(c, "dhchap_ctrl_secret");
 	if (c->dhchap_ctrl_key && !strcmp(c->dhchap_ctrl_key, "none")) {
 		free(c->dhchap_ctrl_key);
--- a/src/nvme/tree.h
+++ b/src/nvme/tree.h
@@ -876,6 +876,21 @@ const char *nvme_ctrl_get_host_traddr(nv
 const char *nvme_ctrl_get_host_iface(nvme_ctrl_t c);
 
 /**
+ * nvme_ctrl_get_dhchap_host_key() - Return host key
+ * @c:	Controller to be checked
+ *
+ * Return: DH-HMAC-CHAP host key or NULL if not set
+ */
+const char *nvme_ctrl_get_dhchap_host_key(nvme_ctrl_t c);
+
+/**
+ * nvme_ctrl_set_dhchap_host_key() - Set host key
+ * @c:		Host for which the key should be set
+ * @key:	DH-HMAC-CHAP Key to set or NULL to clear existing key
+ */
+void nvme_ctrl_set_dhchap_host_key(nvme_ctrl_t c, const char *key);
+
+/**
  * nvme_ctrl_get_dhchap_key() - Return controller key
  * @c:	Controller for which the key should be set
  *
openSUSE Build Service is sponsored by