summaryrefslogtreecommitdiffstats
path: root/drivers/scsi/lpfc/lpfc_els.c
diff options
context:
space:
mode:
authorJames Smart <jsmart2021@gmail.com>2021-03-01 09:18:04 -0800
committerMartin K. Petersen <martin.petersen@oracle.com>2021-03-04 17:37:04 -0500
commit618e2ee146d414481c39af61fb018f50bee4ad33 (patch)
tree9f624f0a8145d74b047e27efd26759f3c42529de /drivers/scsi/lpfc/lpfc_els.c
parent2693f5deed16e302297fa591862dd9cc560ec3b5 (diff)
downloadlinux-618e2ee146d414481c39af61fb018f50bee4ad33.tar.gz
linux-618e2ee146d414481c39af61fb018f50bee4ad33.tar.bz2
linux-618e2ee146d414481c39af61fb018f50bee4ad33.zip
scsi: lpfc: Fix FLOGI failure due to accessing a freed node
After an initial successful FLOGI into the switch, if a subsequent FLOGI fails the driver crashed accessing a node struct. On FLOGI error, the flogi completion logic triggers the final dereference on the node structure without checking if it is registered with a backend. The devloss logic is triggered after node is freed leading to the access of freed node. Fix by adjusting the error path to not take the final dereferece if there is an outstanding transport registration. Let the transport devloss call remove the final reference. Link: https://lore.kernel.org/r/20210301171821.3427-6-jsmart2021@gmail.com Co-developed-by: Dick Kennedy <dick.kennedy@broadcom.com> Signed-off-by: Dick Kennedy <dick.kennedy@broadcom.com> Signed-off-by: James Smart <jsmart2021@gmail.com> Signed-off-by: Martin K. Petersen <martin.petersen@oracle.com>
Diffstat (limited to 'drivers/scsi/lpfc/lpfc_els.c')
-rw-r--r--drivers/scsi/lpfc/lpfc_els.c3
1 files changed, 2 insertions, 1 deletions
diff --git a/drivers/scsi/lpfc/lpfc_els.c b/drivers/scsi/lpfc/lpfc_els.c
index cc0b4f2661ab..27e2f8136f73 100644
--- a/drivers/scsi/lpfc/lpfc_els.c
+++ b/drivers/scsi/lpfc/lpfc_els.c
@@ -1182,7 +1182,8 @@ flogifail:
phba->fcf.fcf_flag &= ~FCF_DISCOVERY;
spin_unlock_irq(&phba->hbalock);
- lpfc_nlp_put(ndlp);
+ if (!(ndlp->fc4_xpt_flags & (SCSI_XPT_REGD | NVME_XPT_REGD)))
+ lpfc_nlp_put(ndlp);
if (!lpfc_error_lost_link(irsp)) {
/* FLOGI failed, so just use loop map to make discovery list */
lpfc_disc_list_loopmap(vport);