forked from Minki/linux
[SCSI] lpfc 8.3.29: SLI related fixes
SLI related fixes: - Fix REG_RPI fails on SLI4 HBA putting NPort into NPR state (126230) - Fix ELS FDISC failing with local reject / invalid RPI. (126350) - Fix reset port when reset is needed during fw_dump (125807) - Fix unbounded firmware revision string from port cause panic (126560) - Fix driver behavior when receiving an ADISC (126654) - Fix driver not returning when bad ndlp found in abts error event handling (126209) - Add more driver logs in area of SLI4 port error attention and reset recovery (126813, 124466) - Fix failure in handling large CQ/EQ identifiers in an IOV environment (126856) - Fix for driver using duplicate RPIs after lancer port reset (126723) - Clear vport->fc_myDID in lpfc_els_issue_fdisc to guarentee a zero SID (126779, 126897) - Fix for SLI4 Port delivery for BLS ABORT ACC (126289) Signed-off-by: Alex Iannicelli <alex.iannicelli@emulex.com> Signed-off-by: James Smart <james.smart@emulex.com> Signed-off-by: James Bottomley <JBottomley@Parallels.com>
This commit is contained in:
parent
3ef6d24cd9
commit
6b5151fd7b
@ -353,7 +353,7 @@ lpfc_fwrev_show(struct device *dev, struct device_attribute *attr,
|
||||
struct lpfc_hba *phba = vport->phba;
|
||||
uint32_t if_type;
|
||||
uint8_t sli_family;
|
||||
char fwrev[32];
|
||||
char fwrev[FW_REV_STR_SIZE];
|
||||
int len;
|
||||
|
||||
lpfc_decode_firmware_rev(phba, fwrev, 1);
|
||||
@ -922,11 +922,15 @@ lpfc_sli4_pdev_reg_request(struct lpfc_hba *phba, uint32_t opcode)
|
||||
rc = lpfc_sli4_pdev_status_reg_wait(phba);
|
||||
|
||||
if (rc == -EPERM) {
|
||||
/* no privilage for reset, restore if needed */
|
||||
if (before_fc_flag & FC_OFFLINE_MODE)
|
||||
goto out;
|
||||
/* no privilage for reset */
|
||||
lpfc_printf_log(phba, KERN_ERR, LOG_SLI,
|
||||
"3150 No privilage to perform the requested "
|
||||
"access: x%x\n", reg_val);
|
||||
} else if (rc == -EIO) {
|
||||
/* reset failed, there is nothing more we can do */
|
||||
lpfc_printf_log(phba, KERN_ERR, LOG_SLI,
|
||||
"3153 Fail to perform the requested "
|
||||
"access: x%x\n", reg_val);
|
||||
return rc;
|
||||
}
|
||||
|
||||
|
@ -3980,7 +3980,7 @@ lpfc_bsg_handle_sli_cfg_mbox(struct lpfc_hba *phba, struct fc_bsg_job *job,
|
||||
case COMN_OPCODE_GET_CNTL_ADDL_ATTRIBUTES:
|
||||
lpfc_printf_log(phba, KERN_INFO, LOG_LIBDFC,
|
||||
"3106 Handled SLI_CONFIG "
|
||||
"subsys_fcoe, opcode:x%x\n",
|
||||
"subsys_comn, opcode:x%x\n",
|
||||
opcode);
|
||||
rc = lpfc_bsg_sli_cfg_read_cmd_ext(phba, job,
|
||||
nemb_mse, dmabuf);
|
||||
@ -3988,7 +3988,7 @@ lpfc_bsg_handle_sli_cfg_mbox(struct lpfc_hba *phba, struct fc_bsg_job *job,
|
||||
default:
|
||||
lpfc_printf_log(phba, KERN_INFO, LOG_LIBDFC,
|
||||
"3107 Reject SLI_CONFIG "
|
||||
"subsys_fcoe, opcode:x%x\n",
|
||||
"subsys_comn, opcode:x%x\n",
|
||||
opcode);
|
||||
rc = -EPERM;
|
||||
break;
|
||||
|
@ -462,3 +462,4 @@ int lpfc_issue_unreg_vfi(struct lpfc_vport *);
|
||||
int lpfc_selective_reset(struct lpfc_hba *);
|
||||
int lpfc_sli4_read_config(struct lpfc_hba *phba);
|
||||
int lpfc_scsi_buf_update(struct lpfc_hba *phba);
|
||||
void lpfc_sli4_node_prep(struct lpfc_hba *phba);
|
||||
|
@ -1076,7 +1076,7 @@ int
|
||||
lpfc_vport_symbolic_node_name(struct lpfc_vport *vport, char *symbol,
|
||||
size_t size)
|
||||
{
|
||||
char fwrev[16];
|
||||
char fwrev[FW_REV_STR_SIZE];
|
||||
int n;
|
||||
|
||||
lpfc_decode_firmware_rev(vport->phba, fwrev, 0);
|
||||
@ -1834,7 +1834,7 @@ lpfc_decode_firmware_rev(struct lpfc_hba *phba, char *fwrevision, int flag)
|
||||
uint8_t *fwname;
|
||||
|
||||
if (phba->sli_rev == LPFC_SLI_REV4)
|
||||
sprintf(fwrevision, "%s", vp->rev.opFwName);
|
||||
snprintf(fwrevision, FW_REV_STR_SIZE, "%s", vp->rev.opFwName);
|
||||
else if (vp->rev.rBit) {
|
||||
if (psli->sli_flag & LPFC_SLI_ACTIVE)
|
||||
rev = vp->rev.sli2FwRev;
|
||||
|
@ -7172,7 +7172,7 @@ lpfc_cmpl_els_fdisc(struct lpfc_hba *phba, struct lpfc_iocbq *cmdiocb,
|
||||
goto out;
|
||||
/* FDISC failed */
|
||||
lpfc_printf_vlog(vport, KERN_ERR, LOG_ELS,
|
||||
"0126 FDISC failed. (%d/%d)\n",
|
||||
"0126 FDISC failed. (x%x/x%x)\n",
|
||||
irsp->ulpStatus, irsp->un.ulpWord[4]);
|
||||
goto fdisc_failed;
|
||||
}
|
||||
@ -7283,6 +7283,7 @@ lpfc_issue_els_fdisc(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
|
||||
int rc;
|
||||
|
||||
vport->port_state = LPFC_FDISC;
|
||||
vport->fc_myDID = 0;
|
||||
cmdsize = (sizeof(uint32_t) + sizeof(struct serv_parm));
|
||||
elsiocb = lpfc_prep_els_iocb(vport, 1, cmdsize, retry, ndlp, did,
|
||||
ELS_CMD_FDISC);
|
||||
|
@ -70,6 +70,7 @@
|
||||
/* vendor ID used in SCSI netlink calls */
|
||||
#define LPFC_NL_VENDOR_ID (SCSI_NL_VID_TYPE_PCI | PCI_VENDOR_ID_EMULEX)
|
||||
|
||||
#define FW_REV_STR_SIZE 32
|
||||
/* Common Transport structures and definitions */
|
||||
|
||||
union CtRevisionId {
|
||||
|
@ -715,12 +715,20 @@ struct lpfc_register {
|
||||
#define lpfc_eqcq_doorbell_eqci_SHIFT 9
|
||||
#define lpfc_eqcq_doorbell_eqci_MASK 0x0001
|
||||
#define lpfc_eqcq_doorbell_eqci_WORD word0
|
||||
#define lpfc_eqcq_doorbell_cqid_SHIFT 0
|
||||
#define lpfc_eqcq_doorbell_cqid_MASK 0x03FF
|
||||
#define lpfc_eqcq_doorbell_cqid_WORD word0
|
||||
#define lpfc_eqcq_doorbell_eqid_SHIFT 0
|
||||
#define lpfc_eqcq_doorbell_eqid_MASK 0x01FF
|
||||
#define lpfc_eqcq_doorbell_eqid_WORD word0
|
||||
#define lpfc_eqcq_doorbell_cqid_lo_SHIFT 0
|
||||
#define lpfc_eqcq_doorbell_cqid_lo_MASK 0x03FF
|
||||
#define lpfc_eqcq_doorbell_cqid_lo_WORD word0
|
||||
#define lpfc_eqcq_doorbell_cqid_hi_SHIFT 11
|
||||
#define lpfc_eqcq_doorbell_cqid_hi_MASK 0x001F
|
||||
#define lpfc_eqcq_doorbell_cqid_hi_WORD word0
|
||||
#define lpfc_eqcq_doorbell_eqid_lo_SHIFT 0
|
||||
#define lpfc_eqcq_doorbell_eqid_lo_MASK 0x01FF
|
||||
#define lpfc_eqcq_doorbell_eqid_lo_WORD word0
|
||||
#define lpfc_eqcq_doorbell_eqid_hi_SHIFT 11
|
||||
#define lpfc_eqcq_doorbell_eqid_hi_MASK 0x001F
|
||||
#define lpfc_eqcq_doorbell_eqid_hi_WORD word0
|
||||
#define LPFC_CQID_HI_FIELD_SHIFT 10
|
||||
#define LPFC_EQID_HI_FIELD_SHIFT 9
|
||||
|
||||
#define LPFC_BMBX 0x0160
|
||||
#define lpfc_bmbx_addr_SHIFT 2
|
||||
@ -3313,7 +3321,11 @@ struct xmit_bls_rsp64_wqe {
|
||||
uint32_t rsrvd4;
|
||||
struct wqe_did wqe_dest;
|
||||
struct wqe_common wqe_com; /* words 6-11 */
|
||||
uint32_t rsvd_12_15[4];
|
||||
uint32_t word12;
|
||||
#define xmit_bls_rsp64_temprpi_SHIFT 0
|
||||
#define xmit_bls_rsp64_temprpi_MASK 0x0000ffff
|
||||
#define xmit_bls_rsp64_temprpi_WORD word12
|
||||
uint32_t rsvd_13_15[3];
|
||||
};
|
||||
|
||||
struct wqe_rctl_dfctl {
|
||||
|
@ -1475,8 +1475,12 @@ lpfc_handle_eratt_s4(struct lpfc_hba *phba)
|
||||
phba->sli4_hba.u.if_type2.STATUSregaddr,
|
||||
&portstat_reg.word0);
|
||||
/* consider PCI bus read error as pci_channel_offline */
|
||||
if (pci_rd_rc1 == -EIO)
|
||||
if (pci_rd_rc1 == -EIO) {
|
||||
lpfc_printf_log(phba, KERN_ERR, LOG_INIT,
|
||||
"3151 PCI bus read access failure: x%x\n",
|
||||
readl(phba->sli4_hba.u.if_type2.STATUSregaddr));
|
||||
return;
|
||||
}
|
||||
reg_err1 = readl(phba->sli4_hba.u.if_type2.ERR1regaddr);
|
||||
reg_err2 = readl(phba->sli4_hba.u.if_type2.ERR2regaddr);
|
||||
if (bf_get(lpfc_sliport_status_oti, &portstat_reg)) {
|
||||
@ -1526,6 +1530,9 @@ lpfc_handle_eratt_s4(struct lpfc_hba *phba)
|
||||
}
|
||||
/* fall through for not able to recover */
|
||||
}
|
||||
lpfc_printf_log(phba, KERN_ERR, LOG_INIT,
|
||||
"3152 Unrecoverable error, bring the port "
|
||||
"offline\n");
|
||||
lpfc_sli4_offline_eratt(phba);
|
||||
break;
|
||||
case LPFC_SLI_INTF_IF_TYPE_1:
|
||||
@ -2513,6 +2520,42 @@ lpfc_block_mgmt_io(struct lpfc_hba * phba)
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* lpfc_sli4_node_prep - Assign RPIs for active nodes.
|
||||
* @phba: pointer to lpfc hba data structure.
|
||||
*
|
||||
* Allocate RPIs for all active remote nodes. This is needed whenever
|
||||
* an SLI4 adapter is reset and the driver is not unloading. Its purpose
|
||||
* is to fixup the temporary rpi assignments.
|
||||
**/
|
||||
void
|
||||
lpfc_sli4_node_prep(struct lpfc_hba *phba)
|
||||
{
|
||||
struct lpfc_nodelist *ndlp, *next_ndlp;
|
||||
struct lpfc_vport **vports;
|
||||
int i;
|
||||
|
||||
if (phba->sli_rev != LPFC_SLI_REV4)
|
||||
return;
|
||||
|
||||
vports = lpfc_create_vport_work_array(phba);
|
||||
if (vports != NULL) {
|
||||
for (i = 0; i <= phba->max_vports && vports[i] != NULL; i++) {
|
||||
if (vports[i]->load_flag & FC_UNLOADING)
|
||||
continue;
|
||||
|
||||
list_for_each_entry_safe(ndlp, next_ndlp,
|
||||
&vports[i]->fc_nodes,
|
||||
nlp_listp) {
|
||||
if (NLP_CHK_NODE_ACT(ndlp))
|
||||
ndlp->nlp_rpi =
|
||||
lpfc_sli4_alloc_rpi(phba);
|
||||
}
|
||||
}
|
||||
}
|
||||
lpfc_destroy_vport_work_array(phba, vports);
|
||||
}
|
||||
|
||||
/**
|
||||
* lpfc_online - Initialize and bring a HBA online
|
||||
* @phba: pointer to lpfc hba data structure.
|
||||
@ -2654,6 +2697,15 @@ lpfc_offline_prep(struct lpfc_hba * phba)
|
||||
}
|
||||
spin_lock_irq(shost->host_lock);
|
||||
ndlp->nlp_flag &= ~NLP_NPR_ADISC;
|
||||
|
||||
/*
|
||||
* Whenever an SLI4 port goes offline, free the
|
||||
* RPI. A new RPI when the adapter port comes
|
||||
* back online.
|
||||
*/
|
||||
if (phba->sli_rev == LPFC_SLI_REV4)
|
||||
lpfc_sli4_free_rpi(phba, ndlp->nlp_rpi);
|
||||
|
||||
spin_unlock_irq(shost->host_lock);
|
||||
lpfc_unreg_rpi(vports[i], ndlp);
|
||||
}
|
||||
@ -7224,19 +7276,17 @@ lpfc_pci_function_reset(struct lpfc_hba *phba)
|
||||
rc = -ENODEV;
|
||||
goto out;
|
||||
}
|
||||
if (bf_get(lpfc_sliport_status_rn, ®_data))
|
||||
reset_again++;
|
||||
if (bf_get(lpfc_sliport_status_rdy, ®_data))
|
||||
break;
|
||||
if (bf_get(lpfc_sliport_status_rn, ®_data)) {
|
||||
reset_again++;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* If the port responds to the init request with
|
||||
* reset needed, delay for a bit and restart the loop.
|
||||
*/
|
||||
if (reset_again) {
|
||||
if (reset_again && (rdy_chk < 1000)) {
|
||||
msleep(10);
|
||||
reset_again = 0;
|
||||
continue;
|
||||
@ -9059,7 +9109,7 @@ lpfc_sli4_get_els_iocb_cnt(struct lpfc_hba *phba)
|
||||
int
|
||||
lpfc_write_firmware(struct lpfc_hba *phba, const struct firmware *fw)
|
||||
{
|
||||
char fwrev[32];
|
||||
char fwrev[FW_REV_STR_SIZE];
|
||||
struct lpfc_grp_hdr *image = (struct lpfc_grp_hdr *)fw->data;
|
||||
struct list_head dma_buffer_list;
|
||||
int i, rc = 0;
|
||||
|
@ -48,6 +48,10 @@ static int
|
||||
lpfc_check_adisc(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
|
||||
struct lpfc_name *nn, struct lpfc_name *pn)
|
||||
{
|
||||
/* First, we MUST have a RPI registered */
|
||||
if (!(ndlp->nlp_flag & NLP_RPI_REGISTERED))
|
||||
return 0;
|
||||
|
||||
/* Compare the ADISC rsp WWNN / WWPN matches our internal node
|
||||
* table entry for that node.
|
||||
*/
|
||||
@ -385,6 +389,10 @@ lpfc_rcv_plogi(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
|
||||
if (!mbox)
|
||||
goto out;
|
||||
|
||||
/* Registering an existing RPI behaves differently for SLI3 vs SLI4 */
|
||||
if (phba->sli_rev == LPFC_SLI_REV4)
|
||||
lpfc_unreg_rpi(vport, ndlp);
|
||||
|
||||
rc = lpfc_reg_rpi(phba, vport->vpi, icmd->un.rcvels.remoteID,
|
||||
(uint8_t *) sp, mbox, ndlp->nlp_rpi);
|
||||
if (rc) {
|
||||
@ -445,11 +453,42 @@ out:
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* lpfc_mbx_cmpl_resume_rpi - Resume RPI completion routine
|
||||
* @phba: pointer to lpfc hba data structure.
|
||||
* @mboxq: pointer to mailbox object
|
||||
*
|
||||
* This routine is invoked to issue a completion to a rcv'ed
|
||||
* ADISC or PDISC after the paused RPI has been resumed.
|
||||
**/
|
||||
static void
|
||||
lpfc_mbx_cmpl_resume_rpi(struct lpfc_hba *phba, LPFC_MBOXQ_t *mboxq)
|
||||
{
|
||||
struct lpfc_vport *vport;
|
||||
struct lpfc_iocbq *elsiocb;
|
||||
struct lpfc_nodelist *ndlp;
|
||||
uint32_t cmd;
|
||||
|
||||
elsiocb = (struct lpfc_iocbq *)mboxq->context1;
|
||||
ndlp = (struct lpfc_nodelist *) mboxq->context2;
|
||||
vport = mboxq->vport;
|
||||
cmd = elsiocb->drvrTimeout;
|
||||
|
||||
if (cmd == ELS_CMD_ADISC) {
|
||||
lpfc_els_rsp_adisc_acc(vport, elsiocb, ndlp);
|
||||
} else {
|
||||
lpfc_els_rsp_acc(vport, ELS_CMD_PLOGI, elsiocb,
|
||||
ndlp, NULL);
|
||||
}
|
||||
kfree(elsiocb);
|
||||
}
|
||||
|
||||
static int
|
||||
lpfc_rcv_padisc(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
|
||||
struct lpfc_iocbq *cmdiocb)
|
||||
{
|
||||
struct Scsi_Host *shost = lpfc_shost_from_vport(vport);
|
||||
struct lpfc_iocbq *elsiocb;
|
||||
struct lpfc_dmabuf *pcmd;
|
||||
struct serv_parm *sp;
|
||||
struct lpfc_name *pnn, *ppn;
|
||||
@ -475,12 +514,43 @@ lpfc_rcv_padisc(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
|
||||
|
||||
icmd = &cmdiocb->iocb;
|
||||
if (icmd->ulpStatus == 0 && lpfc_check_adisc(vport, ndlp, pnn, ppn)) {
|
||||
|
||||
/*
|
||||
* As soon as we send ACC, the remote NPort can
|
||||
* start sending us data. Thus, for SLI4 we must
|
||||
* resume the RPI before the ACC goes out.
|
||||
*/
|
||||
if (vport->phba->sli_rev == LPFC_SLI_REV4) {
|
||||
elsiocb = kmalloc(sizeof(struct lpfc_iocbq),
|
||||
GFP_KERNEL);
|
||||
if (elsiocb) {
|
||||
|
||||
/* Save info from cmd IOCB used in rsp */
|
||||
memcpy((uint8_t *)elsiocb, (uint8_t *)cmdiocb,
|
||||
sizeof(struct lpfc_iocbq));
|
||||
|
||||
/* Save the ELS cmd */
|
||||
elsiocb->drvrTimeout = cmd;
|
||||
|
||||
lpfc_sli4_resume_rpi(ndlp,
|
||||
lpfc_mbx_cmpl_resume_rpi, elsiocb);
|
||||
goto out;
|
||||
}
|
||||
}
|
||||
|
||||
if (cmd == ELS_CMD_ADISC) {
|
||||
lpfc_els_rsp_adisc_acc(vport, cmdiocb, ndlp);
|
||||
} else {
|
||||
lpfc_els_rsp_acc(vport, ELS_CMD_PLOGI, cmdiocb, ndlp,
|
||||
NULL);
|
||||
lpfc_els_rsp_acc(vport, ELS_CMD_PLOGI, cmdiocb,
|
||||
ndlp, NULL);
|
||||
}
|
||||
out:
|
||||
/* If we are authenticated, move to the proper state */
|
||||
if (ndlp->nlp_type & NLP_FCP_TARGET)
|
||||
lpfc_nlp_set_state(vport, ndlp, NLP_STE_MAPPED_NODE);
|
||||
else
|
||||
lpfc_nlp_set_state(vport, ndlp, NLP_STE_UNMAPPED_NODE);
|
||||
|
||||
return 1;
|
||||
}
|
||||
/* Reject this request because invalid parameters */
|
||||
@ -1229,7 +1299,7 @@ lpfc_cmpl_adisc_adisc_issue(struct lpfc_vport *vport,
|
||||
}
|
||||
|
||||
if (phba->sli_rev == LPFC_SLI_REV4) {
|
||||
rc = lpfc_sli4_resume_rpi(ndlp);
|
||||
rc = lpfc_sli4_resume_rpi(ndlp, NULL, NULL);
|
||||
if (rc) {
|
||||
/* Stay in state and retry. */
|
||||
ndlp->nlp_prev_state = NLP_STE_ADISC_ISSUE;
|
||||
|
@ -293,7 +293,9 @@ lpfc_sli4_eq_release(struct lpfc_queue *q, bool arm)
|
||||
}
|
||||
bf_set(lpfc_eqcq_doorbell_num_released, &doorbell, released);
|
||||
bf_set(lpfc_eqcq_doorbell_qt, &doorbell, LPFC_QUEUE_TYPE_EVENT);
|
||||
bf_set(lpfc_eqcq_doorbell_eqid, &doorbell, q->queue_id);
|
||||
bf_set(lpfc_eqcq_doorbell_eqid_hi, &doorbell,
|
||||
(q->queue_id >> LPFC_EQID_HI_FIELD_SHIFT));
|
||||
bf_set(lpfc_eqcq_doorbell_eqid_lo, &doorbell, q->queue_id);
|
||||
writel(doorbell.word0, q->phba->sli4_hba.EQCQDBregaddr);
|
||||
/* PCI read to flush PCI pipeline on re-arming for INTx mode */
|
||||
if ((q->phba->intr_type == INTx) && (arm == LPFC_QUEUE_REARM))
|
||||
@ -372,7 +374,9 @@ lpfc_sli4_cq_release(struct lpfc_queue *q, bool arm)
|
||||
bf_set(lpfc_eqcq_doorbell_arm, &doorbell, 1);
|
||||
bf_set(lpfc_eqcq_doorbell_num_released, &doorbell, released);
|
||||
bf_set(lpfc_eqcq_doorbell_qt, &doorbell, LPFC_QUEUE_TYPE_COMPLETION);
|
||||
bf_set(lpfc_eqcq_doorbell_cqid, &doorbell, q->queue_id);
|
||||
bf_set(lpfc_eqcq_doorbell_cqid_hi, &doorbell,
|
||||
(q->queue_id >> LPFC_CQID_HI_FIELD_SHIFT));
|
||||
bf_set(lpfc_eqcq_doorbell_cqid_lo, &doorbell, q->queue_id);
|
||||
writel(doorbell.word0, q->phba->sli4_hba.EQCQDBregaddr);
|
||||
return released;
|
||||
}
|
||||
@ -5596,6 +5600,8 @@ lpfc_sli4_alloc_resource_identifiers(struct lpfc_hba *phba)
|
||||
for (i = 0; i < count; i++)
|
||||
phba->sli4_hba.rpi_ids[i] = base + i;
|
||||
|
||||
lpfc_sli4_node_prep(phba);
|
||||
|
||||
/* VPIs. */
|
||||
count = phba->sli4_hba.max_cfg_param.max_vpi;
|
||||
base = phba->sli4_hba.max_cfg_param.vpi_base;
|
||||
@ -7555,6 +7561,8 @@ lpfc_sli4_bpl2sgl(struct lpfc_hba *phba, struct lpfc_iocbq *piocbq,
|
||||
|
||||
sgl = (struct sli4_sge *)sglq->sgl;
|
||||
icmd = &piocbq->iocb;
|
||||
if (icmd->ulpCommand == CMD_XMIT_BLS_RSP64_CX)
|
||||
return sglq->sli4_xritag;
|
||||
if (icmd->un.genreq64.bdl.bdeFlags == BUFF_TYPE_BLP_64) {
|
||||
numBdes = icmd->un.genreq64.bdl.bdeSize /
|
||||
sizeof(struct ulp_bde64);
|
||||
@ -7756,6 +7764,7 @@ lpfc_sli4_iocb2wqe(struct lpfc_hba *phba, struct lpfc_iocbq *iocbq,
|
||||
if (if_type == LPFC_SLI_INTF_IF_TYPE_2) {
|
||||
if (pcmd && (*pcmd == ELS_CMD_FLOGI ||
|
||||
*pcmd == ELS_CMD_SCR ||
|
||||
*pcmd == ELS_CMD_FDISC ||
|
||||
*pcmd == ELS_CMD_PLOGI)) {
|
||||
bf_set(els_req64_sp, &wqe->els_req, 1);
|
||||
bf_set(els_req64_sid, &wqe->els_req,
|
||||
@ -7982,6 +7991,7 @@ lpfc_sli4_iocb2wqe(struct lpfc_hba *phba, struct lpfc_iocbq *iocbq,
|
||||
xritag = 0;
|
||||
break;
|
||||
case CMD_XMIT_BLS_RSP64_CX:
|
||||
ndlp = (struct lpfc_nodelist *)iocbq->context1;
|
||||
/* As BLS ABTS RSP WQE is very different from other WQEs,
|
||||
* we re-construct this WQE here based on information in
|
||||
* iocbq from scratch.
|
||||
@ -8008,8 +8018,15 @@ lpfc_sli4_iocb2wqe(struct lpfc_hba *phba, struct lpfc_iocbq *iocbq,
|
||||
}
|
||||
bf_set(xmit_bls_rsp64_seqcnthi, &wqe->xmit_bls_rsp, 0xffff);
|
||||
bf_set(wqe_xmit_bls_pt, &wqe->xmit_bls_rsp.wqe_dest, 0x1);
|
||||
|
||||
/* Use CT=VPI */
|
||||
bf_set(wqe_els_did, &wqe->xmit_bls_rsp.wqe_dest,
|
||||
ndlp->nlp_DID);
|
||||
bf_set(xmit_bls_rsp64_temprpi, &wqe->xmit_bls_rsp,
|
||||
iocbq->iocb.ulpContext);
|
||||
bf_set(wqe_ct, &wqe->xmit_bls_rsp.wqe_com, 1);
|
||||
bf_set(wqe_ctxt_tag, &wqe->xmit_bls_rsp.wqe_com,
|
||||
iocbq->iocb.ulpContext);
|
||||
phba->vpi_ids[phba->pport->vpi]);
|
||||
bf_set(wqe_qosd, &wqe->xmit_bls_rsp.wqe_com, 1);
|
||||
bf_set(wqe_lenloc, &wqe->xmit_bls_rsp.wqe_com,
|
||||
LPFC_WQE_LENLOC_NONE);
|
||||
@ -8073,8 +8090,7 @@ __lpfc_sli_issue_iocb_s4(struct lpfc_hba *phba, uint32_t ring_number,
|
||||
|
||||
if (piocb->sli4_xritag == NO_XRI) {
|
||||
if (piocb->iocb.ulpCommand == CMD_ABORT_XRI_CN ||
|
||||
piocb->iocb.ulpCommand == CMD_CLOSE_XRI_CN ||
|
||||
piocb->iocb.ulpCommand == CMD_XMIT_BLS_RSP64_CX)
|
||||
piocb->iocb.ulpCommand == CMD_CLOSE_XRI_CN)
|
||||
sglq = NULL;
|
||||
else {
|
||||
if (pring->txq_cnt) {
|
||||
@ -8384,10 +8400,13 @@ lpfc_sli4_abts_err_handler(struct lpfc_hba *phba,
|
||||
{
|
||||
struct lpfc_vport *vport;
|
||||
|
||||
if (!ndlp || !NLP_CHK_NODE_ACT(ndlp))
|
||||
if (!ndlp || !NLP_CHK_NODE_ACT(ndlp)) {
|
||||
lpfc_printf_log(phba, KERN_INFO, LOG_SLI,
|
||||
"3115 Node Context not found, driver "
|
||||
"ignoring abts err event\n");
|
||||
return;
|
||||
}
|
||||
|
||||
vport = ndlp->vport;
|
||||
lpfc_printf_log(phba, KERN_WARNING, LOG_SLI,
|
||||
"3116 Port generated FCP XRI ABORT event on "
|
||||
@ -14042,6 +14061,13 @@ lpfc_sli4_seq_abort_rsp_cmpl(struct lpfc_hba *phba,
|
||||
{
|
||||
if (cmd_iocbq)
|
||||
lpfc_sli_release_iocbq(phba, cmd_iocbq);
|
||||
|
||||
/* Failure means BLS ABORT RSP did not get delivered to remote node*/
|
||||
if (rsp_iocbq && rsp_iocbq->iocb.ulpStatus)
|
||||
lpfc_printf_log(phba, KERN_ERR, LOG_SLI,
|
||||
"3154 BLS ABORT RSP failed, data: x%x/x%x\n",
|
||||
rsp_iocbq->iocb.ulpStatus,
|
||||
rsp_iocbq->iocb.un.ulpWord[4]);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -14748,7 +14774,8 @@ lpfc_sli4_remove_rpis(struct lpfc_hba *phba)
|
||||
* provided rpi via a bitmask.
|
||||
**/
|
||||
int
|
||||
lpfc_sli4_resume_rpi(struct lpfc_nodelist *ndlp)
|
||||
lpfc_sli4_resume_rpi(struct lpfc_nodelist *ndlp,
|
||||
void (*cmpl)(struct lpfc_hba *, LPFC_MBOXQ_t *), void *arg)
|
||||
{
|
||||
LPFC_MBOXQ_t *mboxq;
|
||||
struct lpfc_hba *phba = ndlp->phba;
|
||||
@ -14761,6 +14788,12 @@ lpfc_sli4_resume_rpi(struct lpfc_nodelist *ndlp)
|
||||
|
||||
/* Post all rpi memory regions to the port. */
|
||||
lpfc_resume_rpi(mboxq, ndlp);
|
||||
if (cmpl) {
|
||||
mboxq->mbox_cmpl = cmpl;
|
||||
mboxq->context1 = arg;
|
||||
mboxq->context2 = ndlp;
|
||||
}
|
||||
mboxq->vport = ndlp->vport;
|
||||
rc = lpfc_sli_issue_mbox(phba, mboxq, MBX_NOWAIT);
|
||||
if (rc == MBX_NOT_FINISHED) {
|
||||
lpfc_printf_log(phba, KERN_ERR, LOG_SLI,
|
||||
|
@ -633,7 +633,8 @@ void lpfc_sli4_free_rpi(struct lpfc_hba *, int);
|
||||
void lpfc_sli4_remove_rpis(struct lpfc_hba *);
|
||||
void lpfc_sli4_async_event_proc(struct lpfc_hba *);
|
||||
void lpfc_sli4_fcf_redisc_event_proc(struct lpfc_hba *);
|
||||
int lpfc_sli4_resume_rpi(struct lpfc_nodelist *);
|
||||
int lpfc_sli4_resume_rpi(struct lpfc_nodelist *,
|
||||
void (*)(struct lpfc_hba *, LPFC_MBOXQ_t *), void *);
|
||||
void lpfc_sli4_fcp_xri_abort_event_proc(struct lpfc_hba *);
|
||||
void lpfc_sli4_els_xri_abort_event_proc(struct lpfc_hba *);
|
||||
void lpfc_sli4_fcp_xri_aborted(struct lpfc_hba *,
|
||||
|
Loading…
Reference in New Issue
Block a user