git: 02ddb305cc6d - main - nvmf: Refactor nvmf_add_namespaces to be more generic

From: John Baldwin <jhb_at_FreeBSD.org>
Date: Wed, 05 Jun 2024 20:03:59 UTC
The branch main has been updated by jhb:

URL: https://cgit.FreeBSD.org/src/commit/?id=02ddb305cc6d7fc3964e33985ae89501b99bb05b

commit 02ddb305cc6d7fc3964e33985ae89501b99bb05b
Author:     John Baldwin <jhb@FreeBSD.org>
AuthorDate: 2024-06-05 19:51:56 +0000
Commit:     John Baldwin <jhb@FreeBSD.org>
CommitDate: 2024-06-05 19:51:56 +0000

    nvmf: Refactor nvmf_add_namespaces to be more generic
    
    Rename to nvmf_scan_active_namespaces and accept an additional
    callback function and callback argument.  The callback is invoked on
    each active namespace enumerated by the active namespace list from the
    IDENTIFY command.
    
    Reviewed by:    imp
    Sponsored by:   Chelsio Communications
    Differential Revision:  https://reviews.freebsd.org/D45458
---
 sys/dev/nvmf/host/nvmf.c | 74 ++++++++++++++++++++++++++++++------------------
 1 file changed, 47 insertions(+), 27 deletions(-)

diff --git a/sys/dev/nvmf/host/nvmf.c b/sys/dev/nvmf/host/nvmf.c
index e43d438aaa8c..df07d70b6c86 100644
--- a/sys/dev/nvmf/host/nvmf.c
+++ b/sys/dev/nvmf/host/nvmf.c
@@ -295,9 +295,13 @@ nvmf_establish_connection(struct nvmf_softc *sc, struct nvmf_ivars *ivars)
 	return (0);
 }
 
+typedef bool nvmf_scan_active_ns_cb(struct nvmf_softc *, uint32_t,
+    const struct nvme_namespace_data *, void *);
+
 static bool
-nvmf_scan_nslist(struct nvmf_softc *sc, struct nvme_ns_list *nslist,
-    struct nvme_namespace_data *data, uint32_t *nsidp)
+nvmf_scan_active_nslist(struct nvmf_softc *sc, struct nvme_ns_list *nslist,
+    struct nvme_namespace_data *data, uint32_t *nsidp,
+    nvmf_scan_active_ns_cb *cb, void *cb_arg)
 {
 	struct nvmf_completion_status status;
 	uint32_t nsid;
@@ -333,13 +337,6 @@ nvmf_scan_nslist(struct nvmf_softc *sc, struct nvme_ns_list *nslist,
 			return (true);
 		}
 
-		if (sc->ns[nsid - 1] != NULL) {
-			device_printf(sc->dev,
-			    "duplicate namespace %u in active namespace list\n",
-			    nsid);
-			return (false);
-		}
-
 		nvmf_status_init(&status);
 		nvmf_status_wait_io(&status);
 		if (!nvmf_cmd_identify_namespace(sc, nsid, data, nvmf_complete,
@@ -365,21 +362,9 @@ nvmf_scan_nslist(struct nvmf_softc *sc, struct nvme_ns_list *nslist,
 			return (false);
 		}
 
-		/*
-		 * As in nvme_ns_construct, a size of zero indicates an
-		 * invalid namespace.
-		 */
 		nvme_namespace_data_swapbytes(data);
-		if (data->nsze == 0) {
-			device_printf(sc->dev,
-			    "ignoring active namespace %u with zero size\n",
-			    nsid);
-			continue;
-		}
-
-		sc->ns[nsid - 1] = nvmf_init_ns(sc, nsid, data);
-
-		nvmf_sim_rescan_ns(sc, nsid);
+		if (!cb(sc, nsid, data, cb_arg))
+			return (false);
 	}
 
 	MPASS(nsid == nslist->ns[nitems(nslist->ns) - 1] && nsid != 0);
@@ -392,22 +377,22 @@ nvmf_scan_nslist(struct nvmf_softc *sc, struct nvme_ns_list *nslist,
 }
 
 static bool
-nvmf_add_namespaces(struct nvmf_softc *sc)
+nvmf_scan_active_namespaces(struct nvmf_softc *sc, nvmf_scan_active_ns_cb *cb,
+    void *cb_arg)
 {
 	struct nvme_namespace_data *data;
 	struct nvme_ns_list *nslist;
 	uint32_t nsid;
 	bool retval;
 
-	sc->ns = mallocarray(sc->cdata->nn, sizeof(*sc->ns), M_NVMF,
-	    M_WAITOK | M_ZERO);
 	nslist = malloc(sizeof(*nslist), M_NVMF, M_WAITOK);
 	data = malloc(sizeof(*data), M_NVMF, M_WAITOK);
 
 	nsid = 0;
 	retval = true;
 	for (;;) {
-		if (!nvmf_scan_nslist(sc, nslist, data, &nsid)) {
+		if (!nvmf_scan_active_nslist(sc, nslist, data, &nsid, cb,
+		    cb_arg)) {
 			retval = false;
 			break;
 		}
@@ -420,6 +405,41 @@ nvmf_add_namespaces(struct nvmf_softc *sc)
 	return (retval);
 }
 
+static bool
+nvmf_add_ns(struct nvmf_softc *sc, uint32_t nsid,
+    const struct nvme_namespace_data *data, void *arg __unused)
+{
+	if (sc->ns[nsid - 1] != NULL) {
+		device_printf(sc->dev,
+		    "duplicate namespace %u in active namespace list\n",
+		    nsid);
+		return (false);
+	}
+
+	/*
+	 * As in nvme_ns_construct, a size of zero indicates an
+	 * invalid namespace.
+	 */
+	if (data->nsze == 0) {
+		device_printf(sc->dev,
+		    "ignoring active namespace %u with zero size\n", nsid);
+		return (true);
+	}
+
+	sc->ns[nsid - 1] = nvmf_init_ns(sc, nsid, data);
+
+	nvmf_sim_rescan_ns(sc, nsid);
+	return (true);
+}
+
+static bool
+nvmf_add_namespaces(struct nvmf_softc *sc)
+{
+	sc->ns = mallocarray(sc->cdata->nn, sizeof(*sc->ns), M_NVMF,
+	    M_WAITOK | M_ZERO);
+	return (nvmf_scan_active_namespaces(sc, nvmf_add_ns, NULL));
+}
+
 static int
 nvmf_attach(device_t dev)
 {