From: sashiko-bot@kernel.org
To: "Nigel Kirkland" <nkirkland2304@gmail.com>
Cc: linux-scsi@vger.kernel.org
Subject: Re: [PATCH v5 06/10] lpfc: Fix ndlp use-after-free during repeated RSCN and rediscovery sequence
Date: Mon, 28 Sep 2026 18:09:48 +0000 [thread overview]
Message-ID: <20260928180948.CA5301F000FF@smtp.kernel.org> (raw)
In-Reply-To: <20260928181757.21959-7-nkirkland2304@gmail.com>
Thank you for your contribution! Sashiko AI review found 2 potential issue(s) to consider:
- [High] lpfc: UAF and rport leak in lpfc_register_remote_port() due to race with devloss
- [High] lpfc: Duplicate NVMe transport registrations in lpfc_nlp_reg_node() due to missing synchronization
--
commit 01b3084183c4a09b5084e2e3651c384b815d645a
Author: Nigel Kirkland <nkirkland2304@gmail.com>
lpfc: Fix ndlp use-after-free during repeated RSCN and rediscovery sequence
The commit refactors transport registration flags to separate SCSI and
NVME states, preventing premature release of node objects during transport
callbacks. It also introduces symmetric reference-count tracking for NVMET
target nodes.
> diff --git a/drivers/scsi/lpfc/lpfc_hbadisc.c b/drivers/scsi/lpfc/lpfc_hbadisc.c
> --- a/drivers/scsi/lpfc/lpfc_hbadisc.c
> +++ b/drivers/scsi/lpfc/lpfc_hbadisc.c
[ ... ]
> @@ -4481,26 +4481,36 @@ lpfc_register_remote_port(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp)
> struct lpfc_hba *phba = vport->phba;
> unsigned long flags;
>
> - if (vport->cfg_enable_fc4_type == LPFC_ENABLE_NVME)
> + /* Don't add the remote port if unloading. */
> + if (test_bit(FC_UNLOADING, &vport->load_flag))
> return;
>
> + spin_lock_irqsave(&ndlp->lock, flags);
> + if ((ndlp->fc4_xpt_flags & (SCSI_XPT_REGD | SCSI_XPT_UNREG_WAIT)) ==
> + SCSI_XPT_REGD) {
> + /* Prevent racing registrations */
> + spin_unlock_irqrestore(&ndlp->lock, flags);
> + return;
> + }
> + ndlp->fc4_xpt_flags &= ~SCSI_XPT_UNREG_WAIT;
> + ndlp->fc4_xpt_flags |= SCSI_XPT_REGD;
> + spin_unlock_irqrestore(&ndlp->lock, flags);
[Severity: High]
Could this flag manipulation open a race window with devloss? By setting
SCSI_XPT_REGD and dropping ndlp->lock before calling fc_remote_port_add(),
ndlp->rport still points to the old rport.
If a concurrent dev_loss_work executes lpfc_dev_loss_tmo_callbk() on the
old rport before the new one is assigned, it will observe SCSI_XPT_REGD as
set.
If the driver is unloading, lpfc_nlp_put() is called prematurely here,
causing a use-after-free when lpfc_register_remote_port() resumes.
Otherwise, the callback clears SCSI_XPT_REGD, leaving the new rport
permanently unregistered and leaked since subsequent unregister calls will
bypass removal.
> /* Remote port has reappeared. Re-register w/ FC transport */
> rport_ids.node_name = wwn_to_u64(ndlp->nlp_nodename.u.wwn);
> rport_ids.port_name = wwn_to_u64(ndlp->nlp_portname.u.wwn);
[ ... ]
> @@ -4623,7 +4640,10 @@ lpfc_nlp_reg_node(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp)
> lpfc_check_nlp_post_devloss(vport, ndlp);
>
> spin_lock_irqsave(&ndlp->lock, iflags);
> - if (ndlp->fc4_xpt_flags & NLP_XPT_REGD) {
> + if (((ndlp->fc4_xpt_flags & SCSI_XPT_REGD) &&
> + !(ndlp->fc4_xpt_flags & SCSI_XPT_UNREG_WAIT)) ||
> + ((ndlp->fc4_xpt_flags & NVME_XPT_REGD) &&
> + !(ndlp->fc4_xpt_flags & NVME_XPT_UNREG_WAIT))) {
> /* Already registered with backend, trigger rescan */
> spin_unlock_irqrestore(&ndlp->lock, iflags);
[ ... ]
> - ndlp->fc4_xpt_flags |= NLP_XPT_REGD;
> spin_unlock_irqrestore(&ndlp->lock, iflags);
[ ... ]
> - if (vport->phba->sli_rev >= LPFC_SLI_REV4 &&
> - ndlp->nlp_fc4_type & NLP_FC4_NVME) {
> - if (vport->phba->nvmet_support == 0) {
> - /* Register this rport with the transport.
> - * Only NVME Target Rports are registered with
> - * the transport.
> - */
> - if (ndlp->nlp_type & NLP_NVME_TARGET) {
> - vport->phba->nport_event_cnt++;
> - lpfc_nvme_register_port(vport, ndlp);
> + if (vport->phba->nvmet_support == 0) {
> + /* Register this rport with the transport.
> + * Only NVME Target Rports are registered with
> + * the transport.
> + */
> + if (ndlp->nlp_type & NLP_NVME_TARGET) {
> + vport->phba->nport_event_cnt++;
> + lpfc_nvme_register_port(vport, ndlp);
[Severity: High]
Does removing the unified NLP_XPT_REGD flag setting before the unlock
allow duplicate NVMe transport registrations?
By replacing the single check with separate SCSI and NVME flag checks and
dropping ndlp->lock immediately, concurrent executions of lpfc_nlp_reg_node()
(for instance, from RSCN spam) can both observe NVME_XPT_REGD as 0 and
proceed to call lpfc_nvme_register_port().
Since lpfc_nvme_register_port() does not internally synchronize and check
NVME_XPT_REGD before calling nvme_fc_register_remoteport(), both threads
will register a new remoteport and increment the ndlp reference count. The
first remoteport will be overwritten in ndlp->nrport, permanently leaking
the transport object and its reference.
--
Sashiko AI review · https://sashiko.dev/#/patchset/20260928181757.21959-1-nkirkland2304@gmail.com?part=6
next prev parent reply other threads:[~2026-09-28 18:09 UTC|newest]
Thread overview: 17+ messages / expand[flat|nested] mbox.gz Atom feed top
2026-09-28 18:17 [PATCH v5 00/10] lpfc: Update lpfc to revision 15.0.0.1 Nigel Kirkland
2026-09-28 18:17 ` [PATCH v5 01/10] lpfc: Fix use-after-free in lpfc_cmpl_ct_cmd_vmid Nigel Kirkland
2026-09-28 18:17 ` [PATCH v5 02/10] lpfc: Early return out of lpfc_els_abort when HBA_SETUP flag is not set Nigel Kirkland
2026-09-28 18:17 ` [PATCH v5 03/10] lpfc: Fix kernel oops when unmapping scsi dma buffers for an aborted cmd Nigel Kirkland
2026-09-28 18:17 ` [PATCH v5 04/10] lpfc: Check fc4_xpt_flags before decrementing ndlp kref on FDISC error Nigel Kirkland
2026-09-28 18:19 ` sashiko-bot
2026-09-28 18:17 ` [PATCH v5 05/10] lpfc: Add handling for when PLOGI or PRLI is dropped during link failure Nigel Kirkland
2026-09-28 18:17 ` sashiko-bot
2026-09-28 18:17 ` [PATCH v5 06/10] lpfc: Fix ndlp use-after-free during repeated RSCN and rediscovery sequence Nigel Kirkland
2026-09-28 18:09 ` sashiko-bot [this message]
2026-09-28 18:17 ` [PATCH v5 07/10] lpfc: Rework I/O flush ordering when unloading driver Nigel Kirkland
2026-09-28 18:18 ` sashiko-bot
2026-09-28 18:17 ` [PATCH v5 08/10] lpfc: Refactor calls on fc_disctmo to lpfc_set_disctmo in RSCN handler Nigel Kirkland
2026-09-28 18:17 ` [PATCH v5 09/10] lpfc: Update correct ndlp refcnt when rejecting an unsolicited PLOGI Nigel Kirkland
2026-09-28 18:14 ` sashiko-bot
2026-09-28 18:17 ` [PATCH v5 10/10] lpfc: Update lpfc version to 15.0.0.1 Nigel Kirkland
2026-10-01 18:12 ` [PATCH v5 00/10] lpfc: Update lpfc to revision 15.0.0.1 Nigel Kirkland
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20260928180948.CA5301F000FF@smtp.kernel.org \
--to=sashiko-bot@kernel.org \
--cc=linux-scsi@vger.kernel.org \
--cc=nkirkland2304@gmail.com \
--cc=sashiko-reviews@lists.linux.dev \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox