|
Daniel Wagner |
c09905 |
From: James Smart <jsmart2021@gmail.com>
|
|
Daniel Wagner |
c09905 |
Date: Fri, 14 May 2021 12:55:58 -0700
|
|
Daniel Wagner |
c09905 |
Subject: scsi: lpfc: Reregister FPIN types if ELS_RDF is received from fabric
|
|
Daniel Wagner |
c09905 |
controller
|
|
Daniel Wagner |
c09905 |
Patch-mainline: Queued in subsystem maintainer repository
|
|
Daniel Wagner |
c09905 |
Git-repo: git://git.kernel.org/pub/scm/linux/kernel/git/mkp/scsi.git
|
|
Daniel Wagner |
c09905 |
Git-commit: 8eced807077d198fc264629bd2592795d270c9f1
|
|
Daniel Wagner |
c09905 |
References: bsc#1186451
|
|
Daniel Wagner |
c09905 |
|
|
Daniel Wagner |
c09905 |
FC-LS-5 specifies that a received RDF implies a possible change to fabric
|
|
Daniel Wagner |
c09905 |
supported diagnostic functions. Endpoints are to re-perform the RDF
|
|
Daniel Wagner |
c09905 |
exchange with the fabric to enable possible new features or adapt to
|
|
Daniel Wagner |
c09905 |
changes in values.
|
|
Daniel Wagner |
c09905 |
|
|
Daniel Wagner |
c09905 |
This patch adds the logic to RDF receive to re-perform the RDF exchange
|
|
Daniel Wagner |
c09905 |
with the switch.
|
|
Daniel Wagner |
c09905 |
|
|
Daniel Wagner |
c09905 |
Link: https://lore.kernel.org/r/20210514195559.119853-11-jsmart2021@gmail.com
|
|
Daniel Wagner |
c09905 |
Co-developed-by: Justin Tee <justin.tee@broadcom.com>
|
|
Daniel Wagner |
c09905 |
Signed-off-by: Justin Tee <justin.tee@broadcom.com>
|
|
Daniel Wagner |
c09905 |
Signed-off-by: James Smart <jsmart2021@gmail.com>
|
|
Daniel Wagner |
c09905 |
Signed-off-by: Martin K. Petersen <martin.petersen@oracle.com>
|
|
Daniel Wagner |
c09905 |
Acked-by: Daniel Wagner <dwagner@suse.de>
|
|
Daniel Wagner |
c09905 |
---
|
|
Daniel Wagner |
c09905 |
drivers/scsi/lpfc/lpfc.h | 1
|
|
Daniel Wagner |
c09905 |
drivers/scsi/lpfc/lpfc_els.c | 75 +++++++++++++++++++++++++++++++++++++++++++
|
|
Daniel Wagner |
c09905 |
2 files changed, 76 insertions(+)
|
|
Daniel Wagner |
c09905 |
|
|
Daniel Wagner |
c09905 |
--- a/drivers/scsi/lpfc/lpfc.h
|
|
Daniel Wagner |
c09905 |
+++ b/drivers/scsi/lpfc/lpfc.h
|
|
Daniel Wagner |
c09905 |
@@ -266,6 +266,7 @@ struct lpfc_stats {
|
|
Daniel Wagner |
c09905 |
uint32_t elsRcvECHO;
|
|
Daniel Wagner |
c09905 |
uint32_t elsRcvLCB;
|
|
Daniel Wagner |
c09905 |
uint32_t elsRcvRDP;
|
|
Daniel Wagner |
c09905 |
+ uint32_t elsRcvRDF;
|
|
Daniel Wagner |
c09905 |
uint32_t elsXmitFLOGI;
|
|
Daniel Wagner |
c09905 |
uint32_t elsXmitFDISC;
|
|
Daniel Wagner |
c09905 |
uint32_t elsXmitPLOGI;
|
|
Daniel Wagner |
c09905 |
--- a/drivers/scsi/lpfc/lpfc_els.c
|
|
Daniel Wagner |
c09905 |
+++ b/drivers/scsi/lpfc/lpfc_els.c
|
|
Daniel Wagner |
c09905 |
@@ -3670,6 +3670,43 @@ lpfc_issue_els_rdf(struct lpfc_vport *vp
|
|
Daniel Wagner |
c09905 |
return 0;
|
|
Daniel Wagner |
c09905 |
}
|
|
Daniel Wagner |
c09905 |
|
|
Daniel Wagner |
c09905 |
+ /**
|
|
Daniel Wagner |
c09905 |
+ * lpfc_els_rcv_rdf - Receive RDF ELS request from the fabric.
|
|
Daniel Wagner |
c09905 |
+ * @vport: pointer to a host virtual N_Port data structure.
|
|
Daniel Wagner |
c09905 |
+ * @cmdiocb: pointer to lpfc command iocb data structure.
|
|
Daniel Wagner |
c09905 |
+ * @ndlp: pointer to a node-list data structure.
|
|
Daniel Wagner |
c09905 |
+ *
|
|
Daniel Wagner |
c09905 |
+ * A received RDF implies a possible change to fabric supported diagnostic
|
|
Daniel Wagner |
c09905 |
+ * functions. This routine sends LS_ACC and then has the Nx_Port issue a new
|
|
Daniel Wagner |
c09905 |
+ * RDF request to reregister for supported diagnostic functions.
|
|
Daniel Wagner |
c09905 |
+ *
|
|
Daniel Wagner |
c09905 |
+ * Return code
|
|
Daniel Wagner |
c09905 |
+ * 0 - Success
|
|
Daniel Wagner |
c09905 |
+ * -EIO - Failed to process received RDF
|
|
Daniel Wagner |
c09905 |
+ **/
|
|
Daniel Wagner |
c09905 |
+static int
|
|
Daniel Wagner |
c09905 |
+lpfc_els_rcv_rdf(struct lpfc_vport *vport, struct lpfc_iocbq *cmdiocb,
|
|
Daniel Wagner |
c09905 |
+ struct lpfc_nodelist *ndlp)
|
|
Daniel Wagner |
c09905 |
+{
|
|
Daniel Wagner |
c09905 |
+ /* Send LS_ACC */
|
|
Daniel Wagner |
c09905 |
+ if (lpfc_els_rsp_acc(vport, ELS_CMD_RDF, cmdiocb, ndlp, NULL)) {
|
|
Daniel Wagner |
c09905 |
+ lpfc_printf_vlog(vport, KERN_INFO, LOG_ELS,
|
|
Daniel Wagner |
c09905 |
+ "1623 Failed to RDF_ACC from x%x for x%x\n",
|
|
Daniel Wagner |
c09905 |
+ ndlp->nlp_DID, vport->fc_myDID);
|
|
Daniel Wagner |
c09905 |
+ return -EIO;
|
|
Daniel Wagner |
c09905 |
+ }
|
|
Daniel Wagner |
c09905 |
+
|
|
Daniel Wagner |
c09905 |
+ /* Issue new RDF for reregistering */
|
|
Daniel Wagner |
c09905 |
+ if (lpfc_issue_els_rdf(vport, 0)) {
|
|
Daniel Wagner |
c09905 |
+ lpfc_printf_vlog(vport, KERN_INFO, LOG_ELS,
|
|
Daniel Wagner |
c09905 |
+ "2623 Failed to re register RDF for x%x\n",
|
|
Daniel Wagner |
c09905 |
+ vport->fc_myDID);
|
|
Daniel Wagner |
c09905 |
+ return -EIO;
|
|
Daniel Wagner |
c09905 |
+ }
|
|
Daniel Wagner |
c09905 |
+
|
|
Daniel Wagner |
c09905 |
+ return 0;
|
|
Daniel Wagner |
c09905 |
+}
|
|
Daniel Wagner |
c09905 |
+
|
|
Daniel Wagner |
c09905 |
/**
|
|
Daniel Wagner |
c09905 |
* lpfc_cancel_retry_delay_tmo - Cancel the timer with delayed iocb-cmd retry
|
|
Daniel Wagner |
c09905 |
* @vport: pointer to a host virtual N_Port data structure.
|
|
Daniel Wagner |
c09905 |
@@ -4803,6 +4840,7 @@ lpfc_els_rsp_acc(struct lpfc_vport *vpor
|
|
Daniel Wagner |
c09905 |
uint16_t cmdsize;
|
|
Daniel Wagner |
c09905 |
int rc;
|
|
Daniel Wagner |
c09905 |
ELS_PKT *els_pkt_ptr;
|
|
Daniel Wagner |
c09905 |
+ struct fc_els_rdf_resp *rdf_resp;
|
|
Daniel Wagner |
c09905 |
|
|
Daniel Wagner |
c09905 |
oldcmd = &oldiocb->iocb;
|
|
Daniel Wagner |
c09905 |
|
|
Daniel Wagner |
c09905 |
@@ -4914,6 +4952,29 @@ lpfc_els_rsp_acc(struct lpfc_vport *vpor
|
|
Daniel Wagner |
c09905 |
"Issue ACC PRLO: did:x%x flg:x%x",
|
|
Daniel Wagner |
c09905 |
ndlp->nlp_DID, ndlp->nlp_flag, 0);
|
|
Daniel Wagner |
c09905 |
break;
|
|
Daniel Wagner |
c09905 |
+ case ELS_CMD_RDF:
|
|
Daniel Wagner |
c09905 |
+ cmdsize = sizeof(*rdf_resp);
|
|
Daniel Wagner |
c09905 |
+ elsiocb = lpfc_prep_els_iocb(vport, 0, cmdsize, oldiocb->retry,
|
|
Daniel Wagner |
c09905 |
+ ndlp, ndlp->nlp_DID, ELS_CMD_ACC);
|
|
Daniel Wagner |
c09905 |
+ if (!elsiocb)
|
|
Daniel Wagner |
c09905 |
+ return 1;
|
|
Daniel Wagner |
c09905 |
+
|
|
Daniel Wagner |
c09905 |
+ icmd = &elsiocb->iocb;
|
|
Daniel Wagner |
c09905 |
+ icmd->ulpContext = oldcmd->ulpContext; /* Xri / rx_id */
|
|
Daniel Wagner |
c09905 |
+ icmd->unsli3.rcvsli3.ox_id = oldcmd->unsli3.rcvsli3.ox_id;
|
|
Daniel Wagner |
c09905 |
+ pcmd = (((struct lpfc_dmabuf *)elsiocb->context2)->virt);
|
|
Daniel Wagner |
c09905 |
+ rdf_resp = (struct fc_els_rdf_resp *)pcmd;
|
|
Daniel Wagner |
c09905 |
+ memset(rdf_resp, 0, sizeof(*rdf_resp));
|
|
Daniel Wagner |
c09905 |
+ rdf_resp->acc_hdr.la_cmd = ELS_LS_ACC;
|
|
Daniel Wagner |
c09905 |
+
|
|
Daniel Wagner |
c09905 |
+ /* FC-LS-5 specifies desc_list_len shall be set to 12 */
|
|
Daniel Wagner |
c09905 |
+ rdf_resp->desc_list_len = cpu_to_be32(12);
|
|
Daniel Wagner |
c09905 |
+
|
|
Daniel Wagner |
c09905 |
+ /* FC-LS-5 specifies LS REQ Information descriptor */
|
|
Daniel Wagner |
c09905 |
+ rdf_resp->lsri.desc_tag = cpu_to_be32(1);
|
|
Daniel Wagner |
c09905 |
+ rdf_resp->lsri.desc_len = cpu_to_be32(sizeof(u32));
|
|
Daniel Wagner |
c09905 |
+ rdf_resp->lsri.rqst_w0.cmd = ELS_RDF;
|
|
Daniel Wagner |
c09905 |
+ break;
|
|
Daniel Wagner |
c09905 |
default:
|
|
Daniel Wagner |
c09905 |
return 1;
|
|
Daniel Wagner |
c09905 |
}
|
|
Daniel Wagner |
c09905 |
@@ -9027,6 +9088,20 @@ lpfc_els_unsol_buffer(struct lpfc_hba *p
|
|
Daniel Wagner |
c09905 |
|
|
Daniel Wagner |
c09905 |
/* There are no replies, so no rjt codes */
|
|
Daniel Wagner |
c09905 |
break;
|
|
Daniel Wagner |
c09905 |
+ case ELS_CMD_RDF:
|
|
Daniel Wagner |
c09905 |
+ phba->fc_stat.elsRcvRDF++;
|
|
Daniel Wagner |
c09905 |
+ /* Accept RDF only from fabric controller */
|
|
Daniel Wagner |
c09905 |
+ if (did != Fabric_Cntl_DID) {
|
|
Daniel Wagner |
c09905 |
+ lpfc_printf_vlog(vport, KERN_WARNING, LOG_ELS,
|
|
Daniel Wagner |
c09905 |
+ "1115 Received RDF from invalid DID "
|
|
Daniel Wagner |
c09905 |
+ "x%x\n", did);
|
|
Daniel Wagner |
c09905 |
+ rjt_err = LSRJT_PROTOCOL_ERR;
|
|
Daniel Wagner |
c09905 |
+ rjt_exp = LSEXP_NOTHING_MORE;
|
|
Daniel Wagner |
c09905 |
+ goto lsrjt;
|
|
Daniel Wagner |
c09905 |
+ }
|
|
Daniel Wagner |
c09905 |
+
|
|
Daniel Wagner |
c09905 |
+ lpfc_els_rcv_rdf(vport, elsiocb, ndlp);
|
|
Daniel Wagner |
c09905 |
+ break;
|
|
Daniel Wagner |
c09905 |
default:
|
|
Daniel Wagner |
c09905 |
lpfc_debugfs_disc_trc(vport, LPFC_DISC_TRC_ELS_UNSOL,
|
|
Daniel Wagner |
c09905 |
"RCV ELS cmd: cmd:x%x did:x%x/ste:x%x",
|