From 1037e4b4f81dc4ddf928e0ca2f1b182efdfdcc9d Mon Sep 17 00:00:00 2001 From: James Smart Date: Fri, 14 May 2021 12:55:52 -0700 Subject: [PATCH] scsi: lpfc: Add ndlp kref accounting for resume RPI path The driver is crashing due to a bad pointer during driver load due in an adisc acc receive routine. The driver is missing node get/put in the mbx_resume_rpi paths. Fix by adding the proper gets and puts into the resume_rpi path. Link: https://lore.kernel.org/r/20210514195559.119853-5-jsmart2021@gmail.com Co-developed-by: Justin Tee Signed-off-by: Justin Tee Signed-off-by: James Smart Signed-off-by: Martin K. Petersen --- drivers/scsi/lpfc/lpfc_nportdisc.c | 4 ++++ drivers/scsi/lpfc/lpfc_sli.c | 23 ++++++++++++++++++++++- 2 files changed, 26 insertions(+), 1 deletion(-) diff --git a/drivers/scsi/lpfc/lpfc_nportdisc.c b/drivers/scsi/lpfc/lpfc_nportdisc.c index 3dac116..50cf234 100644 --- a/drivers/scsi/lpfc/lpfc_nportdisc.c +++ b/drivers/scsi/lpfc/lpfc_nportdisc.c @@ -662,6 +662,10 @@ lpfc_mbx_cmpl_resume_rpi(struct lpfc_hba *phba, LPFC_MBOXQ_t *mboxq) lpfc_els_rsp_acc(vport, ELS_CMD_PLOGI, elsiocb, ndlp, NULL); } + + /* This nlp_put pairs with lpfc_sli4_resume_rpi */ + lpfc_nlp_put(ndlp); + kfree(elsiocb); mempool_free(mboxq, phba->mbox_mem_pool); } diff --git a/drivers/scsi/lpfc/lpfc_sli.c b/drivers/scsi/lpfc/lpfc_sli.c index aefe16c..f68fe6f 100644 --- a/drivers/scsi/lpfc/lpfc_sli.c +++ b/drivers/scsi/lpfc/lpfc_sli.c @@ -2679,6 +2679,12 @@ lpfc_sli_def_mbox_cmpl(struct lpfc_hba *phba, LPFC_MBOXQ_t *pmb) } } + /* This nlp_put pairs with lpfc_sli4_resume_rpi */ + if (pmb->u.mb.mbxCommand == MBX_RESUME_RPI) { + ndlp = (struct lpfc_nodelist *)pmb->ctx_ndlp; + lpfc_nlp_put(ndlp); + } + /* Check security permission status on INIT_LINK mailbox command */ if ((pmb->u.mb.mbxCommand == MBX_INIT_LINK) && (pmb->u.mb.mbxStatus == MBXERR_SEC_NO_PERMISSION)) @@ -19037,14 +19043,28 @@ lpfc_sli4_resume_rpi(struct lpfc_nodelist *ndlp, if (!mboxq) return -ENOMEM; + /* If cmpl assigned, then this nlp_get pairs with + * lpfc_mbx_cmpl_resume_rpi. + * + * Else cmpl is NULL, then this nlp_get pairs with + * lpfc_sli_def_mbox_cmpl. + */ + if (!lpfc_nlp_get(ndlp)) { + lpfc_printf_log(phba, KERN_ERR, LOG_TRACE_EVENT, + "2122 %s: Failed to get nlp ref\n", + __func__); + mempool_free(mboxq, phba->mbox_mem_pool); + return -EIO; + } + /* Post all rpi memory regions to the port. */ lpfc_resume_rpi(mboxq, ndlp); if (cmpl) { mboxq->mbox_cmpl = cmpl; mboxq->ctx_buf = arg; - mboxq->ctx_ndlp = ndlp; } else mboxq->mbox_cmpl = lpfc_sli_def_mbox_cmpl; + mboxq->ctx_ndlp = ndlp; mboxq->vport = ndlp->vport; rc = lpfc_sli_issue_mbox(phba, mboxq, MBX_NOWAIT); if (rc == MBX_NOT_FINISHED) { @@ -19052,6 +19072,7 @@ lpfc_sli4_resume_rpi(struct lpfc_nodelist *ndlp, "2010 Resume RPI Mailbox failed " "status %d, mbxStatus x%x\n", rc, bf_get(lpfc_mqe_status, &mboxq->u.mqe)); + lpfc_nlp_put(ndlp); mempool_free(mboxq, phba->mbox_mem_pool); return -EIO; } -- 2.7.4