nvme: cleanup namespace identifier reporting in nvme_init_ns_head
authorChristoph Hellwig <hch@lst.de>
Wed, 25 Mar 2020 13:19:37 +0000 (14:19 +0100)
committerKeith Busch <kbusch@kernel.org>
Wed, 25 Mar 2020 19:51:56 +0000 (04:51 +0900)
Lift the common namespace identifier reporting between the shared
namespace and new nshead cases into common code.  This also means
one less lock is held while doing I/O.

Signed-off-by: Christoph Hellwig <hch@lst.de>
Signed-off-by: Keith Busch <kbusch@kernel.org>
drivers/nvme/host/core.c

index 56a0dc18ed2d92fac76e0ffad5cbbe9b37a3ad30..2b0f693437a888e3118f7dae115f7ab671c31cb4 100644 (file)
@@ -3390,7 +3390,8 @@ static int __nvme_check_ids(struct nvme_subsystem *subsys,
 }
 
 static struct nvme_ns_head *nvme_alloc_ns_head(struct nvme_ctrl *ctrl,
-               unsigned nsid, struct nvme_id_ns *id)
+               unsigned nsid, struct nvme_id_ns *id,
+               struct nvme_ns_ids *ids)
 {
        struct nvme_ns_head *head;
        size_t size = sizeof(*head);
@@ -3413,12 +3414,9 @@ static struct nvme_ns_head *nvme_alloc_ns_head(struct nvme_ctrl *ctrl,
                goto out_ida_remove;
        head->subsys = ctrl->subsys;
        head->ns_id = nsid;
+       head->ids = *ids;
        kref_init(&head->ref);
 
-       ret = nvme_report_ns_ids(ctrl, nsid, id, &head->ids);
-       if (ret)
-               goto out_cleanup_srcu;
-
        ret = __nvme_check_ids(ctrl->subsys, head);
        if (ret) {
                dev_err(ctrl->device,
@@ -3453,24 +3451,23 @@ static int nvme_init_ns_head(struct nvme_ns *ns, unsigned nsid,
        struct nvme_ctrl *ctrl = ns->ctrl;
        bool is_shared = id->nmic & (1 << 0);
        struct nvme_ns_head *head = NULL;
+       struct nvme_ns_ids ids;
        int ret = 0;
 
+       ret = nvme_report_ns_ids(ctrl, nsid, id, &ids);
+       if (ret)
+               goto out;
+
        mutex_lock(&ctrl->subsys->lock);
        if (is_shared)
                head = nvme_find_ns_head(ctrl->subsys, nsid);
        if (!head) {
-               head = nvme_alloc_ns_head(ctrl, nsid, id);
+               head = nvme_alloc_ns_head(ctrl, nsid, id, &ids);
                if (IS_ERR(head)) {
                        ret = PTR_ERR(head);
                        goto out_unlock;
                }
        } else {
-               struct nvme_ns_ids ids;
-
-               ret = nvme_report_ns_ids(ctrl, nsid, id, &ids);
-               if (ret)
-                       goto out_unlock;
-
                if (!nvme_ns_ids_equal(&head->ids, &ids)) {
                        dev_err(ctrl->device,
                                "IDs don't match for shared namespace %d\n",
@@ -3485,6 +3482,7 @@ static int nvme_init_ns_head(struct nvme_ns *ns, unsigned nsid,
 
 out_unlock:
        mutex_unlock(&ctrl->subsys->lock);
+out:
        if (ret > 0)
                ret = blk_status_to_errno(nvme_error_status(ret));
        return ret;