0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014
0015
0016
0017
0018
0019
0020
0021
0022
0023
0024 #include <linux/blkdev.h>
0025 #include <linux/pci.h>
0026 #include <linux/slab.h>
0027 #include <linux/interrupt.h>
0028
0029 #include <scsi/scsi.h>
0030 #include <scsi/scsi_device.h>
0031 #include <scsi/scsi_host.h>
0032 #include <scsi/scsi_transport_fc.h>
0033 #include <scsi/fc/fc_fs.h>
0034
0035 #include "lpfc_hw4.h"
0036 #include "lpfc_hw.h"
0037 #include "lpfc_sli.h"
0038 #include "lpfc_sli4.h"
0039 #include "lpfc_nl.h"
0040 #include "lpfc_disc.h"
0041 #include "lpfc.h"
0042 #include "lpfc_scsi.h"
0043 #include "lpfc_nvme.h"
0044 #include "lpfc_logmsg.h"
0045 #include "lpfc_crtn.h"
0046 #include "lpfc_vport.h"
0047 #include "lpfc_debugfs.h"
0048
0049
0050
0051 static int
0052 lpfc_check_adisc(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
0053 struct lpfc_name *nn, struct lpfc_name *pn)
0054 {
0055
0056 if (!(ndlp->nlp_flag & NLP_RPI_REGISTERED))
0057 return 0;
0058
0059
0060
0061
0062 if (memcmp(nn, &ndlp->nlp_nodename, sizeof (struct lpfc_name)))
0063 return 0;
0064
0065 if (memcmp(pn, &ndlp->nlp_portname, sizeof (struct lpfc_name)))
0066 return 0;
0067
0068
0069 return 1;
0070 }
0071
0072 int
0073 lpfc_check_sparm(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
0074 struct serv_parm *sp, uint32_t class, int flogi)
0075 {
0076 volatile struct serv_parm *hsp = &vport->fc_sparam;
0077 uint16_t hsp_value, ssp_value = 0;
0078
0079
0080
0081
0082
0083
0084
0085
0086 if (sp->cls1.classValid) {
0087 if (!flogi) {
0088 hsp_value = ((hsp->cls1.rcvDataSizeMsb << 8) |
0089 hsp->cls1.rcvDataSizeLsb);
0090 ssp_value = ((sp->cls1.rcvDataSizeMsb << 8) |
0091 sp->cls1.rcvDataSizeLsb);
0092 if (!ssp_value)
0093 goto bad_service_param;
0094 if (ssp_value > hsp_value) {
0095 sp->cls1.rcvDataSizeLsb =
0096 hsp->cls1.rcvDataSizeLsb;
0097 sp->cls1.rcvDataSizeMsb =
0098 hsp->cls1.rcvDataSizeMsb;
0099 }
0100 }
0101 } else if (class == CLASS1)
0102 goto bad_service_param;
0103 if (sp->cls2.classValid) {
0104 if (!flogi) {
0105 hsp_value = ((hsp->cls2.rcvDataSizeMsb << 8) |
0106 hsp->cls2.rcvDataSizeLsb);
0107 ssp_value = ((sp->cls2.rcvDataSizeMsb << 8) |
0108 sp->cls2.rcvDataSizeLsb);
0109 if (!ssp_value)
0110 goto bad_service_param;
0111 if (ssp_value > hsp_value) {
0112 sp->cls2.rcvDataSizeLsb =
0113 hsp->cls2.rcvDataSizeLsb;
0114 sp->cls2.rcvDataSizeMsb =
0115 hsp->cls2.rcvDataSizeMsb;
0116 }
0117 }
0118 } else if (class == CLASS2)
0119 goto bad_service_param;
0120 if (sp->cls3.classValid) {
0121 if (!flogi) {
0122 hsp_value = ((hsp->cls3.rcvDataSizeMsb << 8) |
0123 hsp->cls3.rcvDataSizeLsb);
0124 ssp_value = ((sp->cls3.rcvDataSizeMsb << 8) |
0125 sp->cls3.rcvDataSizeLsb);
0126 if (!ssp_value)
0127 goto bad_service_param;
0128 if (ssp_value > hsp_value) {
0129 sp->cls3.rcvDataSizeLsb =
0130 hsp->cls3.rcvDataSizeLsb;
0131 sp->cls3.rcvDataSizeMsb =
0132 hsp->cls3.rcvDataSizeMsb;
0133 }
0134 }
0135 } else if (class == CLASS3)
0136 goto bad_service_param;
0137
0138
0139
0140
0141
0142
0143 hsp_value = (hsp->cmn.bbRcvSizeMsb << 8) | hsp->cmn.bbRcvSizeLsb;
0144 ssp_value = (sp->cmn.bbRcvSizeMsb << 8) | sp->cmn.bbRcvSizeLsb;
0145 if (ssp_value > hsp_value) {
0146 sp->cmn.bbRcvSizeLsb = hsp->cmn.bbRcvSizeLsb;
0147 sp->cmn.bbRcvSizeMsb = (sp->cmn.bbRcvSizeMsb & 0xF0) |
0148 (hsp->cmn.bbRcvSizeMsb & 0x0F);
0149 }
0150
0151 memcpy(&ndlp->nlp_nodename, &sp->nodeName, sizeof (struct lpfc_name));
0152 memcpy(&ndlp->nlp_portname, &sp->portName, sizeof (struct lpfc_name));
0153 return 1;
0154 bad_service_param:
0155 lpfc_printf_vlog(vport, KERN_ERR, LOG_TRACE_EVENT,
0156 "0207 Device %x "
0157 "(%02x:%02x:%02x:%02x:%02x:%02x:%02x:%02x) sent "
0158 "invalid service parameters. Ignoring device.\n",
0159 ndlp->nlp_DID,
0160 sp->nodeName.u.wwn[0], sp->nodeName.u.wwn[1],
0161 sp->nodeName.u.wwn[2], sp->nodeName.u.wwn[3],
0162 sp->nodeName.u.wwn[4], sp->nodeName.u.wwn[5],
0163 sp->nodeName.u.wwn[6], sp->nodeName.u.wwn[7]);
0164 return 0;
0165 }
0166
0167 static void *
0168 lpfc_check_elscmpl_iocb(struct lpfc_hba *phba, struct lpfc_iocbq *cmdiocb,
0169 struct lpfc_iocbq *rspiocb)
0170 {
0171 struct lpfc_dmabuf *pcmd, *prsp;
0172 uint32_t *lp;
0173 void *ptr = NULL;
0174 u32 ulp_status = get_job_ulpstatus(phba, rspiocb);
0175
0176 pcmd = cmdiocb->cmd_dmabuf;
0177
0178
0179
0180
0181 if (pcmd) {
0182 prsp = list_get_first(&pcmd->list, struct lpfc_dmabuf,
0183 list);
0184 if (prsp) {
0185 lp = (uint32_t *) prsp->virt;
0186 ptr = (void *)((uint8_t *)lp + sizeof(uint32_t));
0187 }
0188 } else {
0189
0190 if (!(ulp_status)) {
0191 if (phba->sli_rev == LPFC_SLI_REV4) {
0192 bf_set(lpfc_wcqe_c_status, &rspiocb->wcqe_cmpl,
0193 IOSTAT_LOCAL_REJECT);
0194 rspiocb->wcqe_cmpl.parameter = IOERR_SLI_ABORTED;
0195 } else {
0196 rspiocb->iocb.ulpStatus = IOSTAT_LOCAL_REJECT;
0197 rspiocb->iocb.un.ulpWord[4] = IOERR_SLI_ABORTED;
0198 }
0199 }
0200 ptr = NULL;
0201 }
0202 return ptr;
0203 }
0204
0205
0206
0207
0208
0209
0210
0211
0212 void
0213 lpfc_els_abort(struct lpfc_hba *phba, struct lpfc_nodelist *ndlp)
0214 {
0215 LIST_HEAD(abort_list);
0216 struct lpfc_sli_ring *pring;
0217 struct lpfc_iocbq *iocb, *next_iocb;
0218
0219 pring = lpfc_phba_elsring(phba);
0220
0221
0222 if (unlikely(!pring))
0223 return;
0224
0225
0226 lpfc_printf_vlog(ndlp->vport, KERN_INFO, LOG_DISCOVERY,
0227 "2819 Abort outstanding I/O on NPort x%x "
0228 "Data: x%x x%x x%x\n",
0229 ndlp->nlp_DID, ndlp->nlp_flag, ndlp->nlp_state,
0230 ndlp->nlp_rpi);
0231
0232 lpfc_fabric_abort_nport(ndlp);
0233
0234
0235
0236
0237
0238
0239 spin_lock_irq(&phba->hbalock);
0240 if (phba->sli_rev == LPFC_SLI_REV4)
0241 spin_lock(&pring->ring_lock);
0242 list_for_each_entry_safe(iocb, next_iocb, &pring->txcmplq, list) {
0243
0244 if (lpfc_check_sli_ndlp(phba, pring, iocb, ndlp))
0245 list_add_tail(&iocb->dlist, &abort_list);
0246 }
0247 if (phba->sli_rev == LPFC_SLI_REV4)
0248 spin_unlock(&pring->ring_lock);
0249 spin_unlock_irq(&phba->hbalock);
0250
0251
0252 list_for_each_entry_safe(iocb, next_iocb, &abort_list, dlist) {
0253 spin_lock_irq(&phba->hbalock);
0254 list_del_init(&iocb->dlist);
0255 lpfc_sli_issue_abort_iotag(phba, pring, iocb, NULL);
0256 spin_unlock_irq(&phba->hbalock);
0257 }
0258
0259 lpfc_issue_hb_tmo(phba);
0260
0261 INIT_LIST_HEAD(&abort_list);
0262
0263
0264 spin_lock_irq(&phba->hbalock);
0265 if (phba->sli_rev == LPFC_SLI_REV4)
0266 spin_lock(&pring->ring_lock);
0267
0268 list_for_each_entry_safe(iocb, next_iocb, &pring->txq, list) {
0269
0270 if (lpfc_check_sli_ndlp(phba, pring, iocb, ndlp)) {
0271 list_del_init(&iocb->list);
0272 list_add_tail(&iocb->list, &abort_list);
0273 }
0274 }
0275
0276 if (phba->sli_rev == LPFC_SLI_REV4)
0277 spin_unlock(&pring->ring_lock);
0278 spin_unlock_irq(&phba->hbalock);
0279
0280
0281 lpfc_sli_cancel_iocbs(phba, &abort_list,
0282 IOSTAT_LOCAL_REJECT, IOERR_SLI_ABORTED);
0283
0284 lpfc_cancel_retry_delay_tmo(phba->pport, ndlp);
0285 }
0286
0287
0288
0289
0290
0291
0292
0293 static void
0294 lpfc_defer_plogi_acc(struct lpfc_hba *phba, LPFC_MBOXQ_t *login_mbox)
0295 {
0296 struct lpfc_iocbq *save_iocb;
0297 struct lpfc_nodelist *ndlp;
0298 MAILBOX_t *mb = &login_mbox->u.mb;
0299
0300 int rc;
0301
0302 ndlp = login_mbox->ctx_ndlp;
0303 save_iocb = login_mbox->context3;
0304
0305 if (mb->mbxStatus == MBX_SUCCESS) {
0306
0307
0308
0309 rc = lpfc_els_rsp_acc(login_mbox->vport, ELS_CMD_PLOGI,
0310 save_iocb, ndlp, NULL);
0311 if (rc) {
0312 lpfc_printf_log(phba, KERN_ERR, LOG_TRACE_EVENT,
0313 "4576 PLOGI ACC fails pt2pt discovery: "
0314 "DID %x Data: %x\n", ndlp->nlp_DID, rc);
0315 }
0316 }
0317
0318
0319 lpfc_mbx_cmpl_reg_login(phba, login_mbox);
0320 ndlp->nlp_flag &= ~NLP_ACC_REGLOGIN;
0321 kfree(save_iocb);
0322 }
0323
0324 static int
0325 lpfc_rcv_plogi(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
0326 struct lpfc_iocbq *cmdiocb)
0327 {
0328 struct lpfc_hba *phba = vport->phba;
0329 struct lpfc_dmabuf *pcmd;
0330 uint64_t nlp_portwwn = 0;
0331 uint32_t *lp;
0332 union lpfc_wqe128 *wqe;
0333 IOCB_t *icmd;
0334 struct serv_parm *sp;
0335 uint32_t ed_tov;
0336 LPFC_MBOXQ_t *link_mbox;
0337 LPFC_MBOXQ_t *login_mbox;
0338 struct lpfc_iocbq *save_iocb;
0339 struct ls_rjt stat;
0340 uint32_t vid, flag;
0341 int rc;
0342 u32 remote_did;
0343
0344 memset(&stat, 0, sizeof (struct ls_rjt));
0345 pcmd = cmdiocb->cmd_dmabuf;
0346 lp = (uint32_t *) pcmd->virt;
0347 sp = (struct serv_parm *) ((uint8_t *) lp + sizeof (uint32_t));
0348 if (wwn_to_u64(sp->portName.u.wwn) == 0) {
0349 lpfc_printf_vlog(vport, KERN_ERR, LOG_TRACE_EVENT,
0350 "0140 PLOGI Reject: invalid pname\n");
0351 stat.un.b.lsRjtRsnCode = LSRJT_UNABLE_TPC;
0352 stat.un.b.lsRjtRsnCodeExp = LSEXP_INVALID_PNAME;
0353 lpfc_els_rsp_reject(vport, stat.un.lsRjtError, cmdiocb, ndlp,
0354 NULL);
0355 return 0;
0356 }
0357 if (wwn_to_u64(sp->nodeName.u.wwn) == 0) {
0358 lpfc_printf_vlog(vport, KERN_ERR, LOG_TRACE_EVENT,
0359 "0141 PLOGI Reject: invalid nname\n");
0360 stat.un.b.lsRjtRsnCode = LSRJT_UNABLE_TPC;
0361 stat.un.b.lsRjtRsnCodeExp = LSEXP_INVALID_NNAME;
0362 lpfc_els_rsp_reject(vport, stat.un.lsRjtError, cmdiocb, ndlp,
0363 NULL);
0364 return 0;
0365 }
0366
0367 nlp_portwwn = wwn_to_u64(ndlp->nlp_portname.u.wwn);
0368 if ((lpfc_check_sparm(vport, ndlp, sp, CLASS3, 0) == 0)) {
0369
0370 stat.un.b.lsRjtRsnCode = LSRJT_UNABLE_TPC;
0371 stat.un.b.lsRjtRsnCodeExp = LSEXP_SPARM_OPTIONS;
0372 lpfc_els_rsp_reject(vport, stat.un.lsRjtError, cmdiocb, ndlp,
0373 NULL);
0374 return 0;
0375 }
0376
0377 if (phba->sli_rev == LPFC_SLI_REV4)
0378 wqe = &cmdiocb->wqe;
0379 else
0380 icmd = &cmdiocb->iocb;
0381
0382
0383 lpfc_printf_vlog(vport, KERN_INFO, LOG_ELS,
0384 "0114 PLOGI chkparm OK Data: x%x x%x x%x "
0385 "x%x x%x x%x\n",
0386 ndlp->nlp_DID, ndlp->nlp_state, ndlp->nlp_flag,
0387 ndlp->nlp_rpi, vport->port_state,
0388 vport->fc_flag);
0389
0390 if (vport->cfg_fcp_class == 2 && sp->cls2.classValid)
0391 ndlp->nlp_fcp_info |= CLASS2;
0392 else
0393 ndlp->nlp_fcp_info |= CLASS3;
0394
0395 ndlp->nlp_class_sup = 0;
0396 if (sp->cls1.classValid)
0397 ndlp->nlp_class_sup |= FC_COS_CLASS1;
0398 if (sp->cls2.classValid)
0399 ndlp->nlp_class_sup |= FC_COS_CLASS2;
0400 if (sp->cls3.classValid)
0401 ndlp->nlp_class_sup |= FC_COS_CLASS3;
0402 if (sp->cls4.classValid)
0403 ndlp->nlp_class_sup |= FC_COS_CLASS4;
0404 ndlp->nlp_maxframe =
0405 ((sp->cmn.bbRcvSizeMsb & 0x0F) << 8) | sp->cmn.bbRcvSizeLsb;
0406
0407 switch (ndlp->nlp_state) {
0408 case NLP_STE_NPR_NODE:
0409 if (!(ndlp->nlp_flag & NLP_NPR_ADISC))
0410 break;
0411 fallthrough;
0412 case NLP_STE_REG_LOGIN_ISSUE:
0413 case NLP_STE_PRLI_ISSUE:
0414 case NLP_STE_UNMAPPED_NODE:
0415 case NLP_STE_MAPPED_NODE:
0416
0417
0418
0419
0420 if (!(ndlp->nlp_type & NLP_FABRIC) &&
0421 !(phba->nvmet_support)) {
0422
0423
0424
0425 ndlp->nlp_type &= ~(NLP_FCP_TARGET | NLP_FCP_INITIATOR);
0426 ndlp->nlp_type &= ~(NLP_NVME_TARGET | NLP_NVME_INITIATOR);
0427 ndlp->nlp_fcp_info &= ~NLP_FCP_2_DEVICE;
0428 ndlp->nlp_nvme_info &= ~NLP_NVME_NSLER;
0429 ndlp->nlp_flag &= ~NLP_FIRSTBURST;
0430
0431 lpfc_els_rsp_acc(vport, ELS_CMD_PLOGI, cmdiocb,
0432 ndlp, NULL);
0433 return 1;
0434 }
0435 if (nlp_portwwn != 0 &&
0436 nlp_portwwn != wwn_to_u64(sp->portName.u.wwn))
0437 lpfc_printf_vlog(vport, KERN_ERR, LOG_TRACE_EVENT,
0438 "0143 PLOGI recv'd from DID: x%x "
0439 "WWPN changed: old %llx new %llx\n",
0440 ndlp->nlp_DID,
0441 (unsigned long long)nlp_portwwn,
0442 (unsigned long long)
0443 wwn_to_u64(sp->portName.u.wwn));
0444
0445
0446 if (phba->nvmet_support &&
0447 ndlp->nlp_state == NLP_STE_UNMAPPED_NODE)
0448 lpfc_nvmet_invalidate_host(phba, ndlp);
0449
0450 ndlp->nlp_prev_state = ndlp->nlp_state;
0451
0452 lpfc_nlp_set_state(vport, ndlp, NLP_STE_NPR_NODE);
0453 break;
0454 }
0455
0456 ndlp->nlp_type &= ~(NLP_FCP_TARGET | NLP_FCP_INITIATOR);
0457 ndlp->nlp_type &= ~(NLP_NVME_TARGET | NLP_NVME_INITIATOR);
0458 ndlp->nlp_fcp_info &= ~NLP_FCP_2_DEVICE;
0459 ndlp->nlp_nvme_info &= ~NLP_NVME_NSLER;
0460 ndlp->nlp_flag &= ~NLP_FIRSTBURST;
0461
0462 login_mbox = NULL;
0463 link_mbox = NULL;
0464 save_iocb = NULL;
0465
0466
0467 if ((vport->fc_flag & FC_PT2PT) &&
0468 !(vport->fc_flag & FC_PT2PT_PLOGI)) {
0469
0470 if (phba->sli_rev == LPFC_SLI_REV4) {
0471 vport->fc_myDID = bf_get(els_rsp64_sid,
0472 &cmdiocb->wqe.xmit_els_rsp);
0473 } else {
0474 vport->fc_myDID = icmd->un.rcvels.parmRo;
0475 }
0476
0477
0478
0479
0480
0481
0482
0483
0484 if (phba->hba_flag & HBA_FLOGI_OUTSTANDING)
0485 lpfc_els_abort_flogi(phba);
0486
0487 ed_tov = be32_to_cpu(sp->cmn.e_d_tov);
0488 if (sp->cmn.edtovResolution) {
0489
0490 ed_tov = (phba->fc_edtov + 999999) / 1000000;
0491 }
0492
0493
0494
0495
0496
0497 if (ed_tov > phba->fc_edtov)
0498 phba->fc_edtov = ed_tov;
0499 phba->fc_ratov = (2 * phba->fc_edtov) / 1000;
0500
0501 memcpy(&phba->fc_fabparam, sp, sizeof(struct serv_parm));
0502
0503
0504
0505
0506 if (phba->sli_rev == LPFC_SLI_REV4)
0507 lpfc_issue_reg_vfi(vport);
0508 else {
0509 link_mbox = mempool_alloc(phba->mbox_mem_pool,
0510 GFP_KERNEL);
0511 if (!link_mbox)
0512 goto out;
0513 lpfc_config_link(phba, link_mbox);
0514 link_mbox->mbox_cmpl = lpfc_sli_def_mbox_cmpl;
0515 link_mbox->vport = vport;
0516
0517
0518
0519
0520 link_mbox->ctx_ndlp = ndlp;
0521
0522 rc = lpfc_sli_issue_mbox(phba, link_mbox, MBX_NOWAIT);
0523 if (rc == MBX_NOT_FINISHED) {
0524 mempool_free(link_mbox, phba->mbox_mem_pool);
0525 goto out;
0526 }
0527 }
0528
0529 lpfc_can_disctmo(vport);
0530 }
0531
0532 ndlp->nlp_flag &= ~NLP_SUPPRESS_RSP;
0533 if ((phba->sli.sli_flag & LPFC_SLI_SUPPRESS_RSP) &&
0534 sp->cmn.valid_vendor_ver_level) {
0535 vid = be32_to_cpu(sp->un.vv.vid);
0536 flag = be32_to_cpu(sp->un.vv.flags);
0537 if ((vid == LPFC_VV_EMLX_ID) && (flag & LPFC_VV_SUPPRESS_RSP))
0538 ndlp->nlp_flag |= NLP_SUPPRESS_RSP;
0539 }
0540
0541 login_mbox = mempool_alloc(phba->mbox_mem_pool, GFP_KERNEL);
0542 if (!login_mbox)
0543 goto out;
0544
0545 save_iocb = kzalloc(sizeof(*save_iocb), GFP_KERNEL);
0546 if (!save_iocb)
0547 goto out;
0548
0549
0550 memcpy((uint8_t *)save_iocb, (uint8_t *)cmdiocb,
0551 sizeof(struct lpfc_iocbq));
0552
0553
0554 if (phba->sli_rev == LPFC_SLI_REV4)
0555 lpfc_unreg_rpi(vport, ndlp);
0556
0557
0558
0559
0560 if (phba->sli_rev == LPFC_SLI_REV4)
0561 remote_did = bf_get(wqe_els_did, &wqe->xmit_els_rsp.wqe_dest);
0562 else
0563 remote_did = icmd->un.rcvels.remoteID;
0564 rc = lpfc_reg_rpi(phba, vport->vpi, remote_did,
0565 (uint8_t *)sp, login_mbox, ndlp->nlp_rpi);
0566 if (rc)
0567 goto out;
0568
0569 login_mbox->mbox_cmpl = lpfc_mbx_cmpl_reg_login;
0570 login_mbox->vport = vport;
0571
0572
0573
0574
0575
0576
0577
0578
0579
0580
0581
0582 if ((ndlp->nlp_state == NLP_STE_PLOGI_ISSUE) &&
0583 (vport->fc_flag & FC_FABRIC)) {
0584
0585 lpfc_els_abort(phba, ndlp);
0586 }
0587
0588 if ((vport->port_type == LPFC_NPIV_PORT &&
0589 vport->cfg_restrict_login)) {
0590
0591
0592 kfree(save_iocb);
0593
0594
0595
0596
0597 if (phba->sli_rev == LPFC_SLI_REV4) {
0598 lpfc_mbox_rsrc_cleanup(phba, login_mbox,
0599 MBOX_THD_UNLOCKED);
0600 login_mbox = NULL;
0601 } else {
0602
0603
0604
0605
0606
0607 spin_lock_irq(&ndlp->lock);
0608 ndlp->nlp_flag |= (NLP_RM_DFLT_RPI | NLP_ACC_REGLOGIN |
0609 NLP_RCV_PLOGI);
0610 spin_unlock_irq(&ndlp->lock);
0611 }
0612
0613 stat.un.b.lsRjtRsnCode = LSRJT_INVALID_CMD;
0614 stat.un.b.lsRjtRsnCodeExp = LSEXP_NOTHING_MORE;
0615 rc = lpfc_els_rsp_reject(vport, stat.un.lsRjtError, cmdiocb,
0616 ndlp, login_mbox);
0617 if (rc && login_mbox)
0618 lpfc_mbox_rsrc_cleanup(phba, login_mbox,
0619 MBOX_THD_UNLOCKED);
0620 return 1;
0621 }
0622
0623
0624
0625
0626
0627
0628
0629
0630
0631
0632
0633
0634
0635
0636
0637
0638 login_mbox->mbox_cmpl = lpfc_defer_plogi_acc;
0639 login_mbox->ctx_ndlp = lpfc_nlp_get(ndlp);
0640 if (!login_mbox->ctx_ndlp)
0641 goto out;
0642
0643 login_mbox->context3 = save_iocb;
0644
0645 spin_lock_irq(&ndlp->lock);
0646 ndlp->nlp_flag |= (NLP_ACC_REGLOGIN | NLP_RCV_PLOGI);
0647 spin_unlock_irq(&ndlp->lock);
0648
0649
0650 rc = lpfc_sli_issue_mbox(phba, login_mbox, MBX_NOWAIT);
0651 if (rc == MBX_NOT_FINISHED) {
0652 lpfc_nlp_put(ndlp);
0653 goto out;
0654 }
0655 lpfc_nlp_set_state(vport, ndlp, NLP_STE_REG_LOGIN_ISSUE);
0656
0657 return 1;
0658 out:
0659 kfree(save_iocb);
0660 if (login_mbox)
0661 mempool_free(login_mbox, phba->mbox_mem_pool);
0662
0663 stat.un.b.lsRjtRsnCode = LSRJT_UNABLE_TPC;
0664 stat.un.b.lsRjtRsnCodeExp = LSEXP_OUT_OF_RESOURCE;
0665 lpfc_els_rsp_reject(vport, stat.un.lsRjtError, cmdiocb, ndlp, NULL);
0666 return 0;
0667 }
0668
0669
0670
0671
0672
0673
0674
0675
0676
0677 static void
0678 lpfc_mbx_cmpl_resume_rpi(struct lpfc_hba *phba, LPFC_MBOXQ_t *mboxq)
0679 {
0680 struct lpfc_vport *vport;
0681 struct lpfc_iocbq *elsiocb;
0682 struct lpfc_nodelist *ndlp;
0683 uint32_t cmd;
0684
0685 elsiocb = (struct lpfc_iocbq *)mboxq->ctx_buf;
0686 ndlp = (struct lpfc_nodelist *)mboxq->ctx_ndlp;
0687 vport = mboxq->vport;
0688 cmd = elsiocb->drvrTimeout;
0689
0690 if (cmd == ELS_CMD_ADISC) {
0691 lpfc_els_rsp_adisc_acc(vport, elsiocb, ndlp);
0692 } else {
0693 lpfc_els_rsp_acc(vport, ELS_CMD_PLOGI, elsiocb,
0694 ndlp, NULL);
0695 }
0696
0697
0698 lpfc_nlp_put(ndlp);
0699
0700 kfree(elsiocb);
0701 mempool_free(mboxq, phba->mbox_mem_pool);
0702 }
0703
0704 static int
0705 lpfc_rcv_padisc(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
0706 struct lpfc_iocbq *cmdiocb)
0707 {
0708 struct lpfc_hba *phba = vport->phba;
0709 struct lpfc_iocbq *elsiocb;
0710 struct lpfc_dmabuf *pcmd;
0711 struct serv_parm *sp;
0712 struct lpfc_name *pnn, *ppn;
0713 struct ls_rjt stat;
0714 ADISC *ap;
0715 uint32_t *lp;
0716 uint32_t cmd;
0717
0718 pcmd = cmdiocb->cmd_dmabuf;
0719 lp = (uint32_t *) pcmd->virt;
0720
0721 cmd = *lp++;
0722 if (cmd == ELS_CMD_ADISC) {
0723 ap = (ADISC *) lp;
0724 pnn = (struct lpfc_name *) & ap->nodeName;
0725 ppn = (struct lpfc_name *) & ap->portName;
0726 } else {
0727 sp = (struct serv_parm *) lp;
0728 pnn = (struct lpfc_name *) & sp->nodeName;
0729 ppn = (struct lpfc_name *) & sp->portName;
0730 }
0731
0732 if (get_job_ulpstatus(phba, cmdiocb) == 0 &&
0733 lpfc_check_adisc(vport, ndlp, pnn, ppn)) {
0734
0735
0736
0737
0738
0739
0740 if (vport->phba->sli_rev == LPFC_SLI_REV4) {
0741 elsiocb = kmalloc(sizeof(struct lpfc_iocbq),
0742 GFP_KERNEL);
0743 if (elsiocb) {
0744
0745 memcpy((uint8_t *)elsiocb, (uint8_t *)cmdiocb,
0746 sizeof(struct lpfc_iocbq));
0747
0748
0749 elsiocb->drvrTimeout = cmd;
0750
0751 lpfc_sli4_resume_rpi(ndlp,
0752 lpfc_mbx_cmpl_resume_rpi, elsiocb);
0753 goto out;
0754 }
0755 }
0756
0757 if (cmd == ELS_CMD_ADISC) {
0758 lpfc_els_rsp_adisc_acc(vport, cmdiocb, ndlp);
0759 } else {
0760 lpfc_els_rsp_acc(vport, ELS_CMD_PLOGI, cmdiocb,
0761 ndlp, NULL);
0762 }
0763 out:
0764
0765
0766
0767
0768
0769
0770
0771
0772
0773 if (ndlp->nlp_type & (NLP_FCP_TARGET | NLP_NVME_TARGET)) {
0774 if ((ndlp->nlp_state != NLP_STE_MAPPED_NODE) &&
0775 !(ndlp->nlp_flag & NLP_NPR_ADISC))
0776 lpfc_nlp_set_state(vport, ndlp,
0777 NLP_STE_MAPPED_NODE);
0778 }
0779
0780 return 1;
0781 }
0782
0783 stat.un.b.lsRjtRsvd0 = 0;
0784 stat.un.b.lsRjtRsnCode = LSRJT_UNABLE_TPC;
0785 stat.un.b.lsRjtRsnCodeExp = LSEXP_SPARM_OPTIONS;
0786 stat.un.b.vendorUnique = 0;
0787 lpfc_els_rsp_reject(vport, stat.un.lsRjtError, cmdiocb, ndlp, NULL);
0788
0789
0790 mod_timer(&ndlp->nlp_delayfunc, jiffies + msecs_to_jiffies(1000));
0791
0792 spin_lock_irq(&ndlp->lock);
0793 ndlp->nlp_flag |= NLP_DELAY_TMO;
0794 spin_unlock_irq(&ndlp->lock);
0795 ndlp->nlp_last_elscmd = ELS_CMD_PLOGI;
0796 ndlp->nlp_prev_state = ndlp->nlp_state;
0797 lpfc_nlp_set_state(vport, ndlp, NLP_STE_NPR_NODE);
0798 return 0;
0799 }
0800
0801 static int
0802 lpfc_rcv_logo(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
0803 struct lpfc_iocbq *cmdiocb, uint32_t els_cmd)
0804 {
0805 struct Scsi_Host *shost = lpfc_shost_from_vport(vport);
0806 struct lpfc_hba *phba = vport->phba;
0807 struct lpfc_vport **vports;
0808 int i, active_vlink_present = 0 ;
0809
0810
0811
0812
0813
0814 spin_lock_irq(&ndlp->lock);
0815 ndlp->nlp_flag |= NLP_LOGO_ACC;
0816 spin_unlock_irq(&ndlp->lock);
0817 if (els_cmd == ELS_CMD_PRLO)
0818 lpfc_els_rsp_acc(vport, ELS_CMD_PRLO, cmdiocb, ndlp, NULL);
0819 else
0820 lpfc_els_rsp_acc(vport, ELS_CMD_ACC, cmdiocb, ndlp, NULL);
0821
0822
0823
0824
0825
0826
0827 if (ndlp->nlp_type & NLP_FABRIC &&
0828 ((ndlp->nlp_DID & WELL_KNOWN_DID_MASK) != WELL_KNOWN_DID_MASK))
0829 return 0;
0830
0831
0832 if (phba->nvmet_support &&
0833 ndlp->nlp_state == NLP_STE_UNMAPPED_NODE)
0834 lpfc_nvmet_invalidate_host(phba, ndlp);
0835
0836 if (ndlp->nlp_DID == Fabric_DID) {
0837 if (vport->port_state <= LPFC_FDISC ||
0838 vport->fc_flag & FC_PT2PT)
0839 goto out;
0840 lpfc_linkdown_port(vport);
0841 spin_lock_irq(shost->host_lock);
0842 vport->fc_flag |= FC_VPORT_LOGO_RCVD;
0843 spin_unlock_irq(shost->host_lock);
0844 vports = lpfc_create_vport_work_array(phba);
0845 if (vports) {
0846 for (i = 0; i <= phba->max_vports && vports[i] != NULL;
0847 i++) {
0848 if ((!(vports[i]->fc_flag &
0849 FC_VPORT_LOGO_RCVD)) &&
0850 (vports[i]->port_state > LPFC_FDISC)) {
0851 active_vlink_present = 1;
0852 break;
0853 }
0854 }
0855 lpfc_destroy_vport_work_array(phba, vports);
0856 }
0857
0858
0859
0860
0861
0862
0863 if (!(vport->load_flag & FC_UNLOADING) &&
0864 active_vlink_present) {
0865
0866
0867
0868
0869 mod_timer(&ndlp->nlp_delayfunc,
0870 jiffies + msecs_to_jiffies(1000));
0871 spin_lock_irq(&ndlp->lock);
0872 ndlp->nlp_flag |= NLP_DELAY_TMO;
0873 spin_unlock_irq(&ndlp->lock);
0874 ndlp->nlp_last_elscmd = ELS_CMD_FDISC;
0875 vport->port_state = LPFC_FDISC;
0876 } else {
0877 spin_lock_irq(shost->host_lock);
0878 phba->pport->fc_flag &= ~FC_LOGO_RCVD_DID_CHNG;
0879 spin_unlock_irq(shost->host_lock);
0880 lpfc_retry_pport_discovery(phba);
0881 }
0882 } else if ((!(ndlp->nlp_type & NLP_FABRIC) &&
0883 ((ndlp->nlp_type & NLP_FCP_TARGET) ||
0884 (ndlp->nlp_type & NLP_NVME_TARGET) ||
0885 (vport->fc_flag & FC_PT2PT))) ||
0886 (ndlp->nlp_state == NLP_STE_ADISC_ISSUE)) {
0887
0888
0889
0890
0891
0892 mod_timer(&ndlp->nlp_delayfunc,
0893 jiffies + msecs_to_jiffies(1000 * 1));
0894 spin_lock_irq(&ndlp->lock);
0895 ndlp->nlp_flag |= NLP_DELAY_TMO;
0896 spin_unlock_irq(&ndlp->lock);
0897
0898 ndlp->nlp_last_elscmd = ELS_CMD_PLOGI;
0899 }
0900 out:
0901
0902 lpfc_nlp_unreg_node(vport, ndlp);
0903
0904 ndlp->nlp_prev_state = ndlp->nlp_state;
0905 lpfc_nlp_set_state(vport, ndlp, NLP_STE_NPR_NODE);
0906
0907 spin_lock_irq(&ndlp->lock);
0908 ndlp->nlp_flag &= ~NLP_NPR_ADISC;
0909 spin_unlock_irq(&ndlp->lock);
0910
0911
0912
0913
0914
0915 return 0;
0916 }
0917
0918 static uint32_t
0919 lpfc_rcv_prli_support_check(struct lpfc_vport *vport,
0920 struct lpfc_nodelist *ndlp,
0921 struct lpfc_iocbq *cmdiocb)
0922 {
0923 struct ls_rjt stat;
0924 uint32_t *payload;
0925 uint32_t cmd;
0926
0927 payload = cmdiocb->cmd_dmabuf->virt;
0928 cmd = *payload;
0929 if (vport->phba->nvmet_support) {
0930
0931 if (cmd == ELS_CMD_PRLI)
0932 goto out;
0933 } else {
0934
0935 if (!vport->nvmei_support && (cmd == ELS_CMD_NVMEPRLI))
0936 goto out;
0937 }
0938 return 1;
0939 out:
0940 lpfc_printf_vlog(vport, KERN_WARNING, LOG_NVME_DISC,
0941 "6115 Rcv PRLI (%x) check failed: ndlp rpi %d "
0942 "state x%x flags x%x\n",
0943 cmd, ndlp->nlp_rpi, ndlp->nlp_state,
0944 ndlp->nlp_flag);
0945 memset(&stat, 0, sizeof(struct ls_rjt));
0946 stat.un.b.lsRjtRsnCode = LSRJT_CMD_UNSUPPORTED;
0947 stat.un.b.lsRjtRsnCodeExp = LSEXP_REQ_UNSUPPORTED;
0948 lpfc_els_rsp_reject(vport, stat.un.lsRjtError, cmdiocb,
0949 ndlp, NULL);
0950 return 0;
0951 }
0952
0953 static void
0954 lpfc_rcv_prli(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
0955 struct lpfc_iocbq *cmdiocb)
0956 {
0957 struct lpfc_hba *phba = vport->phba;
0958 struct lpfc_dmabuf *pcmd;
0959 uint32_t *lp;
0960 PRLI *npr;
0961 struct fc_rport *rport = ndlp->rport;
0962 u32 roles;
0963
0964 pcmd = cmdiocb->cmd_dmabuf;
0965 lp = (uint32_t *)pcmd->virt;
0966 npr = (PRLI *)((uint8_t *)lp + sizeof(uint32_t));
0967
0968 if ((npr->prliType == PRLI_FCP_TYPE) ||
0969 (npr->prliType == PRLI_NVME_TYPE)) {
0970 if (npr->initiatorFunc) {
0971 if (npr->prliType == PRLI_FCP_TYPE)
0972 ndlp->nlp_type |= NLP_FCP_INITIATOR;
0973 if (npr->prliType == PRLI_NVME_TYPE)
0974 ndlp->nlp_type |= NLP_NVME_INITIATOR;
0975 }
0976 if (npr->targetFunc) {
0977 if (npr->prliType == PRLI_FCP_TYPE)
0978 ndlp->nlp_type |= NLP_FCP_TARGET;
0979 if (npr->prliType == PRLI_NVME_TYPE)
0980 ndlp->nlp_type |= NLP_NVME_TARGET;
0981 if (npr->writeXferRdyDis)
0982 ndlp->nlp_flag |= NLP_FIRSTBURST;
0983 }
0984 if (npr->Retry && ndlp->nlp_type &
0985 (NLP_FCP_INITIATOR | NLP_FCP_TARGET))
0986 ndlp->nlp_fcp_info |= NLP_FCP_2_DEVICE;
0987
0988 if (npr->Retry && phba->nsler &&
0989 ndlp->nlp_type & (NLP_NVME_INITIATOR | NLP_NVME_TARGET))
0990 ndlp->nlp_nvme_info |= NLP_NVME_NSLER;
0991
0992
0993
0994
0995
0996
0997
0998 if (phba->nvmet_support && (npr->prliType == PRLI_NVME_TYPE)) {
0999 ndlp->nlp_fc4_type |= NLP_FC4_NVME;
1000 lpfc_nlp_set_state(vport, ndlp, NLP_STE_UNMAPPED_NODE);
1001 }
1002
1003
1004
1005
1006 if (npr->prliType == PRLI_FCP_TYPE &&
1007 !(ndlp->nlp_type & NLP_FABRIC))
1008 ndlp->nlp_fc4_type |= NLP_FC4_FCP;
1009 }
1010 if (rport) {
1011
1012 roles = FC_RPORT_ROLE_UNKNOWN;
1013 if (ndlp->nlp_type & NLP_FCP_INITIATOR)
1014 roles |= FC_RPORT_ROLE_FCP_INITIATOR;
1015 if (ndlp->nlp_type & NLP_FCP_TARGET)
1016 roles |= FC_RPORT_ROLE_FCP_TARGET;
1017
1018 lpfc_debugfs_disc_trc(vport, LPFC_DISC_TRC_RPORT,
1019 "rport rolechg: role:x%x did:x%x flg:x%x",
1020 roles, ndlp->nlp_DID, ndlp->nlp_flag);
1021
1022 if (vport->cfg_enable_fc4_type != LPFC_ENABLE_NVME)
1023 fc_remote_port_rolechg(rport, roles);
1024 }
1025 }
1026
1027 static uint32_t
1028 lpfc_disc_set_adisc(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp)
1029 {
1030 if (!(ndlp->nlp_flag & NLP_RPI_REGISTERED)) {
1031 spin_lock_irq(&ndlp->lock);
1032 ndlp->nlp_flag &= ~NLP_NPR_ADISC;
1033 spin_unlock_irq(&ndlp->lock);
1034 return 0;
1035 }
1036
1037 if (!(vport->fc_flag & FC_PT2PT)) {
1038
1039 if (vport->cfg_use_adisc && ((vport->fc_flag & FC_RSCN_MODE) ||
1040 ((ndlp->nlp_fcp_info & NLP_FCP_2_DEVICE) &&
1041 (ndlp->nlp_type & NLP_FCP_TARGET)))) {
1042 spin_lock_irq(&ndlp->lock);
1043 ndlp->nlp_flag |= NLP_NPR_ADISC;
1044 spin_unlock_irq(&ndlp->lock);
1045 return 1;
1046 }
1047 }
1048
1049 spin_lock_irq(&ndlp->lock);
1050 ndlp->nlp_flag &= ~NLP_NPR_ADISC;
1051 spin_unlock_irq(&ndlp->lock);
1052 lpfc_unreg_rpi(vport, ndlp);
1053 return 0;
1054 }
1055
1056
1057
1058
1059
1060
1061
1062
1063
1064
1065
1066 static void
1067 lpfc_release_rpi(struct lpfc_hba *phba, struct lpfc_vport *vport,
1068 struct lpfc_nodelist *ndlp, uint16_t rpi)
1069 {
1070 LPFC_MBOXQ_t *pmb;
1071 int rc;
1072
1073
1074
1075
1076 if (ndlp->nlp_flag & NLP_UNREG_INP) {
1077 lpfc_printf_vlog(vport, KERN_INFO, LOG_DISCOVERY,
1078 "1435 release_rpi SKIP UNREG x%x on "
1079 "NPort x%x deferred x%x flg x%x "
1080 "Data: x%px\n",
1081 ndlp->nlp_rpi, ndlp->nlp_DID,
1082 ndlp->nlp_defer_did,
1083 ndlp->nlp_flag, ndlp);
1084 return;
1085 }
1086
1087 pmb = (LPFC_MBOXQ_t *) mempool_alloc(phba->mbox_mem_pool,
1088 GFP_KERNEL);
1089 if (!pmb)
1090 lpfc_printf_vlog(vport, KERN_ERR, LOG_TRACE_EVENT,
1091 "2796 mailbox memory allocation failed \n");
1092 else {
1093 lpfc_unreg_login(phba, vport->vpi, rpi, pmb);
1094 pmb->mbox_cmpl = lpfc_sli_def_mbox_cmpl;
1095 pmb->vport = vport;
1096 pmb->ctx_ndlp = lpfc_nlp_get(ndlp);
1097 if (!pmb->ctx_ndlp) {
1098 mempool_free(pmb, phba->mbox_mem_pool);
1099 return;
1100 }
1101
1102 if (((ndlp->nlp_DID & Fabric_DID_MASK) != Fabric_DID_MASK) &&
1103 (!(vport->fc_flag & FC_OFFLINE_MODE)))
1104 ndlp->nlp_flag |= NLP_UNREG_INP;
1105
1106 lpfc_printf_vlog(vport, KERN_INFO, LOG_DISCOVERY,
1107 "1437 release_rpi UNREG x%x "
1108 "on NPort x%x flg x%x\n",
1109 ndlp->nlp_rpi, ndlp->nlp_DID, ndlp->nlp_flag);
1110
1111 rc = lpfc_sli_issue_mbox(phba, pmb, MBX_NOWAIT);
1112 if (rc == MBX_NOT_FINISHED) {
1113 lpfc_nlp_put(ndlp);
1114 mempool_free(pmb, phba->mbox_mem_pool);
1115 }
1116 }
1117 }
1118
1119 static uint32_t
1120 lpfc_disc_illegal(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
1121 void *arg, uint32_t evt)
1122 {
1123 struct lpfc_hba *phba;
1124 LPFC_MBOXQ_t *pmb = (LPFC_MBOXQ_t *) arg;
1125 uint16_t rpi;
1126
1127 phba = vport->phba;
1128
1129 if (!(phba->pport->load_flag & FC_UNLOADING) &&
1130 (evt == NLP_EVT_CMPL_REG_LOGIN) &&
1131 (!pmb->u.mb.mbxStatus)) {
1132 rpi = pmb->u.mb.un.varWords[0];
1133 lpfc_release_rpi(phba, vport, ndlp, rpi);
1134 }
1135 lpfc_printf_vlog(vport, KERN_ERR, LOG_TRACE_EVENT,
1136 "0271 Illegal State Transition: node x%x "
1137 "event x%x, state x%x Data: x%x x%x\n",
1138 ndlp->nlp_DID, evt, ndlp->nlp_state, ndlp->nlp_rpi,
1139 ndlp->nlp_flag);
1140 return ndlp->nlp_state;
1141 }
1142
1143 static uint32_t
1144 lpfc_cmpl_plogi_illegal(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
1145 void *arg, uint32_t evt)
1146 {
1147
1148
1149
1150
1151
1152 if (!(ndlp->nlp_flag & NLP_RCV_PLOGI)) {
1153 lpfc_printf_vlog(vport, KERN_ERR, LOG_TRACE_EVENT,
1154 "0272 Illegal State Transition: node x%x "
1155 "event x%x, state x%x Data: x%x x%x\n",
1156 ndlp->nlp_DID, evt, ndlp->nlp_state,
1157 ndlp->nlp_rpi, ndlp->nlp_flag);
1158 }
1159 return ndlp->nlp_state;
1160 }
1161
1162
1163
1164 static uint32_t
1165 lpfc_rcv_plogi_unused_node(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
1166 void *arg, uint32_t evt)
1167 {
1168 struct lpfc_iocbq *cmdiocb;
1169
1170 cmdiocb = (struct lpfc_iocbq *) arg;
1171
1172 if (lpfc_rcv_plogi(vport, ndlp, cmdiocb)) {
1173 return ndlp->nlp_state;
1174 }
1175 return NLP_STE_FREED_NODE;
1176 }
1177
1178 static uint32_t
1179 lpfc_rcv_els_unused_node(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
1180 void *arg, uint32_t evt)
1181 {
1182 lpfc_issue_els_logo(vport, ndlp, 0);
1183 return ndlp->nlp_state;
1184 }
1185
1186 static uint32_t
1187 lpfc_rcv_logo_unused_node(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
1188 void *arg, uint32_t evt)
1189 {
1190 struct lpfc_iocbq *cmdiocb = (struct lpfc_iocbq *) arg;
1191
1192 spin_lock_irq(&ndlp->lock);
1193 ndlp->nlp_flag |= NLP_LOGO_ACC;
1194 spin_unlock_irq(&ndlp->lock);
1195 lpfc_els_rsp_acc(vport, ELS_CMD_ACC, cmdiocb, ndlp, NULL);
1196
1197 return ndlp->nlp_state;
1198 }
1199
1200 static uint32_t
1201 lpfc_cmpl_logo_unused_node(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
1202 void *arg, uint32_t evt)
1203 {
1204 return NLP_STE_FREED_NODE;
1205 }
1206
1207 static uint32_t
1208 lpfc_device_rm_unused_node(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
1209 void *arg, uint32_t evt)
1210 {
1211 return NLP_STE_FREED_NODE;
1212 }
1213
1214 static uint32_t
1215 lpfc_device_recov_unused_node(struct lpfc_vport *vport,
1216 struct lpfc_nodelist *ndlp,
1217 void *arg, uint32_t evt)
1218 {
1219 return ndlp->nlp_state;
1220 }
1221
1222 static uint32_t
1223 lpfc_rcv_plogi_plogi_issue(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
1224 void *arg, uint32_t evt)
1225 {
1226 struct Scsi_Host *shost = lpfc_shost_from_vport(vport);
1227 struct lpfc_hba *phba = vport->phba;
1228 struct lpfc_iocbq *cmdiocb = arg;
1229 struct lpfc_dmabuf *pcmd = cmdiocb->cmd_dmabuf;
1230 uint32_t *lp = (uint32_t *) pcmd->virt;
1231 struct serv_parm *sp = (struct serv_parm *) (lp + 1);
1232 struct ls_rjt stat;
1233 int port_cmp;
1234
1235 memset(&stat, 0, sizeof (struct ls_rjt));
1236
1237
1238
1239
1240 phba->fc_stat.elsLogiCol++;
1241 port_cmp = memcmp(&vport->fc_portname, &sp->portName,
1242 sizeof(struct lpfc_name));
1243
1244 if (port_cmp >= 0) {
1245
1246
1247 stat.un.b.lsRjtRsnCode = LSRJT_UNABLE_TPC;
1248 stat.un.b.lsRjtRsnCodeExp = LSEXP_CMD_IN_PROGRESS;
1249 lpfc_els_rsp_reject(vport, stat.un.lsRjtError, cmdiocb, ndlp,
1250 NULL);
1251 } else {
1252 if (lpfc_rcv_plogi(vport, ndlp, cmdiocb) &&
1253 (ndlp->nlp_flag & NLP_NPR_2B_DISC) &&
1254 (vport->num_disc_nodes)) {
1255 spin_lock_irq(&ndlp->lock);
1256 ndlp->nlp_flag &= ~NLP_NPR_2B_DISC;
1257 spin_unlock_irq(&ndlp->lock);
1258
1259 lpfc_more_plogi(vport);
1260 if (vport->num_disc_nodes == 0) {
1261 spin_lock_irq(shost->host_lock);
1262 vport->fc_flag &= ~FC_NDISC_ACTIVE;
1263 spin_unlock_irq(shost->host_lock);
1264 lpfc_can_disctmo(vport);
1265 lpfc_end_rscn(vport);
1266 }
1267 }
1268 }
1269
1270 return ndlp->nlp_state;
1271 }
1272
1273 static uint32_t
1274 lpfc_rcv_prli_plogi_issue(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
1275 void *arg, uint32_t evt)
1276 {
1277 struct lpfc_iocbq *cmdiocb = (struct lpfc_iocbq *) arg;
1278 struct ls_rjt stat;
1279
1280 memset(&stat, 0, sizeof (struct ls_rjt));
1281 stat.un.b.lsRjtRsnCode = LSRJT_LOGICAL_BSY;
1282 stat.un.b.lsRjtRsnCodeExp = LSEXP_NOTHING_MORE;
1283 lpfc_els_rsp_reject(vport, stat.un.lsRjtError, cmdiocb, ndlp, NULL);
1284 return ndlp->nlp_state;
1285 }
1286
1287 static uint32_t
1288 lpfc_rcv_logo_plogi_issue(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
1289 void *arg, uint32_t evt)
1290 {
1291 struct lpfc_iocbq *cmdiocb = (struct lpfc_iocbq *) arg;
1292
1293
1294 if (vport->phba->sli_rev == LPFC_SLI_REV3)
1295 ndlp->nlp_rpi = cmdiocb->iocb.ulpIoTag;
1296
1297 lpfc_els_abort(vport->phba, ndlp);
1298
1299 lpfc_rcv_logo(vport, ndlp, cmdiocb, ELS_CMD_LOGO);
1300 return ndlp->nlp_state;
1301 }
1302
1303 static uint32_t
1304 lpfc_rcv_els_plogi_issue(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
1305 void *arg, uint32_t evt)
1306 {
1307 struct lpfc_hba *phba = vport->phba;
1308 struct lpfc_iocbq *cmdiocb = (struct lpfc_iocbq *) arg;
1309
1310
1311 lpfc_els_abort(phba, ndlp);
1312
1313 if (evt == NLP_EVT_RCV_LOGO) {
1314 lpfc_els_rsp_acc(vport, ELS_CMD_ACC, cmdiocb, ndlp, NULL);
1315 } else {
1316 lpfc_issue_els_logo(vport, ndlp, 0);
1317 }
1318
1319
1320 mod_timer(&ndlp->nlp_delayfunc, jiffies + msecs_to_jiffies(1000 * 1));
1321 spin_lock_irq(&ndlp->lock);
1322 ndlp->nlp_flag |= NLP_DELAY_TMO;
1323 spin_unlock_irq(&ndlp->lock);
1324 ndlp->nlp_last_elscmd = ELS_CMD_PLOGI;
1325 ndlp->nlp_prev_state = NLP_STE_PLOGI_ISSUE;
1326 lpfc_nlp_set_state(vport, ndlp, NLP_STE_NPR_NODE);
1327
1328 return ndlp->nlp_state;
1329 }
1330
1331 static uint32_t
1332 lpfc_cmpl_plogi_plogi_issue(struct lpfc_vport *vport,
1333 struct lpfc_nodelist *ndlp,
1334 void *arg,
1335 uint32_t evt)
1336 {
1337 struct lpfc_hba *phba = vport->phba;
1338 struct lpfc_iocbq *cmdiocb, *rspiocb;
1339 struct lpfc_dmabuf *pcmd, *prsp;
1340 uint32_t *lp;
1341 uint32_t vid, flag;
1342 struct serv_parm *sp;
1343 uint32_t ed_tov;
1344 LPFC_MBOXQ_t *mbox;
1345 int rc;
1346 u32 ulp_status;
1347 u32 did;
1348
1349 cmdiocb = (struct lpfc_iocbq *) arg;
1350 rspiocb = cmdiocb->rsp_iocb;
1351
1352 ulp_status = get_job_ulpstatus(phba, rspiocb);
1353
1354 if (ndlp->nlp_flag & NLP_ACC_REGLOGIN) {
1355
1356 return ndlp->nlp_state;
1357 }
1358
1359 if (ulp_status)
1360 goto out;
1361
1362 pcmd = cmdiocb->cmd_dmabuf;
1363
1364 prsp = list_get_first(&pcmd->list, struct lpfc_dmabuf, list);
1365 if (!prsp)
1366 goto out;
1367
1368 lp = (uint32_t *) prsp->virt;
1369 sp = (struct serv_parm *) ((uint8_t *) lp + sizeof (uint32_t));
1370
1371
1372 if ((ndlp->nlp_DID != FDMI_DID) &&
1373 (wwn_to_u64(sp->portName.u.wwn) == 0 ||
1374 wwn_to_u64(sp->nodeName.u.wwn) == 0)) {
1375 lpfc_printf_vlog(vport, KERN_ERR, LOG_TRACE_EVENT,
1376 "0142 PLOGI RSP: Invalid WWN.\n");
1377 goto out;
1378 }
1379 if (!lpfc_check_sparm(vport, ndlp, sp, CLASS3, 0))
1380 goto out;
1381
1382 lpfc_printf_vlog(vport, KERN_INFO, LOG_ELS,
1383 "0121 PLOGI chkparm OK Data: x%x x%x x%x x%x\n",
1384 ndlp->nlp_DID, ndlp->nlp_state,
1385 ndlp->nlp_flag, ndlp->nlp_rpi);
1386 if (vport->cfg_fcp_class == 2 && (sp->cls2.classValid))
1387 ndlp->nlp_fcp_info |= CLASS2;
1388 else
1389 ndlp->nlp_fcp_info |= CLASS3;
1390
1391 ndlp->nlp_class_sup = 0;
1392 if (sp->cls1.classValid)
1393 ndlp->nlp_class_sup |= FC_COS_CLASS1;
1394 if (sp->cls2.classValid)
1395 ndlp->nlp_class_sup |= FC_COS_CLASS2;
1396 if (sp->cls3.classValid)
1397 ndlp->nlp_class_sup |= FC_COS_CLASS3;
1398 if (sp->cls4.classValid)
1399 ndlp->nlp_class_sup |= FC_COS_CLASS4;
1400 ndlp->nlp_maxframe =
1401 ((sp->cmn.bbRcvSizeMsb & 0x0F) << 8) | sp->cmn.bbRcvSizeLsb;
1402
1403 if ((vport->fc_flag & FC_PT2PT) &&
1404 (vport->fc_flag & FC_PT2PT_PLOGI)) {
1405 ed_tov = be32_to_cpu(sp->cmn.e_d_tov);
1406 if (sp->cmn.edtovResolution) {
1407
1408 ed_tov = (phba->fc_edtov + 999999) / 1000000;
1409 }
1410
1411 ndlp->nlp_flag &= ~NLP_SUPPRESS_RSP;
1412 if ((phba->sli.sli_flag & LPFC_SLI_SUPPRESS_RSP) &&
1413 sp->cmn.valid_vendor_ver_level) {
1414 vid = be32_to_cpu(sp->un.vv.vid);
1415 flag = be32_to_cpu(sp->un.vv.flags);
1416 if ((vid == LPFC_VV_EMLX_ID) &&
1417 (flag & LPFC_VV_SUPPRESS_RSP))
1418 ndlp->nlp_flag |= NLP_SUPPRESS_RSP;
1419 }
1420
1421
1422
1423
1424
1425 if (ed_tov > phba->fc_edtov)
1426 phba->fc_edtov = ed_tov;
1427 phba->fc_ratov = (2 * phba->fc_edtov) / 1000;
1428
1429 memcpy(&phba->fc_fabparam, sp, sizeof(struct serv_parm));
1430
1431
1432 if (phba->sli_rev == LPFC_SLI_REV4) {
1433 lpfc_issue_reg_vfi(vport);
1434 } else {
1435 mbox = mempool_alloc(phba->mbox_mem_pool, GFP_KERNEL);
1436 if (!mbox) {
1437 lpfc_printf_vlog(vport, KERN_ERR,
1438 LOG_TRACE_EVENT,
1439 "0133 PLOGI: no memory "
1440 "for config_link "
1441 "Data: x%x x%x x%x x%x\n",
1442 ndlp->nlp_DID, ndlp->nlp_state,
1443 ndlp->nlp_flag, ndlp->nlp_rpi);
1444 goto out;
1445 }
1446
1447 lpfc_config_link(phba, mbox);
1448
1449 mbox->mbox_cmpl = lpfc_sli_def_mbox_cmpl;
1450 mbox->vport = vport;
1451 rc = lpfc_sli_issue_mbox(phba, mbox, MBX_NOWAIT);
1452 if (rc == MBX_NOT_FINISHED) {
1453 mempool_free(mbox, phba->mbox_mem_pool);
1454 goto out;
1455 }
1456 }
1457 }
1458
1459 lpfc_unreg_rpi(vport, ndlp);
1460
1461 mbox = mempool_alloc(phba->mbox_mem_pool, GFP_KERNEL);
1462 if (!mbox) {
1463 lpfc_printf_vlog(vport, KERN_ERR, LOG_TRACE_EVENT,
1464 "0018 PLOGI: no memory for reg_login "
1465 "Data: x%x x%x x%x x%x\n",
1466 ndlp->nlp_DID, ndlp->nlp_state,
1467 ndlp->nlp_flag, ndlp->nlp_rpi);
1468 goto out;
1469 }
1470
1471 did = get_job_els_rsp64_did(phba, cmdiocb);
1472
1473 if (lpfc_reg_rpi(phba, vport->vpi, did,
1474 (uint8_t *) sp, mbox, ndlp->nlp_rpi) == 0) {
1475 switch (ndlp->nlp_DID) {
1476 case NameServer_DID:
1477 mbox->mbox_cmpl = lpfc_mbx_cmpl_ns_reg_login;
1478
1479 memcpy(&ndlp->fc_sparam, sp, sizeof(struct serv_parm));
1480 break;
1481 case FDMI_DID:
1482 mbox->mbox_cmpl = lpfc_mbx_cmpl_fdmi_reg_login;
1483 break;
1484 default:
1485 ndlp->nlp_flag |= NLP_REG_LOGIN_SEND;
1486 mbox->mbox_cmpl = lpfc_mbx_cmpl_reg_login;
1487 }
1488
1489 mbox->ctx_ndlp = lpfc_nlp_get(ndlp);
1490 if (!mbox->ctx_ndlp)
1491 goto out;
1492
1493 mbox->vport = vport;
1494 if (lpfc_sli_issue_mbox(phba, mbox, MBX_NOWAIT)
1495 != MBX_NOT_FINISHED) {
1496 lpfc_nlp_set_state(vport, ndlp,
1497 NLP_STE_REG_LOGIN_ISSUE);
1498 return ndlp->nlp_state;
1499 }
1500 if (ndlp->nlp_flag & NLP_REG_LOGIN_SEND)
1501 ndlp->nlp_flag &= ~NLP_REG_LOGIN_SEND;
1502
1503
1504
1505 lpfc_nlp_put(ndlp);
1506 lpfc_mbox_rsrc_cleanup(phba, mbox, MBOX_THD_UNLOCKED);
1507 lpfc_printf_vlog(vport, KERN_ERR, LOG_TRACE_EVENT,
1508 "0134 PLOGI: cannot issue reg_login "
1509 "Data: x%x x%x x%x x%x\n",
1510 ndlp->nlp_DID, ndlp->nlp_state,
1511 ndlp->nlp_flag, ndlp->nlp_rpi);
1512 } else {
1513 mempool_free(mbox, phba->mbox_mem_pool);
1514
1515 lpfc_printf_vlog(vport, KERN_ERR, LOG_TRACE_EVENT,
1516 "0135 PLOGI: cannot format reg_login "
1517 "Data: x%x x%x x%x x%x\n",
1518 ndlp->nlp_DID, ndlp->nlp_state,
1519 ndlp->nlp_flag, ndlp->nlp_rpi);
1520 }
1521
1522
1523 out:
1524 if (ndlp->nlp_DID == NameServer_DID) {
1525 lpfc_vport_set_state(vport, FC_VPORT_FAILED);
1526 lpfc_printf_vlog(vport, KERN_ERR, LOG_TRACE_EVENT,
1527 "0261 Cannot Register NameServer login\n");
1528 }
1529
1530
1531
1532
1533
1534
1535 ndlp->nlp_prev_state = ndlp->nlp_state;
1536 lpfc_nlp_set_state(vport, ndlp, NLP_STE_NPR_NODE);
1537 return NLP_STE_FREED_NODE;
1538 }
1539
1540 static uint32_t
1541 lpfc_cmpl_logo_plogi_issue(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
1542 void *arg, uint32_t evt)
1543 {
1544 return ndlp->nlp_state;
1545 }
1546
1547 static uint32_t
1548 lpfc_cmpl_reglogin_plogi_issue(struct lpfc_vport *vport,
1549 struct lpfc_nodelist *ndlp, void *arg, uint32_t evt)
1550 {
1551 struct lpfc_hba *phba;
1552 LPFC_MBOXQ_t *pmb = (LPFC_MBOXQ_t *) arg;
1553 MAILBOX_t *mb = &pmb->u.mb;
1554 uint16_t rpi;
1555
1556 phba = vport->phba;
1557
1558 if (!(phba->pport->load_flag & FC_UNLOADING) &&
1559 !mb->mbxStatus) {
1560 rpi = pmb->u.mb.un.varWords[0];
1561 lpfc_release_rpi(phba, vport, ndlp, rpi);
1562 }
1563 return ndlp->nlp_state;
1564 }
1565
1566 static uint32_t
1567 lpfc_device_rm_plogi_issue(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
1568 void *arg, uint32_t evt)
1569 {
1570 if (ndlp->nlp_flag & NLP_NPR_2B_DISC) {
1571 spin_lock_irq(&ndlp->lock);
1572 ndlp->nlp_flag |= NLP_NODEV_REMOVE;
1573 spin_unlock_irq(&ndlp->lock);
1574 return ndlp->nlp_state;
1575 } else {
1576
1577 lpfc_els_abort(vport->phba, ndlp);
1578
1579 lpfc_drop_node(vport, ndlp);
1580 return NLP_STE_FREED_NODE;
1581 }
1582 }
1583
1584 static uint32_t
1585 lpfc_device_recov_plogi_issue(struct lpfc_vport *vport,
1586 struct lpfc_nodelist *ndlp,
1587 void *arg,
1588 uint32_t evt)
1589 {
1590 struct lpfc_hba *phba = vport->phba;
1591
1592
1593
1594
1595 if (vport->fc_flag & FC_RSCN_DEFERRED)
1596 return ndlp->nlp_state;
1597
1598
1599 lpfc_els_abort(phba, ndlp);
1600
1601 ndlp->nlp_prev_state = NLP_STE_PLOGI_ISSUE;
1602 lpfc_nlp_set_state(vport, ndlp, NLP_STE_NPR_NODE);
1603 spin_lock_irq(&ndlp->lock);
1604 ndlp->nlp_flag &= ~(NLP_NODEV_REMOVE | NLP_NPR_2B_DISC);
1605 spin_unlock_irq(&ndlp->lock);
1606
1607 return ndlp->nlp_state;
1608 }
1609
1610 static uint32_t
1611 lpfc_rcv_plogi_adisc_issue(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
1612 void *arg, uint32_t evt)
1613 {
1614 struct lpfc_hba *phba = vport->phba;
1615 struct lpfc_iocbq *cmdiocb;
1616
1617
1618 lpfc_els_abort(phba, ndlp);
1619
1620 cmdiocb = (struct lpfc_iocbq *) arg;
1621
1622 if (lpfc_rcv_plogi(vport, ndlp, cmdiocb)) {
1623 if (ndlp->nlp_flag & NLP_NPR_2B_DISC) {
1624 spin_lock_irq(&ndlp->lock);
1625 ndlp->nlp_flag &= ~NLP_NPR_2B_DISC;
1626 spin_unlock_irq(&ndlp->lock);
1627 if (vport->num_disc_nodes)
1628 lpfc_more_adisc(vport);
1629 }
1630 return ndlp->nlp_state;
1631 }
1632 ndlp->nlp_prev_state = NLP_STE_ADISC_ISSUE;
1633 lpfc_issue_els_plogi(vport, ndlp->nlp_DID, 0);
1634 lpfc_nlp_set_state(vport, ndlp, NLP_STE_PLOGI_ISSUE);
1635
1636 return ndlp->nlp_state;
1637 }
1638
1639 static uint32_t
1640 lpfc_rcv_prli_adisc_issue(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
1641 void *arg, uint32_t evt)
1642 {
1643 struct lpfc_iocbq *cmdiocb = (struct lpfc_iocbq *) arg;
1644
1645 if (lpfc_rcv_prli_support_check(vport, ndlp, cmdiocb))
1646 lpfc_els_rsp_prli_acc(vport, cmdiocb, ndlp);
1647 return ndlp->nlp_state;
1648 }
1649
1650 static uint32_t
1651 lpfc_rcv_logo_adisc_issue(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
1652 void *arg, uint32_t evt)
1653 {
1654 struct lpfc_hba *phba = vport->phba;
1655 struct lpfc_iocbq *cmdiocb;
1656
1657 cmdiocb = (struct lpfc_iocbq *) arg;
1658
1659
1660 lpfc_els_abort(phba, ndlp);
1661
1662 lpfc_rcv_logo(vport, ndlp, cmdiocb, ELS_CMD_LOGO);
1663 return ndlp->nlp_state;
1664 }
1665
1666 static uint32_t
1667 lpfc_rcv_padisc_adisc_issue(struct lpfc_vport *vport,
1668 struct lpfc_nodelist *ndlp,
1669 void *arg, uint32_t evt)
1670 {
1671 struct lpfc_iocbq *cmdiocb;
1672
1673 cmdiocb = (struct lpfc_iocbq *) arg;
1674
1675 lpfc_rcv_padisc(vport, ndlp, cmdiocb);
1676 return ndlp->nlp_state;
1677 }
1678
1679 static uint32_t
1680 lpfc_rcv_prlo_adisc_issue(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
1681 void *arg, uint32_t evt)
1682 {
1683 struct lpfc_iocbq *cmdiocb;
1684
1685 cmdiocb = (struct lpfc_iocbq *) arg;
1686
1687
1688 lpfc_rcv_logo(vport, ndlp, cmdiocb, ELS_CMD_PRLO);
1689 return ndlp->nlp_state;
1690 }
1691
1692 static uint32_t
1693 lpfc_cmpl_adisc_adisc_issue(struct lpfc_vport *vport,
1694 struct lpfc_nodelist *ndlp,
1695 void *arg, uint32_t evt)
1696 {
1697 struct lpfc_hba *phba = vport->phba;
1698 struct lpfc_iocbq *cmdiocb, *rspiocb;
1699 ADISC *ap;
1700 int rc;
1701 u32 ulp_status;
1702
1703 cmdiocb = (struct lpfc_iocbq *) arg;
1704 rspiocb = cmdiocb->rsp_iocb;
1705
1706 ulp_status = get_job_ulpstatus(phba, rspiocb);
1707
1708 ap = (ADISC *)lpfc_check_elscmpl_iocb(phba, cmdiocb, rspiocb);
1709
1710 if ((ulp_status) ||
1711 (!lpfc_check_adisc(vport, ndlp, &ap->nodeName, &ap->portName))) {
1712
1713 mod_timer(&ndlp->nlp_delayfunc,
1714 jiffies + msecs_to_jiffies(1000));
1715 spin_lock_irq(&ndlp->lock);
1716 ndlp->nlp_flag |= NLP_DELAY_TMO;
1717 spin_unlock_irq(&ndlp->lock);
1718 ndlp->nlp_last_elscmd = ELS_CMD_PLOGI;
1719
1720 ndlp->nlp_prev_state = NLP_STE_ADISC_ISSUE;
1721 lpfc_nlp_set_state(vport, ndlp, NLP_STE_NPR_NODE);
1722 lpfc_unreg_rpi(vport, ndlp);
1723 return ndlp->nlp_state;
1724 }
1725
1726 if (phba->sli_rev == LPFC_SLI_REV4) {
1727 rc = lpfc_sli4_resume_rpi(ndlp, NULL, NULL);
1728 if (rc) {
1729
1730 ndlp->nlp_prev_state = NLP_STE_ADISC_ISSUE;
1731 return ndlp->nlp_state;
1732 }
1733 }
1734
1735 if (ndlp->nlp_type & NLP_FCP_TARGET)
1736 ndlp->nlp_fc4_type |= NLP_FC4_FCP;
1737
1738 if (ndlp->nlp_type & NLP_NVME_TARGET)
1739 ndlp->nlp_fc4_type |= NLP_FC4_NVME;
1740
1741 if (ndlp->nlp_type & (NLP_FCP_TARGET | NLP_NVME_TARGET)) {
1742 ndlp->nlp_prev_state = NLP_STE_ADISC_ISSUE;
1743 lpfc_nlp_set_state(vport, ndlp, NLP_STE_MAPPED_NODE);
1744 } else {
1745 ndlp->nlp_prev_state = NLP_STE_ADISC_ISSUE;
1746 lpfc_nlp_set_state(vport, ndlp, NLP_STE_UNMAPPED_NODE);
1747 }
1748
1749 return ndlp->nlp_state;
1750 }
1751
1752 static uint32_t
1753 lpfc_device_rm_adisc_issue(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
1754 void *arg, uint32_t evt)
1755 {
1756 if (ndlp->nlp_flag & NLP_NPR_2B_DISC) {
1757 spin_lock_irq(&ndlp->lock);
1758 ndlp->nlp_flag |= NLP_NODEV_REMOVE;
1759 spin_unlock_irq(&ndlp->lock);
1760 return ndlp->nlp_state;
1761 } else {
1762
1763 lpfc_els_abort(vport->phba, ndlp);
1764
1765 lpfc_drop_node(vport, ndlp);
1766 return NLP_STE_FREED_NODE;
1767 }
1768 }
1769
1770 static uint32_t
1771 lpfc_device_recov_adisc_issue(struct lpfc_vport *vport,
1772 struct lpfc_nodelist *ndlp,
1773 void *arg,
1774 uint32_t evt)
1775 {
1776 struct lpfc_hba *phba = vport->phba;
1777
1778
1779
1780
1781 if (vport->fc_flag & FC_RSCN_DEFERRED)
1782 return ndlp->nlp_state;
1783
1784
1785 lpfc_els_abort(phba, ndlp);
1786
1787 ndlp->nlp_prev_state = NLP_STE_ADISC_ISSUE;
1788 lpfc_nlp_set_state(vport, ndlp, NLP_STE_NPR_NODE);
1789 spin_lock_irq(&ndlp->lock);
1790 ndlp->nlp_flag &= ~(NLP_NODEV_REMOVE | NLP_NPR_2B_DISC);
1791 spin_unlock_irq(&ndlp->lock);
1792 lpfc_disc_set_adisc(vport, ndlp);
1793 return ndlp->nlp_state;
1794 }
1795
1796 static uint32_t
1797 lpfc_rcv_plogi_reglogin_issue(struct lpfc_vport *vport,
1798 struct lpfc_nodelist *ndlp,
1799 void *arg,
1800 uint32_t evt)
1801 {
1802 struct lpfc_iocbq *cmdiocb = (struct lpfc_iocbq *) arg;
1803
1804 lpfc_rcv_plogi(vport, ndlp, cmdiocb);
1805 return ndlp->nlp_state;
1806 }
1807
1808 static uint32_t
1809 lpfc_rcv_prli_reglogin_issue(struct lpfc_vport *vport,
1810 struct lpfc_nodelist *ndlp,
1811 void *arg,
1812 uint32_t evt)
1813 {
1814 struct lpfc_iocbq *cmdiocb = (struct lpfc_iocbq *) arg;
1815 struct ls_rjt stat;
1816
1817 if (!lpfc_rcv_prli_support_check(vport, ndlp, cmdiocb)) {
1818 return ndlp->nlp_state;
1819 }
1820 if (vport->phba->nvmet_support) {
1821
1822
1823
1824
1825 if (ndlp->nlp_flag & NLP_RPI_REGISTERED) {
1826 lpfc_rcv_prli(vport, ndlp, cmdiocb);
1827 lpfc_els_rsp_prli_acc(vport, cmdiocb, ndlp);
1828 } else {
1829
1830
1831
1832
1833 memset(&stat, 0, sizeof(struct ls_rjt));
1834 stat.un.b.lsRjtRsnCode = LSRJT_LOGICAL_BSY;
1835 stat.un.b.lsRjtRsnCodeExp = LSEXP_NOTHING_MORE;
1836 lpfc_els_rsp_reject(vport, stat.un.lsRjtError, cmdiocb,
1837 ndlp, NULL);
1838 return ndlp->nlp_state;
1839 }
1840 } else {
1841
1842 lpfc_els_rsp_prli_acc(vport, cmdiocb, ndlp);
1843 }
1844 return ndlp->nlp_state;
1845 }
1846
1847 static uint32_t
1848 lpfc_rcv_logo_reglogin_issue(struct lpfc_vport *vport,
1849 struct lpfc_nodelist *ndlp,
1850 void *arg,
1851 uint32_t evt)
1852 {
1853 struct lpfc_hba *phba = vport->phba;
1854 struct lpfc_iocbq *cmdiocb = (struct lpfc_iocbq *) arg;
1855 LPFC_MBOXQ_t *mb;
1856 LPFC_MBOXQ_t *nextmb;
1857 struct lpfc_nodelist *ns_ndlp;
1858
1859 cmdiocb = (struct lpfc_iocbq *) arg;
1860
1861
1862 if ((mb = phba->sli.mbox_active)) {
1863 if ((mb->u.mb.mbxCommand == MBX_REG_LOGIN64) &&
1864 (ndlp == (struct lpfc_nodelist *)mb->ctx_ndlp)) {
1865 ndlp->nlp_flag &= ~NLP_REG_LOGIN_SEND;
1866 lpfc_nlp_put(ndlp);
1867 mb->ctx_ndlp = NULL;
1868 mb->mbox_cmpl = lpfc_sli_def_mbox_cmpl;
1869 }
1870 }
1871
1872 spin_lock_irq(&phba->hbalock);
1873 list_for_each_entry_safe(mb, nextmb, &phba->sli.mboxq, list) {
1874 if ((mb->u.mb.mbxCommand == MBX_REG_LOGIN64) &&
1875 (ndlp == (struct lpfc_nodelist *)mb->ctx_ndlp)) {
1876 ndlp->nlp_flag &= ~NLP_REG_LOGIN_SEND;
1877 lpfc_nlp_put(ndlp);
1878 list_del(&mb->list);
1879 phba->sli.mboxq_cnt--;
1880 lpfc_mbox_rsrc_cleanup(phba, mb, MBOX_THD_LOCKED);
1881 }
1882 }
1883 spin_unlock_irq(&phba->hbalock);
1884
1885
1886 if (vport->cfg_enable_fc4_type != LPFC_ENABLE_FCP) {
1887 ns_ndlp = lpfc_findnode_did(vport, NameServer_DID);
1888 if (ns_ndlp)
1889 lpfc_els_abort(phba, ns_ndlp);
1890 }
1891
1892 lpfc_rcv_logo(vport, ndlp, cmdiocb, ELS_CMD_LOGO);
1893 return ndlp->nlp_state;
1894 }
1895
1896 static uint32_t
1897 lpfc_rcv_padisc_reglogin_issue(struct lpfc_vport *vport,
1898 struct lpfc_nodelist *ndlp,
1899 void *arg,
1900 uint32_t evt)
1901 {
1902 struct lpfc_iocbq *cmdiocb = (struct lpfc_iocbq *) arg;
1903
1904 lpfc_rcv_padisc(vport, ndlp, cmdiocb);
1905 return ndlp->nlp_state;
1906 }
1907
1908 static uint32_t
1909 lpfc_rcv_prlo_reglogin_issue(struct lpfc_vport *vport,
1910 struct lpfc_nodelist *ndlp,
1911 void *arg,
1912 uint32_t evt)
1913 {
1914 struct lpfc_iocbq *cmdiocb;
1915
1916 cmdiocb = (struct lpfc_iocbq *) arg;
1917 lpfc_els_rsp_acc(vport, ELS_CMD_PRLO, cmdiocb, ndlp, NULL);
1918 return ndlp->nlp_state;
1919 }
1920
1921 static uint32_t
1922 lpfc_cmpl_reglogin_reglogin_issue(struct lpfc_vport *vport,
1923 struct lpfc_nodelist *ndlp,
1924 void *arg,
1925 uint32_t evt)
1926 {
1927 struct lpfc_hba *phba = vport->phba;
1928 LPFC_MBOXQ_t *pmb = (LPFC_MBOXQ_t *) arg;
1929 MAILBOX_t *mb = &pmb->u.mb;
1930 uint32_t did = mb->un.varWords[1];
1931
1932 if (mb->mbxStatus) {
1933
1934 lpfc_printf_vlog(vport, KERN_ERR, LOG_TRACE_EVENT,
1935 "0246 RegLogin failed Data: x%x x%x x%x x%x "
1936 "x%x\n",
1937 did, mb->mbxStatus, vport->port_state,
1938 mb->un.varRegLogin.vpi,
1939 mb->un.varRegLogin.rpi);
1940
1941
1942
1943
1944 if (mb->mbxStatus == MBXERR_RPI_FULL) {
1945 ndlp->nlp_prev_state = NLP_STE_REG_LOGIN_ISSUE;
1946 lpfc_nlp_set_state(vport, ndlp, NLP_STE_NPR_NODE);
1947 return ndlp->nlp_state;
1948 }
1949
1950
1951 mod_timer(&ndlp->nlp_delayfunc,
1952 jiffies + msecs_to_jiffies(1000 * 1));
1953 spin_lock_irq(&ndlp->lock);
1954 ndlp->nlp_flag |= NLP_DELAY_TMO;
1955 spin_unlock_irq(&ndlp->lock);
1956 ndlp->nlp_last_elscmd = ELS_CMD_PLOGI;
1957
1958 lpfc_issue_els_logo(vport, ndlp, 0);
1959 return ndlp->nlp_state;
1960 }
1961
1962
1963 if (phba->sli_rev < LPFC_SLI_REV4)
1964 ndlp->nlp_rpi = mb->un.varWords[0];
1965
1966 ndlp->nlp_flag |= NLP_RPI_REGISTERED;
1967
1968
1969 lpfc_printf_vlog(vport, KERN_INFO, LOG_DISCOVERY,
1970 "3066 RegLogin Complete on x%x x%x x%x\n",
1971 did, ndlp->nlp_type, ndlp->nlp_fc4_type);
1972 if (!(ndlp->nlp_type & NLP_FABRIC) &&
1973 (phba->nvmet_support == 0)) {
1974
1975
1976
1977
1978
1979 if (vport->fc_flag & FC_PT2PT) {
1980
1981
1982
1983
1984 ndlp->nlp_fc4_type |= NLP_FC4_FCP;
1985 if ((!(vport->fc_flag & FC_PT2PT_NO_NVME)) &&
1986 (vport->cfg_enable_fc4_type == LPFC_ENABLE_BOTH ||
1987 vport->cfg_enable_fc4_type == LPFC_ENABLE_NVME)) {
1988 ndlp->nlp_fc4_type |= NLP_FC4_NVME;
1989
1990 lpfc_nvme_update_localport(vport);
1991 }
1992
1993 } else if (phba->fc_topology == LPFC_TOPOLOGY_LOOP) {
1994 ndlp->nlp_fc4_type |= NLP_FC4_FCP;
1995
1996 } else if (ndlp->nlp_fc4_type == 0) {
1997
1998
1999
2000
2001 if (vport->cfg_enable_fc4_type != LPFC_ENABLE_FCP) {
2002 lpfc_ns_cmd(vport, SLI_CTNS_GFT_ID, 0,
2003 ndlp->nlp_DID);
2004 return ndlp->nlp_state;
2005 }
2006 ndlp->nlp_fc4_type = NLP_FC4_FCP;
2007 }
2008
2009 ndlp->nlp_prev_state = NLP_STE_REG_LOGIN_ISSUE;
2010 lpfc_nlp_set_state(vport, ndlp, NLP_STE_PRLI_ISSUE);
2011 if (lpfc_issue_els_prli(vport, ndlp, 0)) {
2012 lpfc_issue_els_logo(vport, ndlp, 0);
2013 ndlp->nlp_prev_state = NLP_STE_REG_LOGIN_ISSUE;
2014 lpfc_nlp_set_state(vport, ndlp, NLP_STE_NPR_NODE);
2015 }
2016 } else {
2017 if ((vport->fc_flag & FC_PT2PT) && phba->nvmet_support)
2018 phba->targetport->port_id = vport->fc_myDID;
2019
2020
2021
2022
2023 if (ndlp->nlp_type & NLP_FABRIC) {
2024 ndlp->nlp_fc4_type &= ~NLP_FC4_FCP;
2025 ndlp->nlp_prev_state = NLP_STE_REG_LOGIN_ISSUE;
2026 lpfc_nlp_set_state(vport, ndlp, NLP_STE_UNMAPPED_NODE);
2027 }
2028 }
2029 return ndlp->nlp_state;
2030 }
2031
2032 static uint32_t
2033 lpfc_device_rm_reglogin_issue(struct lpfc_vport *vport,
2034 struct lpfc_nodelist *ndlp,
2035 void *arg,
2036 uint32_t evt)
2037 {
2038 if (ndlp->nlp_flag & NLP_NPR_2B_DISC) {
2039 spin_lock_irq(&ndlp->lock);
2040 ndlp->nlp_flag |= NLP_NODEV_REMOVE;
2041 spin_unlock_irq(&ndlp->lock);
2042 return ndlp->nlp_state;
2043 } else {
2044 lpfc_drop_node(vport, ndlp);
2045 return NLP_STE_FREED_NODE;
2046 }
2047 }
2048
2049 static uint32_t
2050 lpfc_device_recov_reglogin_issue(struct lpfc_vport *vport,
2051 struct lpfc_nodelist *ndlp,
2052 void *arg,
2053 uint32_t evt)
2054 {
2055
2056
2057
2058 if (vport->fc_flag & FC_RSCN_DEFERRED)
2059 return ndlp->nlp_state;
2060
2061 ndlp->nlp_prev_state = NLP_STE_REG_LOGIN_ISSUE;
2062 lpfc_nlp_set_state(vport, ndlp, NLP_STE_NPR_NODE);
2063 spin_lock_irq(&ndlp->lock);
2064
2065
2066
2067
2068 if (!(ndlp->nlp_flag & NLP_RPI_REGISTERED) ||
2069 !vport->phba->nvmet_support)
2070 ndlp->nlp_flag |= NLP_IGNR_REG_CMPL;
2071
2072 ndlp->nlp_flag &= ~(NLP_NODEV_REMOVE | NLP_NPR_2B_DISC);
2073 spin_unlock_irq(&ndlp->lock);
2074 lpfc_disc_set_adisc(vport, ndlp);
2075 return ndlp->nlp_state;
2076 }
2077
2078 static uint32_t
2079 lpfc_rcv_plogi_prli_issue(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2080 void *arg, uint32_t evt)
2081 {
2082 struct lpfc_iocbq *cmdiocb;
2083
2084 cmdiocb = (struct lpfc_iocbq *) arg;
2085
2086 lpfc_rcv_plogi(vport, ndlp, cmdiocb);
2087 return ndlp->nlp_state;
2088 }
2089
2090 static uint32_t
2091 lpfc_rcv_prli_prli_issue(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2092 void *arg, uint32_t evt)
2093 {
2094 struct lpfc_iocbq *cmdiocb = (struct lpfc_iocbq *) arg;
2095
2096 if (!lpfc_rcv_prli_support_check(vport, ndlp, cmdiocb))
2097 return ndlp->nlp_state;
2098 lpfc_rcv_prli(vport, ndlp, cmdiocb);
2099 lpfc_els_rsp_prli_acc(vport, cmdiocb, ndlp);
2100 return ndlp->nlp_state;
2101 }
2102
2103 static uint32_t
2104 lpfc_rcv_logo_prli_issue(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2105 void *arg, uint32_t evt)
2106 {
2107 struct lpfc_iocbq *cmdiocb = (struct lpfc_iocbq *) arg;
2108
2109
2110 lpfc_els_abort(vport->phba, ndlp);
2111
2112 lpfc_rcv_logo(vport, ndlp, cmdiocb, ELS_CMD_LOGO);
2113 return ndlp->nlp_state;
2114 }
2115
2116 static uint32_t
2117 lpfc_rcv_padisc_prli_issue(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2118 void *arg, uint32_t evt)
2119 {
2120 struct lpfc_iocbq *cmdiocb = (struct lpfc_iocbq *) arg;
2121
2122 lpfc_rcv_padisc(vport, ndlp, cmdiocb);
2123 return ndlp->nlp_state;
2124 }
2125
2126
2127
2128
2129
2130
2131 static uint32_t
2132 lpfc_rcv_prlo_prli_issue(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2133 void *arg, uint32_t evt)
2134 {
2135 struct lpfc_iocbq *cmdiocb = (struct lpfc_iocbq *) arg;
2136
2137 lpfc_els_rsp_acc(vport, ELS_CMD_PRLO, cmdiocb, ndlp, NULL);
2138 return ndlp->nlp_state;
2139 }
2140
2141 static uint32_t
2142 lpfc_cmpl_prli_prli_issue(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2143 void *arg, uint32_t evt)
2144 {
2145 struct lpfc_iocbq *cmdiocb, *rspiocb;
2146 struct lpfc_hba *phba = vport->phba;
2147 PRLI *npr;
2148 struct lpfc_nvme_prli *nvpr;
2149 void *temp_ptr;
2150 u32 ulp_status;
2151
2152 cmdiocb = (struct lpfc_iocbq *) arg;
2153 rspiocb = cmdiocb->rsp_iocb;
2154
2155 ulp_status = get_job_ulpstatus(phba, rspiocb);
2156
2157
2158
2159
2160
2161 npr = NULL;
2162 nvpr = NULL;
2163 temp_ptr = lpfc_check_elscmpl_iocb(phba, cmdiocb, rspiocb);
2164 if (cmdiocb->cmd_flag & LPFC_PRLI_FCP_REQ)
2165 npr = (PRLI *) temp_ptr;
2166 else if (cmdiocb->cmd_flag & LPFC_PRLI_NVME_REQ)
2167 nvpr = (struct lpfc_nvme_prli *) temp_ptr;
2168
2169 if (ulp_status) {
2170 if ((vport->port_type == LPFC_NPIV_PORT) &&
2171 vport->cfg_restrict_login) {
2172 goto out;
2173 }
2174
2175
2176 if (npr)
2177 ndlp->nlp_fc4_type &= ~NLP_FC4_FCP;
2178 if (nvpr)
2179 ndlp->nlp_fc4_type &= ~NLP_FC4_NVME;
2180
2181
2182 goto out_err;
2183 }
2184
2185 if (npr && (npr->acceptRspCode == PRLI_REQ_EXECUTED) &&
2186 (npr->prliType == PRLI_FCP_TYPE)) {
2187 lpfc_printf_vlog(vport, KERN_INFO, LOG_NVME_DISC,
2188 "6028 FCP NPR PRLI Cmpl Init %d Target %d\n",
2189 npr->initiatorFunc,
2190 npr->targetFunc);
2191 if (npr->initiatorFunc)
2192 ndlp->nlp_type |= NLP_FCP_INITIATOR;
2193 if (npr->targetFunc) {
2194 ndlp->nlp_type |= NLP_FCP_TARGET;
2195 if (npr->writeXferRdyDis)
2196 ndlp->nlp_flag |= NLP_FIRSTBURST;
2197 }
2198 if (npr->Retry)
2199 ndlp->nlp_fcp_info |= NLP_FCP_2_DEVICE;
2200
2201 } else if (nvpr &&
2202 (bf_get_be32(prli_acc_rsp_code, nvpr) ==
2203 PRLI_REQ_EXECUTED) &&
2204 (bf_get_be32(prli_type_code, nvpr) ==
2205 PRLI_NVME_TYPE)) {
2206
2207
2208 if (bf_get_be32(prli_init, nvpr))
2209 ndlp->nlp_type |= NLP_NVME_INITIATOR;
2210
2211 if (phba->nsler && bf_get_be32(prli_nsler, nvpr) &&
2212 bf_get_be32(prli_conf, nvpr))
2213
2214 ndlp->nlp_nvme_info |= NLP_NVME_NSLER;
2215 else
2216 ndlp->nlp_nvme_info &= ~NLP_NVME_NSLER;
2217
2218
2219 if (bf_get_be32(prli_tgt, nvpr)) {
2220
2221
2222
2223
2224 ndlp->nlp_type |= NLP_NVME_TARGET;
2225 if (bf_get_be32(prli_disc, nvpr))
2226 ndlp->nlp_type |= NLP_NVME_DISCOVERY;
2227
2228
2229
2230
2231
2232
2233
2234 if ((bf_get_be32(prli_fba, nvpr) == 1) &&
2235 (phba->cfg_nvme_enable_fb) &&
2236 (!phba->nvmet_support)) {
2237
2238
2239
2240 ndlp->nlp_flag |= NLP_FIRSTBURST;
2241 ndlp->nvme_fb_size = bf_get_be32(prli_fb_sz,
2242 nvpr);
2243
2244
2245 if (ndlp->nvme_fb_size)
2246 ndlp->nvme_fb_size <<=
2247 LPFC_NVME_FB_SHIFT;
2248 else
2249 ndlp->nvme_fb_size = LPFC_NVME_MAX_FB;
2250 }
2251 }
2252
2253 lpfc_printf_vlog(vport, KERN_INFO, LOG_NVME_DISC,
2254 "6029 NVME PRLI Cmpl w1 x%08x "
2255 "w4 x%08x w5 x%08x flag x%x, "
2256 "fcp_info x%x nlp_type x%x\n",
2257 be32_to_cpu(nvpr->word1),
2258 be32_to_cpu(nvpr->word4),
2259 be32_to_cpu(nvpr->word5),
2260 ndlp->nlp_flag, ndlp->nlp_fcp_info,
2261 ndlp->nlp_type);
2262 }
2263 if (!(ndlp->nlp_type & NLP_FCP_TARGET) &&
2264 (vport->port_type == LPFC_NPIV_PORT) &&
2265 vport->cfg_restrict_login) {
2266 out:
2267 spin_lock_irq(&ndlp->lock);
2268 ndlp->nlp_flag |= NLP_TARGET_REMOVE;
2269 spin_unlock_irq(&ndlp->lock);
2270 lpfc_issue_els_logo(vport, ndlp, 0);
2271
2272 ndlp->nlp_prev_state = NLP_STE_PRLI_ISSUE;
2273 lpfc_nlp_set_state(vport, ndlp, NLP_STE_NPR_NODE);
2274 return ndlp->nlp_state;
2275 }
2276
2277 out_err:
2278
2279
2280
2281 if (ndlp->fc4_prli_sent == 0) {
2282 ndlp->nlp_prev_state = NLP_STE_PRLI_ISSUE;
2283 if (ndlp->nlp_type & (NLP_FCP_TARGET | NLP_NVME_TARGET))
2284 lpfc_nlp_set_state(vport, ndlp, NLP_STE_MAPPED_NODE);
2285 else if (ndlp->nlp_type &
2286 (NLP_FCP_INITIATOR | NLP_NVME_INITIATOR))
2287 lpfc_nlp_set_state(vport, ndlp, NLP_STE_UNMAPPED_NODE);
2288 } else
2289 lpfc_printf_vlog(vport,
2290 KERN_INFO, LOG_ELS,
2291 "3067 PRLI's still outstanding "
2292 "on x%06x - count %d, Pend Node Mode "
2293 "transition...\n",
2294 ndlp->nlp_DID, ndlp->fc4_prli_sent);
2295
2296 return ndlp->nlp_state;
2297 }
2298
2299
2300
2301
2302
2303
2304
2305
2306
2307
2308
2309
2310
2311
2312
2313
2314
2315
2316
2317 static uint32_t
2318 lpfc_device_rm_prli_issue(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2319 void *arg, uint32_t evt)
2320 {
2321 if (ndlp->nlp_flag & NLP_NPR_2B_DISC) {
2322 spin_lock_irq(&ndlp->lock);
2323 ndlp->nlp_flag |= NLP_NODEV_REMOVE;
2324 spin_unlock_irq(&ndlp->lock);
2325 return ndlp->nlp_state;
2326 } else {
2327
2328 lpfc_els_abort(vport->phba, ndlp);
2329
2330 lpfc_drop_node(vport, ndlp);
2331 return NLP_STE_FREED_NODE;
2332 }
2333 }
2334
2335
2336
2337
2338
2339
2340
2341
2342
2343
2344
2345
2346
2347
2348
2349
2350
2351
2352 static uint32_t
2353 lpfc_device_recov_prli_issue(struct lpfc_vport *vport,
2354 struct lpfc_nodelist *ndlp,
2355 void *arg,
2356 uint32_t evt)
2357 {
2358 struct lpfc_hba *phba = vport->phba;
2359
2360
2361
2362
2363 if (vport->fc_flag & FC_RSCN_DEFERRED)
2364 return ndlp->nlp_state;
2365
2366
2367 lpfc_els_abort(phba, ndlp);
2368
2369 ndlp->nlp_prev_state = NLP_STE_PRLI_ISSUE;
2370 lpfc_nlp_set_state(vport, ndlp, NLP_STE_NPR_NODE);
2371 spin_lock_irq(&ndlp->lock);
2372 ndlp->nlp_flag &= ~(NLP_NODEV_REMOVE | NLP_NPR_2B_DISC);
2373 spin_unlock_irq(&ndlp->lock);
2374 lpfc_disc_set_adisc(vport, ndlp);
2375 return ndlp->nlp_state;
2376 }
2377
2378 static uint32_t
2379 lpfc_rcv_plogi_logo_issue(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2380 void *arg, uint32_t evt)
2381 {
2382 struct lpfc_iocbq *cmdiocb = (struct lpfc_iocbq *)arg;
2383 struct ls_rjt stat;
2384
2385 memset(&stat, 0, sizeof(struct ls_rjt));
2386 stat.un.b.lsRjtRsnCode = LSRJT_UNABLE_TPC;
2387 stat.un.b.lsRjtRsnCodeExp = LSEXP_NOTHING_MORE;
2388 lpfc_els_rsp_reject(vport, stat.un.lsRjtError, cmdiocb, ndlp, NULL);
2389 return ndlp->nlp_state;
2390 }
2391
2392 static uint32_t
2393 lpfc_rcv_prli_logo_issue(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2394 void *arg, uint32_t evt)
2395 {
2396 struct lpfc_iocbq *cmdiocb = (struct lpfc_iocbq *)arg;
2397 struct ls_rjt stat;
2398
2399 memset(&stat, 0, sizeof(struct ls_rjt));
2400 stat.un.b.lsRjtRsnCode = LSRJT_UNABLE_TPC;
2401 stat.un.b.lsRjtRsnCodeExp = LSEXP_NOTHING_MORE;
2402 lpfc_els_rsp_reject(vport, stat.un.lsRjtError, cmdiocb, ndlp, NULL);
2403 return ndlp->nlp_state;
2404 }
2405
2406 static uint32_t
2407 lpfc_rcv_logo_logo_issue(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2408 void *arg, uint32_t evt)
2409 {
2410 struct lpfc_iocbq *cmdiocb = (struct lpfc_iocbq *)arg;
2411
2412 spin_lock_irq(&ndlp->lock);
2413 ndlp->nlp_flag |= NLP_LOGO_ACC;
2414 spin_unlock_irq(&ndlp->lock);
2415 lpfc_els_rsp_acc(vport, ELS_CMD_ACC, cmdiocb, ndlp, NULL);
2416 return ndlp->nlp_state;
2417 }
2418
2419 static uint32_t
2420 lpfc_rcv_padisc_logo_issue(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2421 void *arg, uint32_t evt)
2422 {
2423 struct lpfc_iocbq *cmdiocb = (struct lpfc_iocbq *)arg;
2424 struct ls_rjt stat;
2425
2426 memset(&stat, 0, sizeof(struct ls_rjt));
2427 stat.un.b.lsRjtRsnCode = LSRJT_UNABLE_TPC;
2428 stat.un.b.lsRjtRsnCodeExp = LSEXP_NOTHING_MORE;
2429 lpfc_els_rsp_reject(vport, stat.un.lsRjtError, cmdiocb, ndlp, NULL);
2430 return ndlp->nlp_state;
2431 }
2432
2433 static uint32_t
2434 lpfc_rcv_prlo_logo_issue(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2435 void *arg, uint32_t evt)
2436 {
2437 struct lpfc_iocbq *cmdiocb = (struct lpfc_iocbq *)arg;
2438 struct ls_rjt stat;
2439
2440 memset(&stat, 0, sizeof(struct ls_rjt));
2441 stat.un.b.lsRjtRsnCode = LSRJT_UNABLE_TPC;
2442 stat.un.b.lsRjtRsnCodeExp = LSEXP_NOTHING_MORE;
2443 lpfc_els_rsp_reject(vport, stat.un.lsRjtError, cmdiocb, ndlp, NULL);
2444 return ndlp->nlp_state;
2445 }
2446
2447 static uint32_t
2448 lpfc_cmpl_logo_logo_issue(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2449 void *arg, uint32_t evt)
2450 {
2451 ndlp->nlp_prev_state = NLP_STE_LOGO_ISSUE;
2452 lpfc_nlp_set_state(vport, ndlp, NLP_STE_NPR_NODE);
2453 spin_lock_irq(&ndlp->lock);
2454 ndlp->nlp_flag &= ~(NLP_NODEV_REMOVE | NLP_NPR_2B_DISC);
2455 spin_unlock_irq(&ndlp->lock);
2456 lpfc_disc_set_adisc(vport, ndlp);
2457 return ndlp->nlp_state;
2458 }
2459
2460 static uint32_t
2461 lpfc_device_rm_logo_issue(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2462 void *arg, uint32_t evt)
2463 {
2464
2465
2466
2467
2468
2469 lpfc_unreg_rpi(vport, ndlp);
2470
2471 lpfc_els_abort(vport->phba, ndlp);
2472 lpfc_drop_node(vport, ndlp);
2473 return NLP_STE_FREED_NODE;
2474 }
2475
2476 static uint32_t
2477 lpfc_device_recov_logo_issue(struct lpfc_vport *vport,
2478 struct lpfc_nodelist *ndlp,
2479 void *arg, uint32_t evt)
2480 {
2481
2482
2483
2484
2485
2486 return ndlp->nlp_state;
2487 }
2488
2489 static uint32_t
2490 lpfc_rcv_plogi_unmap_node(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2491 void *arg, uint32_t evt)
2492 {
2493 struct lpfc_iocbq *cmdiocb = (struct lpfc_iocbq *) arg;
2494
2495 lpfc_rcv_plogi(vport, ndlp, cmdiocb);
2496 return ndlp->nlp_state;
2497 }
2498
2499 static uint32_t
2500 lpfc_rcv_prli_unmap_node(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2501 void *arg, uint32_t evt)
2502 {
2503 struct lpfc_iocbq *cmdiocb = (struct lpfc_iocbq *) arg;
2504
2505 if (!lpfc_rcv_prli_support_check(vport, ndlp, cmdiocb))
2506 return ndlp->nlp_state;
2507
2508 lpfc_rcv_prli(vport, ndlp, cmdiocb);
2509 lpfc_els_rsp_prli_acc(vport, cmdiocb, ndlp);
2510 return ndlp->nlp_state;
2511 }
2512
2513 static uint32_t
2514 lpfc_rcv_logo_unmap_node(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2515 void *arg, uint32_t evt)
2516 {
2517 struct lpfc_iocbq *cmdiocb = (struct lpfc_iocbq *) arg;
2518
2519 lpfc_rcv_logo(vport, ndlp, cmdiocb, ELS_CMD_LOGO);
2520 return ndlp->nlp_state;
2521 }
2522
2523 static uint32_t
2524 lpfc_rcv_padisc_unmap_node(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2525 void *arg, uint32_t evt)
2526 {
2527 struct lpfc_iocbq *cmdiocb = (struct lpfc_iocbq *) arg;
2528
2529 lpfc_rcv_padisc(vport, ndlp, cmdiocb);
2530 return ndlp->nlp_state;
2531 }
2532
2533 static uint32_t
2534 lpfc_rcv_prlo_unmap_node(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2535 void *arg, uint32_t evt)
2536 {
2537 struct lpfc_iocbq *cmdiocb = (struct lpfc_iocbq *) arg;
2538
2539 lpfc_els_rsp_acc(vport, ELS_CMD_PRLO, cmdiocb, ndlp, NULL);
2540 return ndlp->nlp_state;
2541 }
2542
2543 static uint32_t
2544 lpfc_device_rm_unmap_node(struct lpfc_vport *vport,
2545 struct lpfc_nodelist *ndlp,
2546 void *arg,
2547 uint32_t evt)
2548 {
2549 lpfc_drop_node(vport, ndlp);
2550 return NLP_STE_FREED_NODE;
2551 }
2552
2553 static uint32_t
2554 lpfc_device_recov_unmap_node(struct lpfc_vport *vport,
2555 struct lpfc_nodelist *ndlp,
2556 void *arg,
2557 uint32_t evt)
2558 {
2559 ndlp->nlp_prev_state = NLP_STE_UNMAPPED_NODE;
2560 lpfc_nlp_set_state(vport, ndlp, NLP_STE_NPR_NODE);
2561 spin_lock_irq(&ndlp->lock);
2562 ndlp->nlp_flag &= ~(NLP_NODEV_REMOVE | NLP_NPR_2B_DISC);
2563 ndlp->nlp_fc4_type &= ~(NLP_FC4_FCP | NLP_FC4_NVME);
2564 spin_unlock_irq(&ndlp->lock);
2565 lpfc_disc_set_adisc(vport, ndlp);
2566
2567 return ndlp->nlp_state;
2568 }
2569
2570 static uint32_t
2571 lpfc_rcv_plogi_mapped_node(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2572 void *arg, uint32_t evt)
2573 {
2574 struct lpfc_iocbq *cmdiocb = (struct lpfc_iocbq *) arg;
2575
2576 lpfc_rcv_plogi(vport, ndlp, cmdiocb);
2577 return ndlp->nlp_state;
2578 }
2579
2580 static uint32_t
2581 lpfc_rcv_prli_mapped_node(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2582 void *arg, uint32_t evt)
2583 {
2584 struct lpfc_iocbq *cmdiocb = (struct lpfc_iocbq *) arg;
2585
2586 if (!lpfc_rcv_prli_support_check(vport, ndlp, cmdiocb))
2587 return ndlp->nlp_state;
2588 lpfc_els_rsp_prli_acc(vport, cmdiocb, ndlp);
2589 return ndlp->nlp_state;
2590 }
2591
2592 static uint32_t
2593 lpfc_rcv_logo_mapped_node(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2594 void *arg, uint32_t evt)
2595 {
2596 struct lpfc_iocbq *cmdiocb = (struct lpfc_iocbq *) arg;
2597
2598 lpfc_rcv_logo(vport, ndlp, cmdiocb, ELS_CMD_LOGO);
2599 return ndlp->nlp_state;
2600 }
2601
2602 static uint32_t
2603 lpfc_rcv_padisc_mapped_node(struct lpfc_vport *vport,
2604 struct lpfc_nodelist *ndlp,
2605 void *arg, uint32_t evt)
2606 {
2607 struct lpfc_iocbq *cmdiocb = (struct lpfc_iocbq *) arg;
2608
2609 lpfc_rcv_padisc(vport, ndlp, cmdiocb);
2610 return ndlp->nlp_state;
2611 }
2612
2613 static uint32_t
2614 lpfc_rcv_prlo_mapped_node(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2615 void *arg, uint32_t evt)
2616 {
2617 struct lpfc_iocbq *cmdiocb = (struct lpfc_iocbq *) arg;
2618
2619
2620 lpfc_sli_abort_iocb(vport, ndlp->nlp_sid, 0, LPFC_CTX_TGT);
2621
2622
2623 lpfc_rcv_logo(vport, ndlp, cmdiocb, ELS_CMD_PRLO);
2624 return ndlp->nlp_state;
2625 }
2626
2627 static uint32_t
2628 lpfc_device_recov_mapped_node(struct lpfc_vport *vport,
2629 struct lpfc_nodelist *ndlp,
2630 void *arg,
2631 uint32_t evt)
2632 {
2633 lpfc_disc_set_adisc(vport, ndlp);
2634
2635 ndlp->nlp_prev_state = NLP_STE_MAPPED_NODE;
2636 lpfc_nlp_set_state(vport, ndlp, NLP_STE_NPR_NODE);
2637 spin_lock_irq(&ndlp->lock);
2638 ndlp->nlp_flag &= ~(NLP_NODEV_REMOVE | NLP_NPR_2B_DISC);
2639 ndlp->nlp_fc4_type &= ~(NLP_FC4_FCP | NLP_FC4_NVME);
2640 spin_unlock_irq(&ndlp->lock);
2641 return ndlp->nlp_state;
2642 }
2643
2644 static uint32_t
2645 lpfc_rcv_plogi_npr_node(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2646 void *arg, uint32_t evt)
2647 {
2648 struct lpfc_iocbq *cmdiocb = (struct lpfc_iocbq *) arg;
2649
2650
2651 if (ndlp->nlp_flag & (NLP_LOGO_SND | NLP_LOGO_ACC))
2652 return ndlp->nlp_state;
2653 if (lpfc_rcv_plogi(vport, ndlp, cmdiocb)) {
2654 lpfc_cancel_retry_delay_tmo(vport, ndlp);
2655 spin_lock_irq(&ndlp->lock);
2656 ndlp->nlp_flag &= ~(NLP_NPR_ADISC | NLP_NPR_2B_DISC);
2657 spin_unlock_irq(&ndlp->lock);
2658 } else if (!(ndlp->nlp_flag & NLP_NPR_2B_DISC)) {
2659
2660 if (!(ndlp->nlp_flag & NLP_DELAY_TMO)) {
2661 ndlp->nlp_prev_state = NLP_STE_NPR_NODE;
2662 lpfc_nlp_set_state(vport, ndlp, NLP_STE_PLOGI_ISSUE);
2663 lpfc_issue_els_plogi(vport, ndlp->nlp_DID, 0);
2664 }
2665 }
2666 return ndlp->nlp_state;
2667 }
2668
2669 static uint32_t
2670 lpfc_rcv_prli_npr_node(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2671 void *arg, uint32_t evt)
2672 {
2673 struct lpfc_iocbq *cmdiocb = (struct lpfc_iocbq *) arg;
2674 struct ls_rjt stat;
2675
2676 memset(&stat, 0, sizeof (struct ls_rjt));
2677 stat.un.b.lsRjtRsnCode = LSRJT_UNABLE_TPC;
2678 stat.un.b.lsRjtRsnCodeExp = LSEXP_NOTHING_MORE;
2679 lpfc_els_rsp_reject(vport, stat.un.lsRjtError, cmdiocb, ndlp, NULL);
2680
2681 if (!(ndlp->nlp_flag & NLP_DELAY_TMO)) {
2682
2683
2684
2685
2686
2687
2688 if (!(ndlp->nlp_flag & NLP_NPR_ADISC)) {
2689 ndlp->nlp_prev_state = NLP_STE_NPR_NODE;
2690 lpfc_nlp_set_state(vport, ndlp, NLP_STE_PLOGI_ISSUE);
2691 lpfc_issue_els_plogi(vport, ndlp->nlp_DID, 0);
2692 }
2693 }
2694 return ndlp->nlp_state;
2695 }
2696
2697 static uint32_t
2698 lpfc_rcv_logo_npr_node(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2699 void *arg, uint32_t evt)
2700 {
2701 struct lpfc_iocbq *cmdiocb = (struct lpfc_iocbq *) arg;
2702
2703 lpfc_rcv_logo(vport, ndlp, cmdiocb, ELS_CMD_LOGO);
2704 return ndlp->nlp_state;
2705 }
2706
2707 static uint32_t
2708 lpfc_rcv_padisc_npr_node(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2709 void *arg, uint32_t evt)
2710 {
2711 struct lpfc_iocbq *cmdiocb = (struct lpfc_iocbq *) arg;
2712
2713 lpfc_rcv_padisc(vport, ndlp, cmdiocb);
2714
2715
2716
2717
2718
2719 if (!(ndlp->nlp_flag & NLP_DELAY_TMO) &&
2720 !(ndlp->nlp_flag & NLP_NPR_2B_DISC)) {
2721
2722
2723
2724
2725
2726
2727 if (!(ndlp->nlp_flag & NLP_NPR_ADISC)) {
2728 ndlp->nlp_prev_state = NLP_STE_NPR_NODE;
2729 lpfc_nlp_set_state(vport, ndlp, NLP_STE_PLOGI_ISSUE);
2730 lpfc_issue_els_plogi(vport, ndlp->nlp_DID, 0);
2731 }
2732 }
2733 return ndlp->nlp_state;
2734 }
2735
2736 static uint32_t
2737 lpfc_rcv_prlo_npr_node(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2738 void *arg, uint32_t evt)
2739 {
2740 struct lpfc_iocbq *cmdiocb = (struct lpfc_iocbq *) arg;
2741
2742 spin_lock_irq(&ndlp->lock);
2743 ndlp->nlp_flag |= NLP_LOGO_ACC;
2744 spin_unlock_irq(&ndlp->lock);
2745
2746 lpfc_els_rsp_acc(vport, ELS_CMD_ACC, cmdiocb, ndlp, NULL);
2747
2748 if ((ndlp->nlp_flag & NLP_DELAY_TMO) == 0) {
2749 mod_timer(&ndlp->nlp_delayfunc,
2750 jiffies + msecs_to_jiffies(1000 * 1));
2751 spin_lock_irq(&ndlp->lock);
2752 ndlp->nlp_flag |= NLP_DELAY_TMO;
2753 ndlp->nlp_flag &= ~NLP_NPR_ADISC;
2754 spin_unlock_irq(&ndlp->lock);
2755 ndlp->nlp_last_elscmd = ELS_CMD_PLOGI;
2756 } else {
2757 spin_lock_irq(&ndlp->lock);
2758 ndlp->nlp_flag &= ~NLP_NPR_ADISC;
2759 spin_unlock_irq(&ndlp->lock);
2760 }
2761 return ndlp->nlp_state;
2762 }
2763
2764 static uint32_t
2765 lpfc_cmpl_plogi_npr_node(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2766 void *arg, uint32_t evt)
2767 {
2768 struct lpfc_hba *phba = vport->phba;
2769 struct lpfc_iocbq *cmdiocb, *rspiocb;
2770 u32 ulp_status;
2771
2772 cmdiocb = (struct lpfc_iocbq *) arg;
2773 rspiocb = cmdiocb->rsp_iocb;
2774
2775 ulp_status = get_job_ulpstatus(phba, rspiocb);
2776
2777 if (ulp_status)
2778 return NLP_STE_FREED_NODE;
2779
2780 return ndlp->nlp_state;
2781 }
2782
2783 static uint32_t
2784 lpfc_cmpl_prli_npr_node(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2785 void *arg, uint32_t evt)
2786 {
2787 struct lpfc_hba *phba = vport->phba;
2788 struct lpfc_iocbq *cmdiocb, *rspiocb;
2789 u32 ulp_status;
2790
2791 cmdiocb = (struct lpfc_iocbq *) arg;
2792 rspiocb = cmdiocb->rsp_iocb;
2793
2794 ulp_status = get_job_ulpstatus(phba, rspiocb);
2795
2796 if (ulp_status && (ndlp->nlp_flag & NLP_NODEV_REMOVE)) {
2797 lpfc_drop_node(vport, ndlp);
2798 return NLP_STE_FREED_NODE;
2799 }
2800 return ndlp->nlp_state;
2801 }
2802
2803 static uint32_t
2804 lpfc_cmpl_logo_npr_node(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2805 void *arg, uint32_t evt)
2806 {
2807 struct Scsi_Host *shost = lpfc_shost_from_vport(vport);
2808
2809
2810 if (ndlp->nlp_DID == Fabric_DID) {
2811 spin_lock_irq(shost->host_lock);
2812 vport->fc_flag &= ~(FC_FABRIC | FC_PUBLIC_LOOP);
2813 spin_unlock_irq(shost->host_lock);
2814 }
2815 lpfc_unreg_rpi(vport, ndlp);
2816 return ndlp->nlp_state;
2817 }
2818
2819 static uint32_t
2820 lpfc_cmpl_adisc_npr_node(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2821 void *arg, uint32_t evt)
2822 {
2823 struct lpfc_hba *phba = vport->phba;
2824 struct lpfc_iocbq *cmdiocb, *rspiocb;
2825 u32 ulp_status;
2826
2827 cmdiocb = (struct lpfc_iocbq *) arg;
2828 rspiocb = cmdiocb->rsp_iocb;
2829
2830 ulp_status = get_job_ulpstatus(phba, rspiocb);
2831
2832 if (ulp_status && (ndlp->nlp_flag & NLP_NODEV_REMOVE)) {
2833 lpfc_drop_node(vport, ndlp);
2834 return NLP_STE_FREED_NODE;
2835 }
2836 return ndlp->nlp_state;
2837 }
2838
2839 static uint32_t
2840 lpfc_cmpl_reglogin_npr_node(struct lpfc_vport *vport,
2841 struct lpfc_nodelist *ndlp,
2842 void *arg, uint32_t evt)
2843 {
2844 LPFC_MBOXQ_t *pmb = (LPFC_MBOXQ_t *) arg;
2845 MAILBOX_t *mb = &pmb->u.mb;
2846
2847 if (!mb->mbxStatus) {
2848
2849 if (vport->phba->sli_rev < LPFC_SLI_REV4)
2850 ndlp->nlp_rpi = mb->un.varWords[0];
2851 ndlp->nlp_flag |= NLP_RPI_REGISTERED;
2852 if (ndlp->nlp_flag & NLP_LOGO_ACC) {
2853 lpfc_unreg_rpi(vport, ndlp);
2854 }
2855 } else {
2856 if (ndlp->nlp_flag & NLP_NODEV_REMOVE) {
2857 lpfc_drop_node(vport, ndlp);
2858 return NLP_STE_FREED_NODE;
2859 }
2860 }
2861 return ndlp->nlp_state;
2862 }
2863
2864 static uint32_t
2865 lpfc_device_rm_npr_node(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2866 void *arg, uint32_t evt)
2867 {
2868 if (ndlp->nlp_flag & NLP_NPR_2B_DISC) {
2869 spin_lock_irq(&ndlp->lock);
2870 ndlp->nlp_flag |= NLP_NODEV_REMOVE;
2871 spin_unlock_irq(&ndlp->lock);
2872 return ndlp->nlp_state;
2873 }
2874 lpfc_drop_node(vport, ndlp);
2875 return NLP_STE_FREED_NODE;
2876 }
2877
2878 static uint32_t
2879 lpfc_device_recov_npr_node(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
2880 void *arg, uint32_t evt)
2881 {
2882
2883
2884
2885 if (vport->fc_flag & FC_RSCN_DEFERRED)
2886 return ndlp->nlp_state;
2887
2888 lpfc_cancel_retry_delay_tmo(vport, ndlp);
2889 spin_lock_irq(&ndlp->lock);
2890 ndlp->nlp_flag &= ~(NLP_NODEV_REMOVE | NLP_NPR_2B_DISC);
2891 ndlp->nlp_fc4_type &= ~(NLP_FC4_FCP | NLP_FC4_NVME);
2892 spin_unlock_irq(&ndlp->lock);
2893 return ndlp->nlp_state;
2894 }
2895
2896
2897
2898
2899
2900
2901
2902
2903
2904
2905
2906
2907
2908
2909
2910
2911
2912
2913
2914
2915
2916
2917
2918
2919
2920
2921
2922
2923
2924
2925
2926
2927
2928
2929
2930
2931
2932
2933
2934
2935
2936
2937
2938
2939
2940
2941
2942
2943
2944
2945
2946
2947
2948
2949
2950
2951
2952
2953 static uint32_t (*lpfc_disc_action[NLP_STE_MAX_STATE * NLP_EVT_MAX_EVENT])
2954 (struct lpfc_vport *, struct lpfc_nodelist *, void *, uint32_t) = {
2955
2956 lpfc_rcv_plogi_unused_node,
2957 lpfc_rcv_els_unused_node,
2958 lpfc_rcv_logo_unused_node,
2959 lpfc_rcv_els_unused_node,
2960 lpfc_rcv_els_unused_node,
2961 lpfc_rcv_els_unused_node,
2962 lpfc_disc_illegal,
2963 lpfc_disc_illegal,
2964 lpfc_cmpl_logo_unused_node,
2965 lpfc_disc_illegal,
2966 lpfc_disc_illegal,
2967 lpfc_device_rm_unused_node,
2968 lpfc_device_recov_unused_node,
2969
2970 lpfc_rcv_plogi_plogi_issue,
2971 lpfc_rcv_prli_plogi_issue,
2972 lpfc_rcv_logo_plogi_issue,
2973 lpfc_rcv_els_plogi_issue,
2974 lpfc_rcv_els_plogi_issue,
2975 lpfc_rcv_els_plogi_issue,
2976 lpfc_cmpl_plogi_plogi_issue,
2977 lpfc_disc_illegal,
2978 lpfc_cmpl_logo_plogi_issue,
2979 lpfc_disc_illegal,
2980 lpfc_cmpl_reglogin_plogi_issue,
2981 lpfc_device_rm_plogi_issue,
2982 lpfc_device_recov_plogi_issue,
2983
2984 lpfc_rcv_plogi_adisc_issue,
2985 lpfc_rcv_prli_adisc_issue,
2986 lpfc_rcv_logo_adisc_issue,
2987 lpfc_rcv_padisc_adisc_issue,
2988 lpfc_rcv_padisc_adisc_issue,
2989 lpfc_rcv_prlo_adisc_issue,
2990 lpfc_disc_illegal,
2991 lpfc_disc_illegal,
2992 lpfc_disc_illegal,
2993 lpfc_cmpl_adisc_adisc_issue,
2994 lpfc_disc_illegal,
2995 lpfc_device_rm_adisc_issue,
2996 lpfc_device_recov_adisc_issue,
2997
2998 lpfc_rcv_plogi_reglogin_issue,
2999 lpfc_rcv_prli_reglogin_issue,
3000 lpfc_rcv_logo_reglogin_issue,
3001 lpfc_rcv_padisc_reglogin_issue,
3002 lpfc_rcv_padisc_reglogin_issue,
3003 lpfc_rcv_prlo_reglogin_issue,
3004 lpfc_cmpl_plogi_illegal,
3005 lpfc_disc_illegal,
3006 lpfc_disc_illegal,
3007 lpfc_disc_illegal,
3008 lpfc_cmpl_reglogin_reglogin_issue,
3009 lpfc_device_rm_reglogin_issue,
3010 lpfc_device_recov_reglogin_issue,
3011
3012 lpfc_rcv_plogi_prli_issue,
3013 lpfc_rcv_prli_prli_issue,
3014 lpfc_rcv_logo_prli_issue,
3015 lpfc_rcv_padisc_prli_issue,
3016 lpfc_rcv_padisc_prli_issue,
3017 lpfc_rcv_prlo_prli_issue,
3018 lpfc_cmpl_plogi_illegal,
3019 lpfc_cmpl_prli_prli_issue,
3020 lpfc_disc_illegal,
3021 lpfc_disc_illegal,
3022 lpfc_disc_illegal,
3023 lpfc_device_rm_prli_issue,
3024 lpfc_device_recov_prli_issue,
3025
3026 lpfc_rcv_plogi_logo_issue,
3027 lpfc_rcv_prli_logo_issue,
3028 lpfc_rcv_logo_logo_issue,
3029 lpfc_rcv_padisc_logo_issue,
3030 lpfc_rcv_padisc_logo_issue,
3031 lpfc_rcv_prlo_logo_issue,
3032 lpfc_cmpl_plogi_illegal,
3033 lpfc_disc_illegal,
3034 lpfc_cmpl_logo_logo_issue,
3035 lpfc_disc_illegal,
3036 lpfc_disc_illegal,
3037 lpfc_device_rm_logo_issue,
3038 lpfc_device_recov_logo_issue,
3039
3040 lpfc_rcv_plogi_unmap_node,
3041 lpfc_rcv_prli_unmap_node,
3042 lpfc_rcv_logo_unmap_node,
3043 lpfc_rcv_padisc_unmap_node,
3044 lpfc_rcv_padisc_unmap_node,
3045 lpfc_rcv_prlo_unmap_node,
3046 lpfc_disc_illegal,
3047 lpfc_disc_illegal,
3048 lpfc_disc_illegal,
3049 lpfc_disc_illegal,
3050 lpfc_disc_illegal,
3051 lpfc_device_rm_unmap_node,
3052 lpfc_device_recov_unmap_node,
3053
3054 lpfc_rcv_plogi_mapped_node,
3055 lpfc_rcv_prli_mapped_node,
3056 lpfc_rcv_logo_mapped_node,
3057 lpfc_rcv_padisc_mapped_node,
3058 lpfc_rcv_padisc_mapped_node,
3059 lpfc_rcv_prlo_mapped_node,
3060 lpfc_disc_illegal,
3061 lpfc_disc_illegal,
3062 lpfc_disc_illegal,
3063 lpfc_disc_illegal,
3064 lpfc_disc_illegal,
3065 lpfc_disc_illegal,
3066 lpfc_device_recov_mapped_node,
3067
3068 lpfc_rcv_plogi_npr_node,
3069 lpfc_rcv_prli_npr_node,
3070 lpfc_rcv_logo_npr_node,
3071 lpfc_rcv_padisc_npr_node,
3072 lpfc_rcv_padisc_npr_node,
3073 lpfc_rcv_prlo_npr_node,
3074 lpfc_cmpl_plogi_npr_node,
3075 lpfc_cmpl_prli_npr_node,
3076 lpfc_cmpl_logo_npr_node,
3077 lpfc_cmpl_adisc_npr_node,
3078 lpfc_cmpl_reglogin_npr_node,
3079 lpfc_device_rm_npr_node,
3080 lpfc_device_recov_npr_node,
3081 };
3082
3083 int
3084 lpfc_disc_state_machine(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,
3085 void *arg, uint32_t evt)
3086 {
3087 uint32_t cur_state, rc;
3088 uint32_t(*func) (struct lpfc_vport *, struct lpfc_nodelist *, void *,
3089 uint32_t);
3090 uint32_t got_ndlp = 0;
3091 uint32_t data1;
3092
3093 if (lpfc_nlp_get(ndlp))
3094 got_ndlp = 1;
3095
3096 cur_state = ndlp->nlp_state;
3097
3098 data1 = (((uint32_t)ndlp->nlp_fc4_type << 16) |
3099 ((uint32_t)ndlp->nlp_type));
3100
3101 lpfc_printf_vlog(vport, KERN_INFO, LOG_DISCOVERY,
3102 "0211 DSM in event x%x on NPort x%x in "
3103 "state %d rpi x%x Data: x%x x%x\n",
3104 evt, ndlp->nlp_DID, cur_state, ndlp->nlp_rpi,
3105 ndlp->nlp_flag, data1);
3106
3107 lpfc_debugfs_disc_trc(vport, LPFC_DISC_TRC_DSM,
3108 "DSM in: evt:%d ste:%d did:x%x",
3109 evt, cur_state, ndlp->nlp_DID);
3110
3111 func = lpfc_disc_action[(cur_state * NLP_EVT_MAX_EVENT) + evt];
3112 rc = (func) (vport, ndlp, arg, evt);
3113
3114
3115 if (got_ndlp) {
3116 data1 = (((uint32_t)ndlp->nlp_fc4_type << 16) |
3117 ((uint32_t)ndlp->nlp_type));
3118 lpfc_printf_vlog(vport, KERN_INFO, LOG_DISCOVERY,
3119 "0212 DSM out state %d on NPort x%x "
3120 "rpi x%x Data: x%x x%x\n",
3121 rc, ndlp->nlp_DID, ndlp->nlp_rpi, ndlp->nlp_flag,
3122 data1);
3123
3124 lpfc_debugfs_disc_trc(vport, LPFC_DISC_TRC_DSM,
3125 "DSM out: ste:%d did:x%x flg:x%x",
3126 rc, ndlp->nlp_DID, ndlp->nlp_flag);
3127
3128 lpfc_nlp_put(ndlp);
3129 } else {
3130 lpfc_printf_vlog(vport, KERN_INFO, LOG_DISCOVERY,
3131 "0213 DSM out state %d on NPort free\n", rc);
3132
3133 lpfc_debugfs_disc_trc(vport, LPFC_DISC_TRC_DSM,
3134 "DSM out: ste:%d did:x%x flg:x%x",
3135 rc, 0, 0);
3136 }
3137
3138 return rc;
3139 }