]> www.infradead.org Git - users/jedix/linux-maple.git/commitdiff
nvme-fc: use lock accessing port_state and rport state
authorDaniel Wagner <wagi@kernel.org>
Tue, 2 Sep 2025 10:22:03 +0000 (12:22 +0200)
committerKeith Busch <kbusch@kernel.org>
Mon, 15 Sep 2025 15:52:57 +0000 (08:52 -0700)
nvme_fc_unregister_remote removes the remote port on a lport object at
any point in time when there is no active association. This races with
with the reconnect logic, because nvme_fc_create_association is not
taking a lock to check the port_state and atomically increase the
active count on the rport.

Reported-by: Shinichiro Kawasaki <shinichiro.kawasaki@wdc.com>
Closes: https://lore.kernel.org/all/u4ttvhnn7lark5w3sgrbuy2rxupcvosp4qmvj46nwzgeo5ausc@uyrkdls2muwx
Signed-off-by: Daniel Wagner <wagi@kernel.org>
Reviewed-by: Hannes Reinecke <hare@suse.de>
Signed-off-by: Keith Busch <kbusch@kernel.org>
drivers/nvme/host/fc.c

index 3e12d4683ac72f9ef9c6dff64d22d5d97e6f3d60..03987f497a5b55533ee169c9a7cb9b479d0f2d92 100644 (file)
@@ -3032,11 +3032,17 @@ nvme_fc_create_association(struct nvme_fc_ctrl *ctrl)
 
        ++ctrl->ctrl.nr_reconnects;
 
-       if (ctrl->rport->remoteport.port_state != FC_OBJSTATE_ONLINE)
+       spin_lock_irqsave(&ctrl->rport->lock, flags);
+       if (ctrl->rport->remoteport.port_state != FC_OBJSTATE_ONLINE) {
+               spin_unlock_irqrestore(&ctrl->rport->lock, flags);
                return -ENODEV;
+       }
 
-       if (nvme_fc_ctlr_active_on_rport(ctrl))
+       if (nvme_fc_ctlr_active_on_rport(ctrl)) {
+               spin_unlock_irqrestore(&ctrl->rport->lock, flags);
                return -ENOTUNIQ;
+       }
+       spin_unlock_irqrestore(&ctrl->rport->lock, flags);
 
        dev_info(ctrl->ctrl.device,
                "NVME-FC{%d}: create association : host wwpn 0x%016llx "