s390/ptrace: get rid of long longs in psw_bits
[linux/fpc-iii.git] / drivers / scsi / lpfc / lpfc_ct.c
blob8fded1f7605f74a09aeda7fd23d7afb88e200207
1 /*******************************************************************
2 * This file is part of the Emulex Linux Device Driver for *
3 * Fibre Channel Host Bus Adapters. *
4 * Copyright (C) 2004-2015 Emulex. All rights reserved. *
5 * EMULEX and SLI are trademarks of Emulex. *
6 * www.emulex.com *
7 * *
8 * This program is free software; you can redistribute it and/or *
9 * modify it under the terms of version 2 of the GNU General *
10 * Public License as published by the Free Software Foundation. *
11 * This program is distributed in the hope that it will be useful. *
12 * ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND *
13 * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, *
14 * FITNESS FOR A PARTICULAR PURPOSE, OR NON-INFRINGEMENT, ARE *
15 * DISCLAIMED, EXCEPT TO THE EXTENT THAT SUCH DISCLAIMERS ARE HELD *
16 * TO BE LEGALLY INVALID. See the GNU General Public License for *
17 * more details, a copy of which can be found in the file COPYING *
18 * included with this package. *
19 *******************************************************************/
22 * Fibre Channel SCSI LAN Device Driver CT support: FC Generic Services FC-GS
25 #include <linux/blkdev.h>
26 #include <linux/pci.h>
27 #include <linux/interrupt.h>
28 #include <linux/slab.h>
29 #include <linux/utsname.h>
31 #include <scsi/scsi.h>
32 #include <scsi/scsi_device.h>
33 #include <scsi/scsi_host.h>
34 #include <scsi/scsi_transport_fc.h>
35 #include <scsi/fc/fc_fs.h>
37 #include "lpfc_hw4.h"
38 #include "lpfc_hw.h"
39 #include "lpfc_sli.h"
40 #include "lpfc_sli4.h"
41 #include "lpfc_nl.h"
42 #include "lpfc_disc.h"
43 #include "lpfc_scsi.h"
44 #include "lpfc.h"
45 #include "lpfc_logmsg.h"
46 #include "lpfc_crtn.h"
47 #include "lpfc_version.h"
48 #include "lpfc_vport.h"
49 #include "lpfc_debugfs.h"
51 /* FDMI Port Speed definitions */
52 #define HBA_PORTSPEED_1GBIT 0x0001 /* 1 GBit/sec */
53 #define HBA_PORTSPEED_2GBIT 0x0002 /* 2 GBit/sec */
54 #define HBA_PORTSPEED_4GBIT 0x0008 /* 4 GBit/sec */
55 #define HBA_PORTSPEED_10GBIT 0x0004 /* 10 GBit/sec */
56 #define HBA_PORTSPEED_8GBIT 0x0010 /* 8 GBit/sec */
57 #define HBA_PORTSPEED_16GBIT 0x0020 /* 16 GBit/sec */
58 #define HBA_PORTSPEED_32GBIT 0x0040 /* 32 GBit/sec */
59 #define HBA_PORTSPEED_UNKNOWN 0x0800 /* Unknown */
61 #define FOURBYTES 4
64 static char *lpfc_release_version = LPFC_DRIVER_VERSION;
66 static void
67 lpfc_ct_ignore_hbq_buffer(struct lpfc_hba *phba, struct lpfc_iocbq *piocbq,
68 struct lpfc_dmabuf *mp, uint32_t size)
70 if (!mp) {
71 lpfc_printf_log(phba, KERN_INFO, LOG_ELS,
72 "0146 Ignoring unsolicited CT No HBQ "
73 "status = x%x\n",
74 piocbq->iocb.ulpStatus);
76 lpfc_printf_log(phba, KERN_INFO, LOG_ELS,
77 "0145 Ignoring unsolicted CT HBQ Size:%d "
78 "status = x%x\n",
79 size, piocbq->iocb.ulpStatus);
82 static void
83 lpfc_ct_unsol_buffer(struct lpfc_hba *phba, struct lpfc_iocbq *piocbq,
84 struct lpfc_dmabuf *mp, uint32_t size)
86 lpfc_ct_ignore_hbq_buffer(phba, piocbq, mp, size);
89 void
90 lpfc_ct_unsol_event(struct lpfc_hba *phba, struct lpfc_sli_ring *pring,
91 struct lpfc_iocbq *piocbq)
93 struct lpfc_dmabuf *mp = NULL;
94 IOCB_t *icmd = &piocbq->iocb;
95 int i;
96 struct lpfc_iocbq *iocbq;
97 dma_addr_t paddr;
98 uint32_t size;
99 struct list_head head;
100 struct lpfc_dmabuf *bdeBuf;
102 if (lpfc_bsg_ct_unsol_event(phba, pring, piocbq) == 0)
103 return;
105 if (unlikely(icmd->ulpStatus == IOSTAT_NEED_BUFFER)) {
106 lpfc_sli_hbqbuf_add_hbqs(phba, LPFC_ELS_HBQ);
107 } else if ((icmd->ulpStatus == IOSTAT_LOCAL_REJECT) &&
108 ((icmd->un.ulpWord[4] & IOERR_PARAM_MASK) ==
109 IOERR_RCV_BUFFER_WAITING)) {
110 /* Not enough posted buffers; Try posting more buffers */
111 phba->fc_stat.NoRcvBuf++;
112 if (!(phba->sli3_options & LPFC_SLI3_HBQ_ENABLED))
113 lpfc_post_buffer(phba, pring, 2);
114 return;
117 /* If there are no BDEs associated with this IOCB,
118 * there is nothing to do.
120 if (icmd->ulpBdeCount == 0)
121 return;
123 if (phba->sli3_options & LPFC_SLI3_HBQ_ENABLED) {
124 INIT_LIST_HEAD(&head);
125 list_add_tail(&head, &piocbq->list);
126 list_for_each_entry(iocbq, &head, list) {
127 icmd = &iocbq->iocb;
128 if (icmd->ulpBdeCount == 0)
129 continue;
130 bdeBuf = iocbq->context2;
131 iocbq->context2 = NULL;
132 size = icmd->un.cont64[0].tus.f.bdeSize;
133 lpfc_ct_unsol_buffer(phba, piocbq, bdeBuf, size);
134 lpfc_in_buf_free(phba, bdeBuf);
135 if (icmd->ulpBdeCount == 2) {
136 bdeBuf = iocbq->context3;
137 iocbq->context3 = NULL;
138 size = icmd->unsli3.rcvsli3.bde2.tus.f.bdeSize;
139 lpfc_ct_unsol_buffer(phba, piocbq, bdeBuf,
140 size);
141 lpfc_in_buf_free(phba, bdeBuf);
144 list_del(&head);
145 } else {
146 INIT_LIST_HEAD(&head);
147 list_add_tail(&head, &piocbq->list);
148 list_for_each_entry(iocbq, &head, list) {
149 icmd = &iocbq->iocb;
150 if (icmd->ulpBdeCount == 0)
151 lpfc_ct_unsol_buffer(phba, iocbq, NULL, 0);
152 for (i = 0; i < icmd->ulpBdeCount; i++) {
153 paddr = getPaddr(icmd->un.cont64[i].addrHigh,
154 icmd->un.cont64[i].addrLow);
155 mp = lpfc_sli_ringpostbuf_get(phba, pring,
156 paddr);
157 size = icmd->un.cont64[i].tus.f.bdeSize;
158 lpfc_ct_unsol_buffer(phba, iocbq, mp, size);
159 lpfc_in_buf_free(phba, mp);
161 lpfc_post_buffer(phba, pring, i);
163 list_del(&head);
168 * lpfc_ct_handle_unsol_abort - ct upper level protocol abort handler
169 * @phba: Pointer to HBA context object.
170 * @dmabuf: pointer to a dmabuf that describes the FC sequence
172 * This function serves as the upper level protocol abort handler for CT
173 * protocol.
175 * Return 1 if abort has been handled, 0 otherwise.
178 lpfc_ct_handle_unsol_abort(struct lpfc_hba *phba, struct hbq_dmabuf *dmabuf)
180 int handled;
182 /* CT upper level goes through BSG */
183 handled = lpfc_bsg_ct_unsol_abort(phba, dmabuf);
185 return handled;
188 static void
189 lpfc_free_ct_rsp(struct lpfc_hba *phba, struct lpfc_dmabuf *mlist)
191 struct lpfc_dmabuf *mlast, *next_mlast;
193 list_for_each_entry_safe(mlast, next_mlast, &mlist->list, list) {
194 lpfc_mbuf_free(phba, mlast->virt, mlast->phys);
195 list_del(&mlast->list);
196 kfree(mlast);
198 lpfc_mbuf_free(phba, mlist->virt, mlist->phys);
199 kfree(mlist);
200 return;
203 static struct lpfc_dmabuf *
204 lpfc_alloc_ct_rsp(struct lpfc_hba *phba, int cmdcode, struct ulp_bde64 *bpl,
205 uint32_t size, int *entries)
207 struct lpfc_dmabuf *mlist = NULL;
208 struct lpfc_dmabuf *mp;
209 int cnt, i = 0;
211 /* We get chunks of FCELSSIZE */
212 cnt = size > FCELSSIZE ? FCELSSIZE: size;
214 while (size) {
215 /* Allocate buffer for rsp payload */
216 mp = kmalloc(sizeof(struct lpfc_dmabuf), GFP_KERNEL);
217 if (!mp) {
218 if (mlist)
219 lpfc_free_ct_rsp(phba, mlist);
220 return NULL;
223 INIT_LIST_HEAD(&mp->list);
225 if (cmdcode == be16_to_cpu(SLI_CTNS_GID_FT) ||
226 cmdcode == be16_to_cpu(SLI_CTNS_GFF_ID))
227 mp->virt = lpfc_mbuf_alloc(phba, MEM_PRI, &(mp->phys));
228 else
229 mp->virt = lpfc_mbuf_alloc(phba, 0, &(mp->phys));
231 if (!mp->virt) {
232 kfree(mp);
233 if (mlist)
234 lpfc_free_ct_rsp(phba, mlist);
235 return NULL;
238 /* Queue it to a linked list */
239 if (!mlist)
240 mlist = mp;
241 else
242 list_add_tail(&mp->list, &mlist->list);
244 bpl->tus.f.bdeFlags = BUFF_TYPE_BDE_64I;
245 /* build buffer ptr list for IOCB */
246 bpl->addrLow = le32_to_cpu(putPaddrLow(mp->phys) );
247 bpl->addrHigh = le32_to_cpu(putPaddrHigh(mp->phys) );
248 bpl->tus.f.bdeSize = (uint16_t) cnt;
249 bpl->tus.w = le32_to_cpu(bpl->tus.w);
250 bpl++;
252 i++;
253 size -= cnt;
256 *entries = i;
257 return mlist;
261 lpfc_ct_free_iocb(struct lpfc_hba *phba, struct lpfc_iocbq *ctiocb)
263 struct lpfc_dmabuf *buf_ptr;
265 if (ctiocb->context_un.ndlp) {
266 lpfc_nlp_put(ctiocb->context_un.ndlp);
267 ctiocb->context_un.ndlp = NULL;
269 if (ctiocb->context1) {
270 buf_ptr = (struct lpfc_dmabuf *) ctiocb->context1;
271 lpfc_mbuf_free(phba, buf_ptr->virt, buf_ptr->phys);
272 kfree(buf_ptr);
273 ctiocb->context1 = NULL;
275 if (ctiocb->context2) {
276 lpfc_free_ct_rsp(phba, (struct lpfc_dmabuf *) ctiocb->context2);
277 ctiocb->context2 = NULL;
280 if (ctiocb->context3) {
281 buf_ptr = (struct lpfc_dmabuf *) ctiocb->context3;
282 lpfc_mbuf_free(phba, buf_ptr->virt, buf_ptr->phys);
283 kfree(buf_ptr);
284 ctiocb->context3 = NULL;
286 lpfc_sli_release_iocbq(phba, ctiocb);
287 return 0;
290 static int
291 lpfc_gen_req(struct lpfc_vport *vport, struct lpfc_dmabuf *bmp,
292 struct lpfc_dmabuf *inp, struct lpfc_dmabuf *outp,
293 void (*cmpl) (struct lpfc_hba *, struct lpfc_iocbq *,
294 struct lpfc_iocbq *),
295 struct lpfc_nodelist *ndlp, uint32_t usr_flg, uint32_t num_entry,
296 uint32_t tmo, uint8_t retry)
298 struct lpfc_hba *phba = vport->phba;
299 IOCB_t *icmd;
300 struct lpfc_iocbq *geniocb;
301 int rc;
303 /* Allocate buffer for command iocb */
304 geniocb = lpfc_sli_get_iocbq(phba);
306 if (geniocb == NULL)
307 return 1;
309 icmd = &geniocb->iocb;
310 icmd->un.genreq64.bdl.ulpIoTag32 = 0;
311 icmd->un.genreq64.bdl.addrHigh = putPaddrHigh(bmp->phys);
312 icmd->un.genreq64.bdl.addrLow = putPaddrLow(bmp->phys);
313 icmd->un.genreq64.bdl.bdeFlags = BUFF_TYPE_BLP_64;
314 icmd->un.genreq64.bdl.bdeSize = (num_entry * sizeof (struct ulp_bde64));
316 if (usr_flg)
317 geniocb->context3 = NULL;
318 else
319 geniocb->context3 = (uint8_t *) bmp;
321 /* Save for completion so we can release these resources */
322 geniocb->context1 = (uint8_t *) inp;
323 geniocb->context2 = (uint8_t *) outp;
324 geniocb->context_un.ndlp = lpfc_nlp_get(ndlp);
326 /* Fill in payload, bp points to frame payload */
327 icmd->ulpCommand = CMD_GEN_REQUEST64_CR;
329 /* Fill in rest of iocb */
330 icmd->un.genreq64.w5.hcsw.Fctl = (SI | LA);
331 icmd->un.genreq64.w5.hcsw.Dfctl = 0;
332 icmd->un.genreq64.w5.hcsw.Rctl = FC_RCTL_DD_UNSOL_CTL;
333 icmd->un.genreq64.w5.hcsw.Type = FC_TYPE_CT;
335 if (!tmo) {
336 /* FC spec states we need 3 * ratov for CT requests */
337 tmo = (3 * phba->fc_ratov);
339 icmd->ulpTimeout = tmo;
340 icmd->ulpBdeCount = 1;
341 icmd->ulpLe = 1;
342 icmd->ulpClass = CLASS3;
343 icmd->ulpContext = ndlp->nlp_rpi;
344 if (phba->sli_rev == LPFC_SLI_REV4)
345 icmd->ulpContext = phba->sli4_hba.rpi_ids[ndlp->nlp_rpi];
347 if (phba->sli3_options & LPFC_SLI3_NPIV_ENABLED) {
348 /* For GEN_REQUEST64_CR, use the RPI */
349 icmd->ulpCt_h = 0;
350 icmd->ulpCt_l = 0;
353 /* Issue GEN REQ IOCB for NPORT <did> */
354 lpfc_printf_vlog(vport, KERN_INFO, LOG_ELS,
355 "0119 Issue GEN REQ IOCB to NPORT x%x "
356 "Data: x%x x%x\n",
357 ndlp->nlp_DID, icmd->ulpIoTag,
358 vport->port_state);
359 geniocb->iocb_cmpl = cmpl;
360 geniocb->drvrTimeout = icmd->ulpTimeout + LPFC_DRVR_TIMEOUT;
361 geniocb->vport = vport;
362 geniocb->retry = retry;
363 rc = lpfc_sli_issue_iocb(phba, LPFC_ELS_RING, geniocb, 0);
365 if (rc == IOCB_ERROR) {
366 lpfc_sli_release_iocbq(phba, geniocb);
367 return 1;
370 return 0;
373 static int
374 lpfc_ct_cmd(struct lpfc_vport *vport, struct lpfc_dmabuf *inmp,
375 struct lpfc_dmabuf *bmp, struct lpfc_nodelist *ndlp,
376 void (*cmpl) (struct lpfc_hba *, struct lpfc_iocbq *,
377 struct lpfc_iocbq *),
378 uint32_t rsp_size, uint8_t retry)
380 struct lpfc_hba *phba = vport->phba;
381 struct ulp_bde64 *bpl = (struct ulp_bde64 *) bmp->virt;
382 struct lpfc_dmabuf *outmp;
383 int cnt = 0, status;
384 int cmdcode = ((struct lpfc_sli_ct_request *) inmp->virt)->
385 CommandResponse.bits.CmdRsp;
387 bpl++; /* Skip past ct request */
389 /* Put buffer(s) for ct rsp in bpl */
390 outmp = lpfc_alloc_ct_rsp(phba, cmdcode, bpl, rsp_size, &cnt);
391 if (!outmp)
392 return -ENOMEM;
394 * Form the CT IOCB. The total number of BDEs in this IOCB
395 * is the single command plus response count from
396 * lpfc_alloc_ct_rsp.
398 cnt += 1;
399 status = lpfc_gen_req(vport, bmp, inmp, outmp, cmpl, ndlp, 0,
400 cnt, 0, retry);
401 if (status) {
402 lpfc_free_ct_rsp(phba, outmp);
403 return -ENOMEM;
405 return 0;
408 struct lpfc_vport *
409 lpfc_find_vport_by_did(struct lpfc_hba *phba, uint32_t did) {
410 struct lpfc_vport *vport_curr;
411 unsigned long flags;
413 spin_lock_irqsave(&phba->hbalock, flags);
414 list_for_each_entry(vport_curr, &phba->port_list, listentry) {
415 if ((vport_curr->fc_myDID) && (vport_curr->fc_myDID == did)) {
416 spin_unlock_irqrestore(&phba->hbalock, flags);
417 return vport_curr;
420 spin_unlock_irqrestore(&phba->hbalock, flags);
421 return NULL;
424 static int
425 lpfc_ns_rsp(struct lpfc_vport *vport, struct lpfc_dmabuf *mp, uint32_t Size)
427 struct lpfc_hba *phba = vport->phba;
428 struct lpfc_sli_ct_request *Response =
429 (struct lpfc_sli_ct_request *) mp->virt;
430 struct lpfc_nodelist *ndlp = NULL;
431 struct lpfc_dmabuf *mlast, *next_mp;
432 uint32_t *ctptr = (uint32_t *) & Response->un.gid.PortType;
433 uint32_t Did, CTentry;
434 int Cnt;
435 struct list_head head;
437 lpfc_set_disctmo(vport);
438 vport->num_disc_nodes = 0;
439 vport->fc_ns_retry = 0;
442 list_add_tail(&head, &mp->list);
443 list_for_each_entry_safe(mp, next_mp, &head, list) {
444 mlast = mp;
446 Cnt = Size > FCELSSIZE ? FCELSSIZE : Size;
448 Size -= Cnt;
450 if (!ctptr) {
451 ctptr = (uint32_t *) mlast->virt;
452 } else
453 Cnt -= 16; /* subtract length of CT header */
455 /* Loop through entire NameServer list of DIDs */
456 while (Cnt >= sizeof (uint32_t)) {
457 /* Get next DID from NameServer List */
458 CTentry = *ctptr++;
459 Did = ((be32_to_cpu(CTentry)) & Mask_DID);
461 ndlp = NULL;
464 * Check for rscn processing or not
465 * To conserve rpi's, filter out addresses for other
466 * vports on the same physical HBAs.
468 if ((Did != vport->fc_myDID) &&
469 ((lpfc_find_vport_by_did(phba, Did) == NULL) ||
470 vport->cfg_peer_port_login)) {
471 if ((vport->port_type != LPFC_NPIV_PORT) ||
472 (!(vport->ct_flags & FC_CT_RFF_ID)) ||
473 (!vport->cfg_restrict_login)) {
474 ndlp = lpfc_setup_disc_node(vport, Did);
475 if (ndlp && NLP_CHK_NODE_ACT(ndlp)) {
476 lpfc_debugfs_disc_trc(vport,
477 LPFC_DISC_TRC_CT,
478 "Parse GID_FTrsp: "
479 "did:x%x flg:x%x x%x",
480 Did, ndlp->nlp_flag,
481 vport->fc_flag);
483 lpfc_printf_vlog(vport,
484 KERN_INFO,
485 LOG_DISCOVERY,
486 "0238 Process "
487 "x%x NameServer Rsp"
488 "Data: x%x x%x x%x\n",
489 Did, ndlp->nlp_flag,
490 vport->fc_flag,
491 vport->fc_rscn_id_cnt);
492 } else {
493 lpfc_debugfs_disc_trc(vport,
494 LPFC_DISC_TRC_CT,
495 "Skip1 GID_FTrsp: "
496 "did:x%x flg:x%x cnt:%d",
497 Did, vport->fc_flag,
498 vport->fc_rscn_id_cnt);
500 lpfc_printf_vlog(vport,
501 KERN_INFO,
502 LOG_DISCOVERY,
503 "0239 Skip x%x "
504 "NameServer Rsp Data: "
505 "x%x x%x\n",
506 Did, vport->fc_flag,
507 vport->fc_rscn_id_cnt);
510 } else {
511 if (!(vport->fc_flag & FC_RSCN_MODE) ||
512 (lpfc_rscn_payload_check(vport, Did))) {
513 lpfc_debugfs_disc_trc(vport,
514 LPFC_DISC_TRC_CT,
515 "Query GID_FTrsp: "
516 "did:x%x flg:x%x cnt:%d",
517 Did, vport->fc_flag,
518 vport->fc_rscn_id_cnt);
520 /* This NPortID was previously
521 * a FCP target, * Don't even
522 * bother to send GFF_ID.
524 ndlp = lpfc_findnode_did(vport,
525 Did);
526 if (ndlp &&
527 NLP_CHK_NODE_ACT(ndlp)
528 && (ndlp->nlp_type &
529 NLP_FCP_TARGET))
530 lpfc_setup_disc_node
531 (vport, Did);
532 else if (lpfc_ns_cmd(vport,
533 SLI_CTNS_GFF_ID,
534 0, Did) == 0)
535 vport->num_disc_nodes++;
536 else
537 lpfc_setup_disc_node
538 (vport, Did);
540 else {
541 lpfc_debugfs_disc_trc(vport,
542 LPFC_DISC_TRC_CT,
543 "Skip2 GID_FTrsp: "
544 "did:x%x flg:x%x cnt:%d",
545 Did, vport->fc_flag,
546 vport->fc_rscn_id_cnt);
548 lpfc_printf_vlog(vport,
549 KERN_INFO,
550 LOG_DISCOVERY,
551 "0245 Skip x%x "
552 "NameServer Rsp Data: "
553 "x%x x%x\n",
554 Did, vport->fc_flag,
555 vport->fc_rscn_id_cnt);
559 if (CTentry & (cpu_to_be32(SLI_CT_LAST_ENTRY)))
560 goto nsout1;
561 Cnt -= sizeof (uint32_t);
563 ctptr = NULL;
567 nsout1:
568 list_del(&head);
569 return 0;
572 static void
573 lpfc_cmpl_ct_cmd_gid_ft(struct lpfc_hba *phba, struct lpfc_iocbq *cmdiocb,
574 struct lpfc_iocbq *rspiocb)
576 struct lpfc_vport *vport = cmdiocb->vport;
577 struct Scsi_Host *shost = lpfc_shost_from_vport(vport);
578 IOCB_t *irsp;
579 struct lpfc_dmabuf *outp;
580 struct lpfc_sli_ct_request *CTrsp;
581 struct lpfc_nodelist *ndlp;
582 int rc;
584 /* First save ndlp, before we overwrite it */
585 ndlp = cmdiocb->context_un.ndlp;
587 /* we pass cmdiocb to state machine which needs rspiocb as well */
588 cmdiocb->context_un.rsp_iocb = rspiocb;
590 outp = (struct lpfc_dmabuf *) cmdiocb->context2;
591 irsp = &rspiocb->iocb;
593 lpfc_debugfs_disc_trc(vport, LPFC_DISC_TRC_CT,
594 "GID_FT cmpl: status:x%x/x%x rtry:%d",
595 irsp->ulpStatus, irsp->un.ulpWord[4], vport->fc_ns_retry);
597 /* Don't bother processing response if vport is being torn down. */
598 if (vport->load_flag & FC_UNLOADING) {
599 if (vport->fc_flag & FC_RSCN_MODE)
600 lpfc_els_flush_rscn(vport);
601 goto out;
604 if (lpfc_els_chk_latt(vport)) {
605 lpfc_printf_vlog(vport, KERN_INFO, LOG_DISCOVERY,
606 "0216 Link event during NS query\n");
607 if (vport->fc_flag & FC_RSCN_MODE)
608 lpfc_els_flush_rscn(vport);
609 lpfc_vport_set_state(vport, FC_VPORT_FAILED);
610 goto out;
612 if (lpfc_error_lost_link(irsp)) {
613 lpfc_printf_vlog(vport, KERN_INFO, LOG_DISCOVERY,
614 "0226 NS query failed due to link event\n");
615 if (vport->fc_flag & FC_RSCN_MODE)
616 lpfc_els_flush_rscn(vport);
617 goto out;
619 if (irsp->ulpStatus) {
620 /* Check for retry */
621 if (vport->fc_ns_retry < LPFC_MAX_NS_RETRY) {
622 if (irsp->ulpStatus != IOSTAT_LOCAL_REJECT ||
623 (irsp->un.ulpWord[4] & IOERR_PARAM_MASK) !=
624 IOERR_NO_RESOURCES)
625 vport->fc_ns_retry++;
627 /* CT command is being retried */
628 rc = lpfc_ns_cmd(vport, SLI_CTNS_GID_FT,
629 vport->fc_ns_retry, 0);
630 if (rc == 0)
631 goto out;
633 if (vport->fc_flag & FC_RSCN_MODE)
634 lpfc_els_flush_rscn(vport);
635 lpfc_vport_set_state(vport, FC_VPORT_FAILED);
636 lpfc_printf_vlog(vport, KERN_ERR, LOG_ELS,
637 "0257 GID_FT Query error: 0x%x 0x%x\n",
638 irsp->ulpStatus, vport->fc_ns_retry);
639 } else {
640 /* Good status, continue checking */
641 CTrsp = (struct lpfc_sli_ct_request *) outp->virt;
642 if (CTrsp->CommandResponse.bits.CmdRsp ==
643 cpu_to_be16(SLI_CT_RESPONSE_FS_ACC)) {
644 lpfc_printf_vlog(vport, KERN_INFO, LOG_DISCOVERY,
645 "0208 NameServer Rsp Data: x%x\n",
646 vport->fc_flag);
647 lpfc_ns_rsp(vport, outp,
648 (uint32_t) (irsp->un.genreq64.bdl.bdeSize));
649 } else if (CTrsp->CommandResponse.bits.CmdRsp ==
650 be16_to_cpu(SLI_CT_RESPONSE_FS_RJT)) {
651 /* NameServer Rsp Error */
652 if ((CTrsp->ReasonCode == SLI_CT_UNABLE_TO_PERFORM_REQ)
653 && (CTrsp->Explanation == SLI_CT_NO_FC4_TYPES)) {
654 lpfc_printf_vlog(vport, KERN_INFO,
655 LOG_DISCOVERY,
656 "0269 No NameServer Entries "
657 "Data: x%x x%x x%x x%x\n",
658 CTrsp->CommandResponse.bits.CmdRsp,
659 (uint32_t) CTrsp->ReasonCode,
660 (uint32_t) CTrsp->Explanation,
661 vport->fc_flag);
663 lpfc_debugfs_disc_trc(vport, LPFC_DISC_TRC_CT,
664 "GID_FT no entry cmd:x%x rsn:x%x exp:x%x",
665 (uint32_t)CTrsp->CommandResponse.bits.CmdRsp,
666 (uint32_t) CTrsp->ReasonCode,
667 (uint32_t) CTrsp->Explanation);
668 } else {
669 lpfc_printf_vlog(vport, KERN_INFO,
670 LOG_DISCOVERY,
671 "0240 NameServer Rsp Error "
672 "Data: x%x x%x x%x x%x\n",
673 CTrsp->CommandResponse.bits.CmdRsp,
674 (uint32_t) CTrsp->ReasonCode,
675 (uint32_t) CTrsp->Explanation,
676 vport->fc_flag);
678 lpfc_debugfs_disc_trc(vport, LPFC_DISC_TRC_CT,
679 "GID_FT rsp err1 cmd:x%x rsn:x%x exp:x%x",
680 (uint32_t)CTrsp->CommandResponse.bits.CmdRsp,
681 (uint32_t) CTrsp->ReasonCode,
682 (uint32_t) CTrsp->Explanation);
686 } else {
687 /* NameServer Rsp Error */
688 lpfc_printf_vlog(vport, KERN_ERR, LOG_DISCOVERY,
689 "0241 NameServer Rsp Error "
690 "Data: x%x x%x x%x x%x\n",
691 CTrsp->CommandResponse.bits.CmdRsp,
692 (uint32_t) CTrsp->ReasonCode,
693 (uint32_t) CTrsp->Explanation,
694 vport->fc_flag);
696 lpfc_debugfs_disc_trc(vport, LPFC_DISC_TRC_CT,
697 "GID_FT rsp err2 cmd:x%x rsn:x%x exp:x%x",
698 (uint32_t)CTrsp->CommandResponse.bits.CmdRsp,
699 (uint32_t) CTrsp->ReasonCode,
700 (uint32_t) CTrsp->Explanation);
703 /* Link up / RSCN discovery */
704 if (vport->num_disc_nodes == 0) {
706 * The driver has cycled through all Nports in the RSCN payload.
707 * Complete the handling by cleaning up and marking the
708 * current driver state.
710 if (vport->port_state >= LPFC_DISC_AUTH) {
711 if (vport->fc_flag & FC_RSCN_MODE) {
712 lpfc_els_flush_rscn(vport);
713 spin_lock_irq(shost->host_lock);
714 vport->fc_flag |= FC_RSCN_MODE; /* RSCN still */
715 spin_unlock_irq(shost->host_lock);
717 else
718 lpfc_els_flush_rscn(vport);
721 lpfc_disc_start(vport);
723 out:
724 cmdiocb->context_un.ndlp = ndlp; /* Now restore ndlp for free */
725 lpfc_ct_free_iocb(phba, cmdiocb);
726 return;
729 static void
730 lpfc_cmpl_ct_cmd_gff_id(struct lpfc_hba *phba, struct lpfc_iocbq *cmdiocb,
731 struct lpfc_iocbq *rspiocb)
733 struct lpfc_vport *vport = cmdiocb->vport;
734 struct Scsi_Host *shost = lpfc_shost_from_vport(vport);
735 IOCB_t *irsp = &rspiocb->iocb;
736 struct lpfc_dmabuf *inp = (struct lpfc_dmabuf *) cmdiocb->context1;
737 struct lpfc_dmabuf *outp = (struct lpfc_dmabuf *) cmdiocb->context2;
738 struct lpfc_sli_ct_request *CTrsp;
739 int did, rc, retry;
740 uint8_t fbits;
741 struct lpfc_nodelist *ndlp;
743 did = ((struct lpfc_sli_ct_request *) inp->virt)->un.gff.PortId;
744 did = be32_to_cpu(did);
746 lpfc_debugfs_disc_trc(vport, LPFC_DISC_TRC_CT,
747 "GFF_ID cmpl: status:x%x/x%x did:x%x",
748 irsp->ulpStatus, irsp->un.ulpWord[4], did);
750 if (irsp->ulpStatus == IOSTAT_SUCCESS) {
751 /* Good status, continue checking */
752 CTrsp = (struct lpfc_sli_ct_request *) outp->virt;
753 fbits = CTrsp->un.gff_acc.fbits[FCP_TYPE_FEATURE_OFFSET];
755 if (CTrsp->CommandResponse.bits.CmdRsp ==
756 be16_to_cpu(SLI_CT_RESPONSE_FS_ACC)) {
757 if ((fbits & FC4_FEATURE_INIT) &&
758 !(fbits & FC4_FEATURE_TARGET)) {
759 lpfc_printf_vlog(vport, KERN_INFO,
760 LOG_DISCOVERY,
761 "0270 Skip x%x GFF "
762 "NameServer Rsp Data: (init) "
763 "x%x x%x\n", did, fbits,
764 vport->fc_rscn_id_cnt);
765 goto out;
769 else {
770 /* Check for retry */
771 if (cmdiocb->retry < LPFC_MAX_NS_RETRY) {
772 retry = 1;
773 if (irsp->ulpStatus == IOSTAT_LOCAL_REJECT) {
774 switch ((irsp->un.ulpWord[4] &
775 IOERR_PARAM_MASK)) {
777 case IOERR_NO_RESOURCES:
778 /* We don't increment the retry
779 * count for this case.
781 break;
782 case IOERR_LINK_DOWN:
783 case IOERR_SLI_ABORTED:
784 case IOERR_SLI_DOWN:
785 retry = 0;
786 break;
787 default:
788 cmdiocb->retry++;
791 else
792 cmdiocb->retry++;
794 if (retry) {
795 /* CT command is being retried */
796 rc = lpfc_ns_cmd(vport, SLI_CTNS_GFF_ID,
797 cmdiocb->retry, did);
798 if (rc == 0) {
799 /* success */
800 lpfc_ct_free_iocb(phba, cmdiocb);
801 return;
805 lpfc_printf_vlog(vport, KERN_ERR, LOG_DISCOVERY,
806 "0267 NameServer GFF Rsp "
807 "x%x Error (%d %d) Data: x%x x%x\n",
808 did, irsp->ulpStatus, irsp->un.ulpWord[4],
809 vport->fc_flag, vport->fc_rscn_id_cnt);
812 /* This is a target port, unregistered port, or the GFF_ID failed */
813 ndlp = lpfc_setup_disc_node(vport, did);
814 if (ndlp && NLP_CHK_NODE_ACT(ndlp)) {
815 lpfc_printf_vlog(vport, KERN_INFO, LOG_DISCOVERY,
816 "0242 Process x%x GFF "
817 "NameServer Rsp Data: x%x x%x x%x\n",
818 did, ndlp->nlp_flag, vport->fc_flag,
819 vport->fc_rscn_id_cnt);
820 } else {
821 lpfc_printf_vlog(vport, KERN_INFO, LOG_DISCOVERY,
822 "0243 Skip x%x GFF "
823 "NameServer Rsp Data: x%x x%x\n", did,
824 vport->fc_flag, vport->fc_rscn_id_cnt);
826 out:
827 /* Link up / RSCN discovery */
828 if (vport->num_disc_nodes)
829 vport->num_disc_nodes--;
830 if (vport->num_disc_nodes == 0) {
832 * The driver has cycled through all Nports in the RSCN payload.
833 * Complete the handling by cleaning up and marking the
834 * current driver state.
836 if (vport->port_state >= LPFC_DISC_AUTH) {
837 if (vport->fc_flag & FC_RSCN_MODE) {
838 lpfc_els_flush_rscn(vport);
839 spin_lock_irq(shost->host_lock);
840 vport->fc_flag |= FC_RSCN_MODE; /* RSCN still */
841 spin_unlock_irq(shost->host_lock);
843 else
844 lpfc_els_flush_rscn(vport);
846 lpfc_disc_start(vport);
848 lpfc_ct_free_iocb(phba, cmdiocb);
849 return;
853 static void
854 lpfc_cmpl_ct(struct lpfc_hba *phba, struct lpfc_iocbq *cmdiocb,
855 struct lpfc_iocbq *rspiocb)
857 struct lpfc_vport *vport = cmdiocb->vport;
858 struct lpfc_dmabuf *inp;
859 struct lpfc_dmabuf *outp;
860 IOCB_t *irsp;
861 struct lpfc_sli_ct_request *CTrsp;
862 struct lpfc_nodelist *ndlp;
863 int cmdcode, rc;
864 uint8_t retry;
865 uint32_t latt;
867 /* First save ndlp, before we overwrite it */
868 ndlp = cmdiocb->context_un.ndlp;
870 /* we pass cmdiocb to state machine which needs rspiocb as well */
871 cmdiocb->context_un.rsp_iocb = rspiocb;
873 inp = (struct lpfc_dmabuf *) cmdiocb->context1;
874 outp = (struct lpfc_dmabuf *) cmdiocb->context2;
875 irsp = &rspiocb->iocb;
877 cmdcode = be16_to_cpu(((struct lpfc_sli_ct_request *) inp->virt)->
878 CommandResponse.bits.CmdRsp);
879 CTrsp = (struct lpfc_sli_ct_request *) outp->virt;
881 latt = lpfc_els_chk_latt(vport);
883 /* RFT request completes status <ulpStatus> CmdRsp <CmdRsp> */
884 lpfc_printf_vlog(vport, KERN_INFO, LOG_DISCOVERY,
885 "0209 CT Request completes, latt %d, "
886 "ulpStatus x%x CmdRsp x%x, Context x%x, Tag x%x\n",
887 latt, irsp->ulpStatus,
888 CTrsp->CommandResponse.bits.CmdRsp,
889 cmdiocb->iocb.ulpContext, cmdiocb->iocb.ulpIoTag);
891 lpfc_debugfs_disc_trc(vport, LPFC_DISC_TRC_CT,
892 "CT cmd cmpl: status:x%x/x%x cmd:x%x",
893 irsp->ulpStatus, irsp->un.ulpWord[4], cmdcode);
895 if (irsp->ulpStatus) {
896 lpfc_printf_vlog(vport, KERN_ERR, LOG_DISCOVERY,
897 "0268 NS cmd x%x Error (x%x x%x)\n",
898 cmdcode, irsp->ulpStatus, irsp->un.ulpWord[4]);
900 if ((irsp->ulpStatus == IOSTAT_LOCAL_REJECT) &&
901 (((irsp->un.ulpWord[4] & IOERR_PARAM_MASK) ==
902 IOERR_SLI_DOWN) ||
903 ((irsp->un.ulpWord[4] & IOERR_PARAM_MASK) ==
904 IOERR_SLI_ABORTED)))
905 goto out;
907 retry = cmdiocb->retry;
908 if (retry >= LPFC_MAX_NS_RETRY)
909 goto out;
911 retry++;
912 lpfc_printf_vlog(vport, KERN_INFO, LOG_DISCOVERY,
913 "0250 Retrying NS cmd %x\n", cmdcode);
914 rc = lpfc_ns_cmd(vport, cmdcode, retry, 0);
915 if (rc == 0)
916 goto out;
919 out:
920 cmdiocb->context_un.ndlp = ndlp; /* Now restore ndlp for free */
921 lpfc_ct_free_iocb(phba, cmdiocb);
922 return;
925 static void
926 lpfc_cmpl_ct_cmd_rft_id(struct lpfc_hba *phba, struct lpfc_iocbq *cmdiocb,
927 struct lpfc_iocbq *rspiocb)
929 IOCB_t *irsp = &rspiocb->iocb;
930 struct lpfc_vport *vport = cmdiocb->vport;
932 if (irsp->ulpStatus == IOSTAT_SUCCESS) {
933 struct lpfc_dmabuf *outp;
934 struct lpfc_sli_ct_request *CTrsp;
936 outp = (struct lpfc_dmabuf *) cmdiocb->context2;
937 CTrsp = (struct lpfc_sli_ct_request *) outp->virt;
938 if (CTrsp->CommandResponse.bits.CmdRsp ==
939 be16_to_cpu(SLI_CT_RESPONSE_FS_ACC))
940 vport->ct_flags |= FC_CT_RFT_ID;
942 lpfc_cmpl_ct(phba, cmdiocb, rspiocb);
943 return;
946 static void
947 lpfc_cmpl_ct_cmd_rnn_id(struct lpfc_hba *phba, struct lpfc_iocbq *cmdiocb,
948 struct lpfc_iocbq *rspiocb)
950 IOCB_t *irsp = &rspiocb->iocb;
951 struct lpfc_vport *vport = cmdiocb->vport;
953 if (irsp->ulpStatus == IOSTAT_SUCCESS) {
954 struct lpfc_dmabuf *outp;
955 struct lpfc_sli_ct_request *CTrsp;
957 outp = (struct lpfc_dmabuf *) cmdiocb->context2;
958 CTrsp = (struct lpfc_sli_ct_request *) outp->virt;
959 if (CTrsp->CommandResponse.bits.CmdRsp ==
960 be16_to_cpu(SLI_CT_RESPONSE_FS_ACC))
961 vport->ct_flags |= FC_CT_RNN_ID;
963 lpfc_cmpl_ct(phba, cmdiocb, rspiocb);
964 return;
967 static void
968 lpfc_cmpl_ct_cmd_rspn_id(struct lpfc_hba *phba, struct lpfc_iocbq *cmdiocb,
969 struct lpfc_iocbq *rspiocb)
971 IOCB_t *irsp = &rspiocb->iocb;
972 struct lpfc_vport *vport = cmdiocb->vport;
974 if (irsp->ulpStatus == IOSTAT_SUCCESS) {
975 struct lpfc_dmabuf *outp;
976 struct lpfc_sli_ct_request *CTrsp;
978 outp = (struct lpfc_dmabuf *) cmdiocb->context2;
979 CTrsp = (struct lpfc_sli_ct_request *) outp->virt;
980 if (CTrsp->CommandResponse.bits.CmdRsp ==
981 be16_to_cpu(SLI_CT_RESPONSE_FS_ACC))
982 vport->ct_flags |= FC_CT_RSPN_ID;
984 lpfc_cmpl_ct(phba, cmdiocb, rspiocb);
985 return;
988 static void
989 lpfc_cmpl_ct_cmd_rsnn_nn(struct lpfc_hba *phba, struct lpfc_iocbq *cmdiocb,
990 struct lpfc_iocbq *rspiocb)
992 IOCB_t *irsp = &rspiocb->iocb;
993 struct lpfc_vport *vport = cmdiocb->vport;
995 if (irsp->ulpStatus == IOSTAT_SUCCESS) {
996 struct lpfc_dmabuf *outp;
997 struct lpfc_sli_ct_request *CTrsp;
999 outp = (struct lpfc_dmabuf *) cmdiocb->context2;
1000 CTrsp = (struct lpfc_sli_ct_request *) outp->virt;
1001 if (CTrsp->CommandResponse.bits.CmdRsp ==
1002 be16_to_cpu(SLI_CT_RESPONSE_FS_ACC))
1003 vport->ct_flags |= FC_CT_RSNN_NN;
1005 lpfc_cmpl_ct(phba, cmdiocb, rspiocb);
1006 return;
1009 static void
1010 lpfc_cmpl_ct_cmd_da_id(struct lpfc_hba *phba, struct lpfc_iocbq *cmdiocb,
1011 struct lpfc_iocbq *rspiocb)
1013 struct lpfc_vport *vport = cmdiocb->vport;
1015 /* even if it fails we will act as though it succeeded. */
1016 vport->ct_flags = 0;
1017 lpfc_cmpl_ct(phba, cmdiocb, rspiocb);
1018 return;
1021 static void
1022 lpfc_cmpl_ct_cmd_rff_id(struct lpfc_hba *phba, struct lpfc_iocbq *cmdiocb,
1023 struct lpfc_iocbq *rspiocb)
1025 IOCB_t *irsp = &rspiocb->iocb;
1026 struct lpfc_vport *vport = cmdiocb->vport;
1028 if (irsp->ulpStatus == IOSTAT_SUCCESS) {
1029 struct lpfc_dmabuf *outp;
1030 struct lpfc_sli_ct_request *CTrsp;
1032 outp = (struct lpfc_dmabuf *) cmdiocb->context2;
1033 CTrsp = (struct lpfc_sli_ct_request *) outp->virt;
1034 if (CTrsp->CommandResponse.bits.CmdRsp ==
1035 be16_to_cpu(SLI_CT_RESPONSE_FS_ACC))
1036 vport->ct_flags |= FC_CT_RFF_ID;
1038 lpfc_cmpl_ct(phba, cmdiocb, rspiocb);
1039 return;
1043 lpfc_vport_symbolic_port_name(struct lpfc_vport *vport, char *symbol,
1044 size_t size)
1046 int n;
1047 uint8_t *wwn = vport->phba->wwpn;
1049 n = snprintf(symbol, size,
1050 "Emulex PPN-%02x:%02x:%02x:%02x:%02x:%02x:%02x:%02x",
1051 wwn[0], wwn[1], wwn[2], wwn[3],
1052 wwn[4], wwn[5], wwn[6], wwn[7]);
1054 if (vport->port_type == LPFC_PHYSICAL_PORT)
1055 return n;
1057 if (n < size)
1058 n += snprintf(symbol + n, size - n, " VPort-%d", vport->vpi);
1060 if (n < size &&
1061 strlen(vport->fc_vport->symbolic_name))
1062 n += snprintf(symbol + n, size - n, " VName-%s",
1063 vport->fc_vport->symbolic_name);
1064 return n;
1068 lpfc_vport_symbolic_node_name(struct lpfc_vport *vport, char *symbol,
1069 size_t size)
1071 char fwrev[FW_REV_STR_SIZE];
1072 int n;
1074 lpfc_decode_firmware_rev(vport->phba, fwrev, 0);
1076 n = snprintf(symbol, size, "Emulex %s", vport->phba->ModelName);
1078 if (size < n)
1079 return n;
1080 n += snprintf(symbol + n, size - n, " FV%s", fwrev);
1082 if (size < n)
1083 return n;
1084 n += snprintf(symbol + n, size - n, " DV%s", lpfc_release_version);
1086 if (size < n)
1087 return n;
1088 n += snprintf(symbol + n, size - n, " HN:%s", init_utsname()->nodename);
1090 /* Note :- OS name is "Linux" */
1091 if (size < n)
1092 return n;
1093 n += snprintf(symbol + n, size - n, " OS:%s", init_utsname()->sysname);
1095 return n;
1098 static uint32_t
1099 lpfc_find_map_node(struct lpfc_vport *vport)
1101 struct lpfc_nodelist *ndlp, *next_ndlp;
1102 struct Scsi_Host *shost;
1103 uint32_t cnt = 0;
1105 shost = lpfc_shost_from_vport(vport);
1106 spin_lock_irq(shost->host_lock);
1107 list_for_each_entry_safe(ndlp, next_ndlp, &vport->fc_nodes, nlp_listp) {
1108 if (ndlp->nlp_type & NLP_FABRIC)
1109 continue;
1110 if ((ndlp->nlp_state == NLP_STE_MAPPED_NODE) ||
1111 (ndlp->nlp_state == NLP_STE_UNMAPPED_NODE))
1112 cnt++;
1114 spin_unlock_irq(shost->host_lock);
1115 return cnt;
1119 * lpfc_ns_cmd
1120 * Description:
1121 * Issue Cmd to NameServer
1122 * SLI_CTNS_GID_FT
1123 * LI_CTNS_RFT_ID
1126 lpfc_ns_cmd(struct lpfc_vport *vport, int cmdcode,
1127 uint8_t retry, uint32_t context)
1129 struct lpfc_nodelist * ndlp;
1130 struct lpfc_hba *phba = vport->phba;
1131 struct lpfc_dmabuf *mp, *bmp;
1132 struct lpfc_sli_ct_request *CtReq;
1133 struct ulp_bde64 *bpl;
1134 void (*cmpl) (struct lpfc_hba *, struct lpfc_iocbq *,
1135 struct lpfc_iocbq *) = NULL;
1136 uint32_t rsp_size = 1024;
1137 size_t size;
1138 int rc = 0;
1140 ndlp = lpfc_findnode_did(vport, NameServer_DID);
1141 if (!ndlp || !NLP_CHK_NODE_ACT(ndlp)
1142 || ndlp->nlp_state != NLP_STE_UNMAPPED_NODE) {
1143 rc=1;
1144 goto ns_cmd_exit;
1147 /* fill in BDEs for command */
1148 /* Allocate buffer for command payload */
1149 mp = kmalloc(sizeof (struct lpfc_dmabuf), GFP_KERNEL);
1150 if (!mp) {
1151 rc=2;
1152 goto ns_cmd_exit;
1155 INIT_LIST_HEAD(&mp->list);
1156 mp->virt = lpfc_mbuf_alloc(phba, MEM_PRI, &(mp->phys));
1157 if (!mp->virt) {
1158 rc=3;
1159 goto ns_cmd_free_mp;
1162 /* Allocate buffer for Buffer ptr list */
1163 bmp = kmalloc(sizeof (struct lpfc_dmabuf), GFP_KERNEL);
1164 if (!bmp) {
1165 rc=4;
1166 goto ns_cmd_free_mpvirt;
1169 INIT_LIST_HEAD(&bmp->list);
1170 bmp->virt = lpfc_mbuf_alloc(phba, MEM_PRI, &(bmp->phys));
1171 if (!bmp->virt) {
1172 rc=5;
1173 goto ns_cmd_free_bmp;
1176 /* NameServer Req */
1177 lpfc_printf_vlog(vport, KERN_INFO ,LOG_DISCOVERY,
1178 "0236 NameServer Req Data: x%x x%x x%x\n",
1179 cmdcode, vport->fc_flag, vport->fc_rscn_id_cnt);
1181 bpl = (struct ulp_bde64 *) bmp->virt;
1182 memset(bpl, 0, sizeof(struct ulp_bde64));
1183 bpl->addrHigh = le32_to_cpu(putPaddrHigh(mp->phys) );
1184 bpl->addrLow = le32_to_cpu(putPaddrLow(mp->phys) );
1185 bpl->tus.f.bdeFlags = 0;
1186 if (cmdcode == SLI_CTNS_GID_FT)
1187 bpl->tus.f.bdeSize = GID_REQUEST_SZ;
1188 else if (cmdcode == SLI_CTNS_GFF_ID)
1189 bpl->tus.f.bdeSize = GFF_REQUEST_SZ;
1190 else if (cmdcode == SLI_CTNS_RFT_ID)
1191 bpl->tus.f.bdeSize = RFT_REQUEST_SZ;
1192 else if (cmdcode == SLI_CTNS_RNN_ID)
1193 bpl->tus.f.bdeSize = RNN_REQUEST_SZ;
1194 else if (cmdcode == SLI_CTNS_RSPN_ID)
1195 bpl->tus.f.bdeSize = RSPN_REQUEST_SZ;
1196 else if (cmdcode == SLI_CTNS_RSNN_NN)
1197 bpl->tus.f.bdeSize = RSNN_REQUEST_SZ;
1198 else if (cmdcode == SLI_CTNS_DA_ID)
1199 bpl->tus.f.bdeSize = DA_ID_REQUEST_SZ;
1200 else if (cmdcode == SLI_CTNS_RFF_ID)
1201 bpl->tus.f.bdeSize = RFF_REQUEST_SZ;
1202 else
1203 bpl->tus.f.bdeSize = 0;
1204 bpl->tus.w = le32_to_cpu(bpl->tus.w);
1206 CtReq = (struct lpfc_sli_ct_request *) mp->virt;
1207 memset(CtReq, 0, sizeof (struct lpfc_sli_ct_request));
1208 CtReq->RevisionId.bits.Revision = SLI_CT_REVISION;
1209 CtReq->RevisionId.bits.InId = 0;
1210 CtReq->FsType = SLI_CT_DIRECTORY_SERVICE;
1211 CtReq->FsSubType = SLI_CT_DIRECTORY_NAME_SERVER;
1212 CtReq->CommandResponse.bits.Size = 0;
1213 switch (cmdcode) {
1214 case SLI_CTNS_GID_FT:
1215 CtReq->CommandResponse.bits.CmdRsp =
1216 cpu_to_be16(SLI_CTNS_GID_FT);
1217 CtReq->un.gid.Fc4Type = SLI_CTPT_FCP;
1218 if (vport->port_state < LPFC_NS_QRY)
1219 vport->port_state = LPFC_NS_QRY;
1220 lpfc_set_disctmo(vport);
1221 cmpl = lpfc_cmpl_ct_cmd_gid_ft;
1222 rsp_size = FC_MAX_NS_RSP;
1223 break;
1225 case SLI_CTNS_GFF_ID:
1226 CtReq->CommandResponse.bits.CmdRsp =
1227 cpu_to_be16(SLI_CTNS_GFF_ID);
1228 CtReq->un.gff.PortId = cpu_to_be32(context);
1229 cmpl = lpfc_cmpl_ct_cmd_gff_id;
1230 break;
1232 case SLI_CTNS_RFT_ID:
1233 vport->ct_flags &= ~FC_CT_RFT_ID;
1234 CtReq->CommandResponse.bits.CmdRsp =
1235 cpu_to_be16(SLI_CTNS_RFT_ID);
1236 CtReq->un.rft.PortId = cpu_to_be32(vport->fc_myDID);
1237 CtReq->un.rft.fcpReg = 1;
1238 cmpl = lpfc_cmpl_ct_cmd_rft_id;
1239 break;
1241 case SLI_CTNS_RNN_ID:
1242 vport->ct_flags &= ~FC_CT_RNN_ID;
1243 CtReq->CommandResponse.bits.CmdRsp =
1244 cpu_to_be16(SLI_CTNS_RNN_ID);
1245 CtReq->un.rnn.PortId = cpu_to_be32(vport->fc_myDID);
1246 memcpy(CtReq->un.rnn.wwnn, &vport->fc_nodename,
1247 sizeof (struct lpfc_name));
1248 cmpl = lpfc_cmpl_ct_cmd_rnn_id;
1249 break;
1251 case SLI_CTNS_RSPN_ID:
1252 vport->ct_flags &= ~FC_CT_RSPN_ID;
1253 CtReq->CommandResponse.bits.CmdRsp =
1254 cpu_to_be16(SLI_CTNS_RSPN_ID);
1255 CtReq->un.rspn.PortId = cpu_to_be32(vport->fc_myDID);
1256 size = sizeof(CtReq->un.rspn.symbname);
1257 CtReq->un.rspn.len =
1258 lpfc_vport_symbolic_port_name(vport,
1259 CtReq->un.rspn.symbname, size);
1260 cmpl = lpfc_cmpl_ct_cmd_rspn_id;
1261 break;
1262 case SLI_CTNS_RSNN_NN:
1263 vport->ct_flags &= ~FC_CT_RSNN_NN;
1264 CtReq->CommandResponse.bits.CmdRsp =
1265 cpu_to_be16(SLI_CTNS_RSNN_NN);
1266 memcpy(CtReq->un.rsnn.wwnn, &vport->fc_nodename,
1267 sizeof (struct lpfc_name));
1268 size = sizeof(CtReq->un.rsnn.symbname);
1269 CtReq->un.rsnn.len =
1270 lpfc_vport_symbolic_node_name(vport,
1271 CtReq->un.rsnn.symbname, size);
1272 cmpl = lpfc_cmpl_ct_cmd_rsnn_nn;
1273 break;
1274 case SLI_CTNS_DA_ID:
1275 /* Implement DA_ID Nameserver request */
1276 CtReq->CommandResponse.bits.CmdRsp =
1277 cpu_to_be16(SLI_CTNS_DA_ID);
1278 CtReq->un.da_id.port_id = cpu_to_be32(vport->fc_myDID);
1279 cmpl = lpfc_cmpl_ct_cmd_da_id;
1280 break;
1281 case SLI_CTNS_RFF_ID:
1282 vport->ct_flags &= ~FC_CT_RFF_ID;
1283 CtReq->CommandResponse.bits.CmdRsp =
1284 cpu_to_be16(SLI_CTNS_RFF_ID);
1285 CtReq->un.rff.PortId = cpu_to_be32(vport->fc_myDID);
1286 CtReq->un.rff.fbits = FC4_FEATURE_INIT;
1287 CtReq->un.rff.type_code = FC_TYPE_FCP;
1288 cmpl = lpfc_cmpl_ct_cmd_rff_id;
1289 break;
1291 /* The lpfc_ct_cmd/lpfc_get_req shall increment ndlp reference count
1292 * to hold ndlp reference for the corresponding callback function.
1294 if (!lpfc_ct_cmd(vport, mp, bmp, ndlp, cmpl, rsp_size, retry)) {
1295 /* On success, The cmpl function will free the buffers */
1296 lpfc_debugfs_disc_trc(vport, LPFC_DISC_TRC_CT,
1297 "Issue CT cmd: cmd:x%x did:x%x",
1298 cmdcode, ndlp->nlp_DID, 0);
1299 return 0;
1301 rc=6;
1303 /* Decrement ndlp reference count to release ndlp reference held
1304 * for the failed command's callback function.
1306 lpfc_nlp_put(ndlp);
1308 lpfc_mbuf_free(phba, bmp->virt, bmp->phys);
1309 ns_cmd_free_bmp:
1310 kfree(bmp);
1311 ns_cmd_free_mpvirt:
1312 lpfc_mbuf_free(phba, mp->virt, mp->phys);
1313 ns_cmd_free_mp:
1314 kfree(mp);
1315 ns_cmd_exit:
1316 lpfc_printf_vlog(vport, KERN_ERR, LOG_DISCOVERY,
1317 "0266 Issue NameServer Req x%x err %d Data: x%x x%x\n",
1318 cmdcode, rc, vport->fc_flag, vport->fc_rscn_id_cnt);
1319 return 1;
1322 static void
1323 lpfc_cmpl_ct_cmd_fdmi(struct lpfc_hba *phba, struct lpfc_iocbq *cmdiocb,
1324 struct lpfc_iocbq * rspiocb)
1326 struct lpfc_dmabuf *inp = cmdiocb->context1;
1327 struct lpfc_dmabuf *outp = cmdiocb->context2;
1328 struct lpfc_sli_ct_request *CTrsp = outp->virt;
1329 struct lpfc_sli_ct_request *CTcmd = inp->virt;
1330 struct lpfc_nodelist *ndlp;
1331 uint16_t fdmi_cmd = CTcmd->CommandResponse.bits.CmdRsp;
1332 uint16_t fdmi_rsp = CTrsp->CommandResponse.bits.CmdRsp;
1333 struct lpfc_vport *vport = cmdiocb->vport;
1334 IOCB_t *irsp = &rspiocb->iocb;
1335 uint32_t latt;
1337 latt = lpfc_els_chk_latt(vport);
1338 lpfc_debugfs_disc_trc(vport, LPFC_DISC_TRC_CT,
1339 "FDMI cmpl: status:x%x/x%x latt:%d",
1340 irsp->ulpStatus, irsp->un.ulpWord[4], latt);
1342 if (latt || irsp->ulpStatus) {
1343 lpfc_printf_vlog(vport, KERN_INFO, LOG_DISCOVERY,
1344 "0229 FDMI cmd %04x failed, latt = %d "
1345 "ulpStatus: x%x, rid x%x\n",
1346 be16_to_cpu(fdmi_cmd), latt, irsp->ulpStatus,
1347 irsp->un.ulpWord[4]);
1348 goto fail_out;
1351 ndlp = lpfc_findnode_did(vport, FDMI_DID);
1352 if (!ndlp || !NLP_CHK_NODE_ACT(ndlp))
1353 goto fail_out;
1355 if (fdmi_rsp == cpu_to_be16(SLI_CT_RESPONSE_FS_RJT)) {
1356 /* FDMI rsp failed */
1357 lpfc_printf_vlog(vport, KERN_INFO, LOG_DISCOVERY,
1358 "0220 FDMI rsp failed Data: x%x\n",
1359 be16_to_cpu(fdmi_cmd));
1362 fail_out:
1363 lpfc_ct_free_iocb(phba, cmdiocb);
1366 static void
1367 lpfc_cmpl_ct_disc_fdmi(struct lpfc_hba *phba, struct lpfc_iocbq *cmdiocb,
1368 struct lpfc_iocbq *rspiocb)
1370 struct lpfc_vport *vport = cmdiocb->vport;
1371 struct lpfc_dmabuf *inp = cmdiocb->context1;
1372 struct lpfc_sli_ct_request *CTcmd = inp->virt;
1373 uint16_t fdmi_cmd = CTcmd->CommandResponse.bits.CmdRsp;
1374 struct lpfc_nodelist *ndlp;
1376 lpfc_cmpl_ct_cmd_fdmi(phba, cmdiocb, rspiocb);
1378 ndlp = lpfc_findnode_did(vport, FDMI_DID);
1379 if (!ndlp || !NLP_CHK_NODE_ACT(ndlp))
1380 return;
1383 * Need to cycle thru FDMI registration for discovery
1384 * DHBA -> DPRT -> RHBA -> RPA
1386 switch (be16_to_cpu(fdmi_cmd)) {
1387 case SLI_MGMT_RHBA:
1388 lpfc_fdmi_cmd(vport, ndlp, SLI_MGMT_RPA);
1389 break;
1391 case SLI_MGMT_DHBA:
1392 lpfc_fdmi_cmd(vport, ndlp, SLI_MGMT_DPRT);
1393 break;
1395 case SLI_MGMT_DPRT:
1396 lpfc_fdmi_cmd(vport, ndlp, SLI_MGMT_RHBA);
1397 break;
1403 lpfc_fdmi_cmd(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp, int cmdcode)
1405 struct lpfc_hba *phba = vport->phba;
1406 struct lpfc_dmabuf *mp, *bmp;
1407 struct lpfc_sli_ct_request *CtReq;
1408 struct ulp_bde64 *bpl;
1409 uint32_t size;
1410 uint32_t rsp_size;
1411 struct lpfc_fdmi_reg_hba *rh;
1412 struct lpfc_fdmi_port_entry *pe;
1413 struct lpfc_fdmi_reg_portattr *pab = NULL;
1414 struct lpfc_fdmi_attr_block *ab = NULL;
1415 struct lpfc_fdmi_attr_entry *ae;
1416 struct lpfc_fdmi_attr_def *ad;
1417 void (*cmpl) (struct lpfc_hba *, struct lpfc_iocbq *,
1418 struct lpfc_iocbq *);
1420 if (ndlp == NULL) {
1421 ndlp = lpfc_findnode_did(vport, FDMI_DID);
1422 if (!ndlp || !NLP_CHK_NODE_ACT(ndlp))
1423 return 0;
1424 cmpl = lpfc_cmpl_ct_cmd_fdmi; /* cmd interface */
1425 } else {
1426 cmpl = lpfc_cmpl_ct_disc_fdmi; /* called from discovery */
1429 /* fill in BDEs for command */
1430 /* Allocate buffer for command payload */
1431 mp = kmalloc(sizeof(struct lpfc_dmabuf), GFP_KERNEL);
1432 if (!mp)
1433 goto fdmi_cmd_exit;
1435 mp->virt = lpfc_mbuf_alloc(phba, 0, &(mp->phys));
1436 if (!mp->virt)
1437 goto fdmi_cmd_free_mp;
1439 /* Allocate buffer for Buffer ptr list */
1440 bmp = kmalloc(sizeof(struct lpfc_dmabuf), GFP_KERNEL);
1441 if (!bmp)
1442 goto fdmi_cmd_free_mpvirt;
1444 bmp->virt = lpfc_mbuf_alloc(phba, 0, &(bmp->phys));
1445 if (!bmp->virt)
1446 goto fdmi_cmd_free_bmp;
1448 INIT_LIST_HEAD(&mp->list);
1449 INIT_LIST_HEAD(&bmp->list);
1451 /* FDMI request */
1452 lpfc_printf_vlog(vport, KERN_INFO, LOG_DISCOVERY,
1453 "0218 FDMI Request Data: x%x x%x x%x\n",
1454 vport->fc_flag, vport->port_state, cmdcode);
1455 CtReq = (struct lpfc_sli_ct_request *)mp->virt;
1457 /* First populate the CT_IU preamble */
1458 memset(CtReq, 0, sizeof(struct lpfc_sli_ct_request));
1459 CtReq->RevisionId.bits.Revision = SLI_CT_REVISION;
1460 CtReq->RevisionId.bits.InId = 0;
1462 CtReq->FsType = SLI_CT_MANAGEMENT_SERVICE;
1463 CtReq->FsSubType = SLI_CT_FDMI_Subtypes;
1465 CtReq->CommandResponse.bits.CmdRsp = cpu_to_be16(cmdcode);
1466 rsp_size = LPFC_BPL_SIZE;
1467 size = 0;
1469 /* Next fill in the specific FDMI cmd information */
1470 switch (cmdcode) {
1471 case SLI_MGMT_RHAT:
1472 case SLI_MGMT_RHBA:
1474 lpfc_vpd_t *vp = &phba->vpd;
1475 uint32_t i, j, incr;
1476 int len = 0;
1478 rh = (struct lpfc_fdmi_reg_hba *)&CtReq->un.PortID;
1479 /* HBA Identifier */
1480 memcpy(&rh->hi.PortName, &vport->fc_sparam.portName,
1481 sizeof(struct lpfc_name));
1483 if (cmdcode == SLI_MGMT_RHBA) {
1484 /* Registered Port List */
1485 /* One entry (port) per adapter */
1486 rh->rpl.EntryCnt = cpu_to_be32(1);
1487 memcpy(&rh->rpl.pe, &vport->fc_sparam.portName,
1488 sizeof(struct lpfc_name));
1490 /* point to the HBA attribute block */
1491 size = 2 * sizeof(struct lpfc_name) +
1492 FOURBYTES;
1493 } else {
1494 size = sizeof(struct lpfc_name);
1496 ab = (struct lpfc_fdmi_attr_block *)
1497 ((uint8_t *)rh + size);
1498 ab->EntryCnt = 0;
1499 size += FOURBYTES;
1502 * Point to beginning of first HBA attribute entry
1504 /* #1 HBA attribute entry */
1505 ad = (struct lpfc_fdmi_attr_def *)
1506 ((uint8_t *)rh + size);
1507 ae = (struct lpfc_fdmi_attr_entry *)&ad->AttrValue;
1508 memset(ae, 0, sizeof(struct lpfc_name));
1509 ad->AttrType = cpu_to_be16(RHBA_NODENAME);
1510 ad->AttrLen = cpu_to_be16(FOURBYTES
1511 + sizeof(struct lpfc_name));
1512 memcpy(&ae->un.NodeName, &vport->fc_sparam.nodeName,
1513 sizeof(struct lpfc_name));
1514 ab->EntryCnt++;
1515 size += FOURBYTES + sizeof(struct lpfc_name);
1516 if ((size + LPFC_FDMI_MAX_AE_SIZE) >
1517 (LPFC_BPL_SIZE - LPFC_CT_PREAMBLE))
1518 goto hba_out;
1520 /* #2 HBA attribute entry */
1521 ad = (struct lpfc_fdmi_attr_def *)
1522 ((uint8_t *)rh + size);
1523 ae = (struct lpfc_fdmi_attr_entry *)&ad->AttrValue;
1524 memset(ae, 0, sizeof(ae->un.Manufacturer));
1525 ad->AttrType = cpu_to_be16(RHBA_MANUFACTURER);
1526 strncpy(ae->un.Manufacturer, "Emulex Corporation",
1527 sizeof(ae->un.Manufacturer));
1528 len = strnlen(ae->un.Manufacturer,
1529 sizeof(ae->un.Manufacturer));
1530 len += (len & 3) ? (4 - (len & 3)) : 4;
1531 ad->AttrLen = cpu_to_be16(FOURBYTES + len);
1532 ab->EntryCnt++;
1533 size += FOURBYTES + len;
1534 if ((size + LPFC_FDMI_MAX_AE_SIZE) >
1535 (LPFC_BPL_SIZE - LPFC_CT_PREAMBLE))
1536 goto hba_out;
1538 /* #3 HBA attribute entry */
1539 ad = (struct lpfc_fdmi_attr_def *)
1540 ((uint8_t *)rh + size);
1541 ae = (struct lpfc_fdmi_attr_entry *)&ad->AttrValue;
1542 memset(ae, 0, sizeof(ae->un.SerialNumber));
1543 ad->AttrType = cpu_to_be16(RHBA_SERIAL_NUMBER);
1544 strncpy(ae->un.SerialNumber, phba->SerialNumber,
1545 sizeof(ae->un.SerialNumber));
1546 len = strnlen(ae->un.SerialNumber,
1547 sizeof(ae->un.SerialNumber));
1548 len += (len & 3) ? (4 - (len & 3)) : 4;
1549 ad->AttrLen = cpu_to_be16(FOURBYTES + len);
1550 ab->EntryCnt++;
1551 size += FOURBYTES + len;
1552 if ((size + LPFC_FDMI_MAX_AE_SIZE) >
1553 (LPFC_BPL_SIZE - LPFC_CT_PREAMBLE))
1554 goto hba_out;
1556 /* #4 HBA attribute entry */
1557 ad = (struct lpfc_fdmi_attr_def *)
1558 ((uint8_t *)rh + size);
1559 ae = (struct lpfc_fdmi_attr_entry *)&ad->AttrValue;
1560 memset(ae, 0, sizeof(ae->un.Model));
1561 ad->AttrType = cpu_to_be16(RHBA_MODEL);
1562 strncpy(ae->un.Model, phba->ModelName,
1563 sizeof(ae->un.Model));
1564 len = strnlen(ae->un.Model, sizeof(ae->un.Model));
1565 len += (len & 3) ? (4 - (len & 3)) : 4;
1566 ad->AttrLen = cpu_to_be16(FOURBYTES + len);
1567 ab->EntryCnt++;
1568 size += FOURBYTES + len;
1569 if ((size + LPFC_FDMI_MAX_AE_SIZE) >
1570 (LPFC_BPL_SIZE - LPFC_CT_PREAMBLE))
1571 goto hba_out;
1573 /* #5 HBA attribute entry */
1574 ad = (struct lpfc_fdmi_attr_def *)
1575 ((uint8_t *)rh + size);
1576 ae = (struct lpfc_fdmi_attr_entry *)&ad->AttrValue;
1577 memset(ae, 0, sizeof(ae->un.ModelDescription));
1578 ad->AttrType = cpu_to_be16(RHBA_MODEL_DESCRIPTION);
1579 strncpy(ae->un.ModelDescription, phba->ModelDesc,
1580 sizeof(ae->un.ModelDescription));
1581 len = strnlen(ae->un.ModelDescription,
1582 sizeof(ae->un.ModelDescription));
1583 len += (len & 3) ? (4 - (len & 3)) : 4;
1584 ad->AttrLen = cpu_to_be16(FOURBYTES + len);
1585 ab->EntryCnt++;
1586 size += FOURBYTES + len;
1587 if ((size + 8) > (LPFC_BPL_SIZE - LPFC_CT_PREAMBLE))
1588 goto hba_out;
1590 /* #6 HBA attribute entry */
1591 ad = (struct lpfc_fdmi_attr_def *)
1592 ((uint8_t *)rh + size);
1593 ae = (struct lpfc_fdmi_attr_entry *)&ad->AttrValue;
1594 memset(ae, 0, 8);
1595 ad->AttrType = cpu_to_be16(RHBA_HARDWARE_VERSION);
1596 ad->AttrLen = cpu_to_be16(FOURBYTES + 8);
1597 /* Convert JEDEC ID to ascii for hardware version */
1598 incr = vp->rev.biuRev;
1599 for (i = 0; i < 8; i++) {
1600 j = (incr & 0xf);
1601 if (j <= 9)
1602 ae->un.HardwareVersion[7 - i] =
1603 (char)((uint8_t)0x30 +
1604 (uint8_t)j);
1605 else
1606 ae->un.HardwareVersion[7 - i] =
1607 (char)((uint8_t)0x61 +
1608 (uint8_t)(j - 10));
1609 incr = (incr >> 4);
1611 ab->EntryCnt++;
1612 size += FOURBYTES + 8;
1613 if ((size + LPFC_FDMI_MAX_AE_SIZE) >
1614 (LPFC_BPL_SIZE - LPFC_CT_PREAMBLE))
1615 goto hba_out;
1617 /* #7 HBA attribute entry */
1618 ad = (struct lpfc_fdmi_attr_def *)
1619 ((uint8_t *)rh + size);
1620 ae = (struct lpfc_fdmi_attr_entry *)&ad->AttrValue;
1621 memset(ae, 0, sizeof(ae->un.DriverVersion));
1622 ad->AttrType = cpu_to_be16(RHBA_DRIVER_VERSION);
1623 strncpy(ae->un.DriverVersion, lpfc_release_version,
1624 sizeof(ae->un.DriverVersion));
1625 len = strnlen(ae->un.DriverVersion,
1626 sizeof(ae->un.DriverVersion));
1627 len += (len & 3) ? (4 - (len & 3)) : 4;
1628 ad->AttrLen = cpu_to_be16(FOURBYTES + len);
1629 ab->EntryCnt++;
1630 size += FOURBYTES + len;
1631 if ((size + LPFC_FDMI_MAX_AE_SIZE) >
1632 (LPFC_BPL_SIZE - LPFC_CT_PREAMBLE))
1633 goto hba_out;
1635 /* #8 HBA attribute entry */
1636 ad = (struct lpfc_fdmi_attr_def *)
1637 ((uint8_t *)rh + size);
1638 ae = (struct lpfc_fdmi_attr_entry *)&ad->AttrValue;
1639 memset(ae, 0, sizeof(ae->un.OptionROMVersion));
1640 ad->AttrType = cpu_to_be16(RHBA_OPTION_ROM_VERSION);
1641 strncpy(ae->un.OptionROMVersion, phba->OptionROMVersion,
1642 sizeof(ae->un.OptionROMVersion));
1643 len = strnlen(ae->un.OptionROMVersion,
1644 sizeof(ae->un.OptionROMVersion));
1645 len += (len & 3) ? (4 - (len & 3)) : 4;
1646 ad->AttrLen = cpu_to_be16(FOURBYTES + len);
1647 ab->EntryCnt++;
1648 size += FOURBYTES + len;
1649 if ((size + LPFC_FDMI_MAX_AE_SIZE) >
1650 (LPFC_BPL_SIZE - LPFC_CT_PREAMBLE))
1651 goto hba_out;
1653 /* #9 HBA attribute entry */
1654 ad = (struct lpfc_fdmi_attr_def *)
1655 ((uint8_t *)rh + size);
1656 ae = (struct lpfc_fdmi_attr_entry *)&ad->AttrValue;
1657 memset(ae, 0, sizeof(ae->un.FirmwareVersion));
1658 ad->AttrType = cpu_to_be16(RHBA_FIRMWARE_VERSION);
1659 lpfc_decode_firmware_rev(phba, ae->un.FirmwareVersion,
1661 len = strnlen(ae->un.FirmwareVersion,
1662 sizeof(ae->un.FirmwareVersion));
1663 len += (len & 3) ? (4 - (len & 3)) : 4;
1664 ad->AttrLen = cpu_to_be16(FOURBYTES + len);
1665 ab->EntryCnt++;
1666 size += FOURBYTES + len;
1667 if ((size + LPFC_FDMI_MAX_AE_SIZE) >
1668 (LPFC_BPL_SIZE - LPFC_CT_PREAMBLE))
1669 goto hba_out;
1671 /* #10 HBA attribute entry */
1672 ad = (struct lpfc_fdmi_attr_def *)
1673 ((uint8_t *)rh + size);
1674 ae = (struct lpfc_fdmi_attr_entry *)&ad->AttrValue;
1675 memset(ae, 0, sizeof(ae->un.OsNameVersion));
1676 ad->AttrType = cpu_to_be16(RHBA_OS_NAME_VERSION);
1677 snprintf(ae->un.OsNameVersion,
1678 sizeof(ae->un.OsNameVersion),
1679 "%s %s %s",
1680 init_utsname()->sysname,
1681 init_utsname()->release,
1682 init_utsname()->version);
1683 len = strnlen(ae->un.OsNameVersion,
1684 sizeof(ae->un.OsNameVersion));
1685 len += (len & 3) ? (4 - (len & 3)) : 4;
1686 ad->AttrLen = cpu_to_be16(FOURBYTES + len);
1687 ab->EntryCnt++;
1688 size += FOURBYTES + len;
1689 if ((size + 4) > (LPFC_BPL_SIZE - LPFC_CT_PREAMBLE))
1690 goto hba_out;
1692 /* #11 HBA attribute entry */
1693 ad = (struct lpfc_fdmi_attr_def *)
1694 ((uint8_t *)rh + size);
1695 ae = (struct lpfc_fdmi_attr_entry *)&ad->AttrValue;
1696 ad->AttrType =
1697 cpu_to_be16(RHBA_MAX_CT_PAYLOAD_LEN);
1698 ad->AttrLen = cpu_to_be16(FOURBYTES + 4);
1699 ae->un.MaxCTPayloadLen = cpu_to_be32(LPFC_MAX_CT_SIZE);
1700 ab->EntryCnt++;
1701 size += FOURBYTES + 4;
1702 if ((size + LPFC_FDMI_MAX_AE_SIZE) >
1703 (LPFC_BPL_SIZE - LPFC_CT_PREAMBLE))
1704 goto hba_out;
1707 * Currently switches don't seem to support the
1708 * following extended HBA attributes.
1710 if (!(vport->cfg_fdmi_on & LPFC_FDMI_ALL_ATTRIB))
1711 goto hba_out;
1713 /* #12 HBA attribute entry */
1714 ad = (struct lpfc_fdmi_attr_def *)
1715 ((uint8_t *)rh + size);
1716 ae = (struct lpfc_fdmi_attr_entry *)&ad->AttrValue;
1717 memset(ae, 0, sizeof(ae->un.NodeSymName));
1718 ad->AttrType = cpu_to_be16(RHBA_SYM_NODENAME);
1719 len = lpfc_vport_symbolic_node_name(vport,
1720 ae->un.NodeSymName, sizeof(ae->un.NodeSymName));
1721 len += (len & 3) ? (4 - (len & 3)) : 4;
1722 ad->AttrLen = cpu_to_be16(FOURBYTES + len);
1723 ab->EntryCnt++;
1724 size += FOURBYTES + len;
1725 hba_out:
1726 ab->EntryCnt = cpu_to_be32(ab->EntryCnt);
1727 /* Total size */
1728 size = GID_REQUEST_SZ - 4 + size;
1730 break;
1732 case SLI_MGMT_RPRT:
1733 case SLI_MGMT_RPA:
1735 struct serv_parm *hsp;
1736 int len = 0;
1738 if (cmdcode == SLI_MGMT_RPRT) {
1739 rh = (struct lpfc_fdmi_reg_hba *)
1740 &CtReq->un.PortID;
1741 /* HBA Identifier */
1742 memcpy(&rh->hi.PortName,
1743 &vport->fc_sparam.portName,
1744 sizeof(struct lpfc_name));
1745 pab = (struct lpfc_fdmi_reg_portattr *)
1746 &rh->rpl.EntryCnt;
1747 } else
1748 pab = (struct lpfc_fdmi_reg_portattr *)
1749 &CtReq->un.PortID;
1750 size = sizeof(struct lpfc_name) + FOURBYTES;
1751 memcpy((uint8_t *)&pab->PortName,
1752 (uint8_t *)&vport->fc_sparam.portName,
1753 sizeof(struct lpfc_name));
1754 pab->ab.EntryCnt = 0;
1756 /* #1 Port attribute entry */
1757 ad = (struct lpfc_fdmi_attr_def *)
1758 ((uint8_t *)pab + size);
1759 ae = (struct lpfc_fdmi_attr_entry *)&ad->AttrValue;
1760 memset(ae, 0, sizeof(ae->un.FC4Types));
1761 ad->AttrType =
1762 cpu_to_be16(RPRT_SUPPORTED_FC4_TYPES);
1763 ad->AttrLen = cpu_to_be16(FOURBYTES + 32);
1764 ae->un.FC4Types[0] = 0x40; /* Type 1 - ELS */
1765 ae->un.FC4Types[1] = 0x80; /* Type 8 - FCP */
1766 ae->un.FC4Types[4] = 0x80; /* Type 32 - CT */
1767 pab->ab.EntryCnt++;
1768 size += FOURBYTES + 32;
1770 /* #2 Port attribute entry */
1771 ad = (struct lpfc_fdmi_attr_def *)
1772 ((uint8_t *)pab + size);
1773 ae = (struct lpfc_fdmi_attr_entry *)&ad->AttrValue;
1774 ad->AttrType = cpu_to_be16(RPRT_SUPPORTED_SPEED);
1775 ad->AttrLen = cpu_to_be16(FOURBYTES + 4);
1776 ae->un.SupportSpeed = 0;
1777 if (phba->lmt & LMT_32Gb)
1778 ae->un.SupportSpeed |= HBA_PORTSPEED_32GBIT;
1779 if (phba->lmt & LMT_16Gb)
1780 ae->un.SupportSpeed |= HBA_PORTSPEED_16GBIT;
1781 if (phba->lmt & LMT_10Gb)
1782 ae->un.SupportSpeed |= HBA_PORTSPEED_10GBIT;
1783 if (phba->lmt & LMT_8Gb)
1784 ae->un.SupportSpeed |= HBA_PORTSPEED_8GBIT;
1785 if (phba->lmt & LMT_4Gb)
1786 ae->un.SupportSpeed |= HBA_PORTSPEED_4GBIT;
1787 if (phba->lmt & LMT_2Gb)
1788 ae->un.SupportSpeed |= HBA_PORTSPEED_2GBIT;
1789 if (phba->lmt & LMT_1Gb)
1790 ae->un.SupportSpeed |= HBA_PORTSPEED_1GBIT;
1791 ae->un.SupportSpeed =
1792 cpu_to_be32(ae->un.SupportSpeed);
1794 pab->ab.EntryCnt++;
1795 size += FOURBYTES + 4;
1797 /* #3 Port attribute entry */
1798 ad = (struct lpfc_fdmi_attr_def *)
1799 ((uint8_t *)pab + size);
1800 ae = (struct lpfc_fdmi_attr_entry *)&ad->AttrValue;
1801 ad->AttrType = cpu_to_be16(RPRT_PORT_SPEED);
1802 ad->AttrLen = cpu_to_be16(FOURBYTES + 4);
1803 switch (phba->fc_linkspeed) {
1804 case LPFC_LINK_SPEED_1GHZ:
1805 ae->un.PortSpeed = HBA_PORTSPEED_1GBIT;
1806 break;
1807 case LPFC_LINK_SPEED_2GHZ:
1808 ae->un.PortSpeed = HBA_PORTSPEED_2GBIT;
1809 break;
1810 case LPFC_LINK_SPEED_4GHZ:
1811 ae->un.PortSpeed = HBA_PORTSPEED_4GBIT;
1812 break;
1813 case LPFC_LINK_SPEED_8GHZ:
1814 ae->un.PortSpeed = HBA_PORTSPEED_8GBIT;
1815 break;
1816 case LPFC_LINK_SPEED_10GHZ:
1817 ae->un.PortSpeed = HBA_PORTSPEED_10GBIT;
1818 break;
1819 case LPFC_LINK_SPEED_16GHZ:
1820 ae->un.PortSpeed = HBA_PORTSPEED_16GBIT;
1821 break;
1822 case LPFC_LINK_SPEED_32GHZ:
1823 ae->un.PortSpeed = HBA_PORTSPEED_32GBIT;
1824 break;
1825 default:
1826 ae->un.PortSpeed = HBA_PORTSPEED_UNKNOWN;
1827 break;
1829 ae->un.PortSpeed = cpu_to_be32(ae->un.PortSpeed);
1830 pab->ab.EntryCnt++;
1831 size += FOURBYTES + 4;
1833 /* #4 Port attribute entry */
1834 ad = (struct lpfc_fdmi_attr_def *)
1835 ((uint8_t *)pab + size);
1836 ae = (struct lpfc_fdmi_attr_entry *)&ad->AttrValue;
1837 ad->AttrType = cpu_to_be16(RPRT_MAX_FRAME_SIZE);
1838 ad->AttrLen = cpu_to_be16(FOURBYTES + 4);
1839 hsp = (struct serv_parm *)&vport->fc_sparam;
1840 ae->un.MaxFrameSize =
1841 (((uint32_t)hsp->cmn.
1842 bbRcvSizeMsb) << 8) | (uint32_t)hsp->cmn.
1843 bbRcvSizeLsb;
1844 ae->un.MaxFrameSize =
1845 cpu_to_be32(ae->un.MaxFrameSize);
1846 pab->ab.EntryCnt++;
1847 size += FOURBYTES + 4;
1848 if ((size + LPFC_FDMI_MAX_AE_SIZE) >
1849 (LPFC_BPL_SIZE - LPFC_CT_PREAMBLE))
1850 goto port_out;
1852 /* #5 Port attribute entry */
1853 ad = (struct lpfc_fdmi_attr_def *)
1854 ((uint8_t *)pab + size);
1855 ae = (struct lpfc_fdmi_attr_entry *)&ad->AttrValue;
1856 memset(ae, 0, sizeof(ae->un.OsDeviceName));
1857 ad->AttrType = cpu_to_be16(RPRT_OS_DEVICE_NAME);
1858 strncpy((char *)ae->un.OsDeviceName, LPFC_DRIVER_NAME,
1859 sizeof(ae->un.OsDeviceName));
1860 len = strnlen((char *)ae->un.OsDeviceName,
1861 sizeof(ae->un.OsDeviceName));
1862 len += (len & 3) ? (4 - (len & 3)) : 4;
1863 ad->AttrLen = cpu_to_be16(FOURBYTES + len);
1864 pab->ab.EntryCnt++;
1865 size += FOURBYTES + len;
1866 if ((size + LPFC_FDMI_MAX_AE_SIZE) >
1867 (LPFC_BPL_SIZE - LPFC_CT_PREAMBLE))
1868 goto port_out;
1870 /* #6 Port attribute entry */
1871 ad = (struct lpfc_fdmi_attr_def *)
1872 ((uint8_t *)pab + size);
1873 ae = (struct lpfc_fdmi_attr_entry *)&ad->AttrValue;
1874 memset(ae, 0, sizeof(ae->un.HostName));
1875 snprintf(ae->un.HostName, sizeof(ae->un.HostName), "%s",
1876 init_utsname()->nodename);
1877 ad->AttrType = cpu_to_be16(RPRT_HOST_NAME);
1878 len = strnlen(ae->un.HostName,
1879 sizeof(ae->un.HostName));
1880 len += (len & 3) ? (4 - (len & 3)) : 4;
1881 ad->AttrLen =
1882 cpu_to_be16(FOURBYTES + len);
1883 pab->ab.EntryCnt++;
1884 size += FOURBYTES + len;
1885 if ((size + sizeof(struct lpfc_name)) >
1886 (LPFC_BPL_SIZE - LPFC_CT_PREAMBLE))
1887 goto port_out;
1890 * Currently switches don't seem to support the
1891 * following extended Port attributes.
1893 if (!(vport->cfg_fdmi_on & LPFC_FDMI_ALL_ATTRIB))
1894 goto port_out;
1896 /* #7 Port attribute entry */
1897 ad = (struct lpfc_fdmi_attr_def *)
1898 ((uint8_t *)pab + size);
1899 ae = (struct lpfc_fdmi_attr_entry *)&ad->AttrValue;
1900 memset(ae, 0, sizeof(struct lpfc_name));
1901 ad->AttrType = cpu_to_be16(RPRT_NODENAME);
1902 ad->AttrLen = cpu_to_be16(FOURBYTES
1903 + sizeof(struct lpfc_name));
1904 memcpy(&ae->un.NodeName, &vport->fc_sparam.nodeName,
1905 sizeof(struct lpfc_name));
1906 pab->ab.EntryCnt++;
1907 size += FOURBYTES + sizeof(struct lpfc_name);
1908 if ((size + sizeof(struct lpfc_name)) >
1909 (LPFC_BPL_SIZE - LPFC_CT_PREAMBLE))
1910 goto port_out;
1912 /* #8 Port attribute entry */
1913 ad = (struct lpfc_fdmi_attr_def *)
1914 ((uint8_t *)pab + size);
1915 ae = (struct lpfc_fdmi_attr_entry *)&ad->AttrValue;
1916 memset(ae, 0, sizeof(struct lpfc_name));
1917 ad->AttrType = cpu_to_be16(RPRT_PORTNAME);
1918 ad->AttrLen = cpu_to_be16(FOURBYTES
1919 + sizeof(struct lpfc_name));
1920 memcpy(&ae->un.PortName, &vport->fc_sparam.portName,
1921 sizeof(struct lpfc_name));
1922 pab->ab.EntryCnt++;
1923 size += FOURBYTES + sizeof(struct lpfc_name);
1924 if ((size + LPFC_FDMI_MAX_AE_SIZE) >
1925 (LPFC_BPL_SIZE - LPFC_CT_PREAMBLE))
1926 goto port_out;
1928 /* #9 Port attribute entry */
1929 ad = (struct lpfc_fdmi_attr_def *)
1930 ((uint8_t *)pab + size);
1931 ae = (struct lpfc_fdmi_attr_entry *)&ad->AttrValue;
1932 memset(ae, 0, sizeof(ae->un.NodeSymName));
1933 ad->AttrType = cpu_to_be16(RPRT_SYM_PORTNAME);
1934 len = lpfc_vport_symbolic_port_name(vport,
1935 ae->un.NodeSymName, sizeof(ae->un.NodeSymName));
1936 len += (len & 3) ? (4 - (len & 3)) : 4;
1937 ad->AttrLen = cpu_to_be16(FOURBYTES + len);
1938 pab->ab.EntryCnt++;
1939 size += FOURBYTES + len;
1940 if ((size + 4) > (LPFC_BPL_SIZE - LPFC_CT_PREAMBLE))
1941 goto port_out;
1943 /* #10 Port attribute entry */
1944 ad = (struct lpfc_fdmi_attr_def *)
1945 ((uint8_t *)pab + size);
1946 ae = (struct lpfc_fdmi_attr_entry *)&ad->AttrValue;
1947 ad->AttrType = cpu_to_be16(RPRT_PORT_TYPE);
1948 ae->un.PortState = 0;
1949 ad->AttrLen = cpu_to_be16(FOURBYTES + 4);
1950 pab->ab.EntryCnt++;
1951 size += FOURBYTES + 4;
1952 if ((size + 4) > (LPFC_BPL_SIZE - LPFC_CT_PREAMBLE))
1953 goto port_out;
1955 /* #11 Port attribute entry */
1956 ad = (struct lpfc_fdmi_attr_def *)
1957 ((uint8_t *)pab + size);
1958 ae = (struct lpfc_fdmi_attr_entry *)&ad->AttrValue;
1959 ad->AttrType = cpu_to_be16(RPRT_SUPPORTED_CLASS);
1960 ae->un.SupportClass =
1961 cpu_to_be32(FC_COS_CLASS2 | FC_COS_CLASS3);
1962 ad->AttrLen = cpu_to_be16(FOURBYTES + 4);
1963 pab->ab.EntryCnt++;
1964 size += FOURBYTES + 4;
1965 if ((size + sizeof(struct lpfc_name)) >
1966 (LPFC_BPL_SIZE - LPFC_CT_PREAMBLE))
1967 goto port_out;
1969 /* #12 Port attribute entry */
1970 ad = (struct lpfc_fdmi_attr_def *)
1971 ((uint8_t *)pab + size);
1972 ae = (struct lpfc_fdmi_attr_entry *)&ad->AttrValue;
1973 memset(ae, 0, sizeof(struct lpfc_name));
1974 ad->AttrType = cpu_to_be16(RPRT_FABRICNAME);
1975 ad->AttrLen = cpu_to_be16(FOURBYTES
1976 + sizeof(struct lpfc_name));
1977 memcpy(&ae->un.FabricName, &vport->fabric_nodename,
1978 sizeof(struct lpfc_name));
1979 pab->ab.EntryCnt++;
1980 size += FOURBYTES + sizeof(struct lpfc_name);
1981 if ((size + LPFC_FDMI_MAX_AE_SIZE) >
1982 (LPFC_BPL_SIZE - LPFC_CT_PREAMBLE))
1983 goto port_out;
1985 /* #13 Port attribute entry */
1986 ad = (struct lpfc_fdmi_attr_def *)
1987 ((uint8_t *)pab + size);
1988 ae = (struct lpfc_fdmi_attr_entry *)&ad->AttrValue;
1989 memset(ae, 0, sizeof(ae->un.FC4Types));
1990 ad->AttrType =
1991 cpu_to_be16(RPRT_ACTIVE_FC4_TYPES);
1992 ad->AttrLen = cpu_to_be16(FOURBYTES + 32);
1993 ae->un.FC4Types[0] = 0x40; /* Type 1 - ELS */
1994 ae->un.FC4Types[1] = 0x80; /* Type 8 - FCP */
1995 ae->un.FC4Types[4] = 0x80; /* Type 32 - CT */
1996 pab->ab.EntryCnt++;
1997 size += FOURBYTES + 32;
1998 if ((size + 4) > (LPFC_BPL_SIZE - LPFC_CT_PREAMBLE))
1999 goto port_out;
2001 /* #257 Port attribute entry */
2002 ad = (struct lpfc_fdmi_attr_def *)
2003 ((uint8_t *)pab + size);
2004 ae = (struct lpfc_fdmi_attr_entry *)&ad->AttrValue;
2005 ad->AttrType = cpu_to_be16(RPRT_PORT_STATE);
2006 ae->un.PortState = 0;
2007 ad->AttrLen = cpu_to_be16(FOURBYTES + 4);
2008 pab->ab.EntryCnt++;
2009 size += FOURBYTES + 4;
2010 if ((size + 4) > (LPFC_BPL_SIZE - LPFC_CT_PREAMBLE))
2011 goto port_out;
2013 /* #258 Port attribute entry */
2014 ad = (struct lpfc_fdmi_attr_def *)
2015 ((uint8_t *)pab + size);
2016 ae = (struct lpfc_fdmi_attr_entry *)&ad->AttrValue;
2017 ad->AttrType = cpu_to_be16(RPRT_DISC_PORT);
2018 ae->un.PortState = lpfc_find_map_node(vport);
2019 ae->un.PortState = cpu_to_be32(ae->un.PortState);
2020 ad->AttrLen = cpu_to_be16(FOURBYTES + 4);
2021 pab->ab.EntryCnt++;
2022 size += FOURBYTES + 4;
2023 if ((size + 4) > (LPFC_BPL_SIZE - LPFC_CT_PREAMBLE))
2024 goto port_out;
2026 /* #259 Port attribute entry */
2027 ad = (struct lpfc_fdmi_attr_def *)
2028 ((uint8_t *)pab + size);
2029 ae = (struct lpfc_fdmi_attr_entry *)&ad->AttrValue;
2030 ad->AttrType = cpu_to_be16(RPRT_PORT_ID);
2031 ae->un.PortId = cpu_to_be32(vport->fc_myDID);
2032 ad->AttrLen = cpu_to_be16(FOURBYTES + 4);
2033 pab->ab.EntryCnt++;
2034 size += FOURBYTES + 4;
2035 port_out:
2036 pab->ab.EntryCnt = cpu_to_be32(pab->ab.EntryCnt);
2037 /* Total size */
2038 size = GID_REQUEST_SZ - 4 + size;
2040 break;
2042 case SLI_MGMT_GHAT:
2043 case SLI_MGMT_GRPL:
2044 rsp_size = FC_MAX_NS_RSP;
2045 case SLI_MGMT_DHBA:
2046 case SLI_MGMT_DHAT:
2047 pe = (struct lpfc_fdmi_port_entry *)&CtReq->un.PortID;
2048 memcpy((uint8_t *)&pe->PortName,
2049 (uint8_t *)&vport->fc_sparam.portName,
2050 sizeof(struct lpfc_name));
2051 size = GID_REQUEST_SZ - 4 + sizeof(struct lpfc_name);
2052 break;
2054 case SLI_MGMT_GPAT:
2055 case SLI_MGMT_GPAS:
2056 rsp_size = FC_MAX_NS_RSP;
2057 case SLI_MGMT_DPRT:
2058 case SLI_MGMT_DPA:
2059 pe = (struct lpfc_fdmi_port_entry *)&CtReq->un.PortID;
2060 memcpy((uint8_t *)&pe->PortName,
2061 (uint8_t *)&vport->fc_sparam.portName,
2062 sizeof(struct lpfc_name));
2063 size = GID_REQUEST_SZ - 4 + sizeof(struct lpfc_name);
2064 break;
2065 case SLI_MGMT_GRHL:
2066 size = GID_REQUEST_SZ - 4;
2067 break;
2068 default:
2069 lpfc_printf_vlog(vport, KERN_WARNING, LOG_DISCOVERY,
2070 "0298 FDMI cmdcode x%x not supported\n",
2071 cmdcode);
2072 goto fdmi_cmd_free_bmpvirt;
2074 CtReq->CommandResponse.bits.Size = cpu_to_be16(rsp_size);
2076 bpl = (struct ulp_bde64 *)bmp->virt;
2077 bpl->addrHigh = le32_to_cpu(putPaddrHigh(mp->phys));
2078 bpl->addrLow = le32_to_cpu(putPaddrLow(mp->phys));
2079 bpl->tus.f.bdeFlags = 0;
2080 bpl->tus.f.bdeSize = size;
2083 * The lpfc_ct_cmd/lpfc_get_req shall increment ndlp reference count
2084 * to hold ndlp reference for the corresponding callback function.
2086 if (!lpfc_ct_cmd(vport, mp, bmp, ndlp, cmpl, rsp_size, 0))
2087 return 0;
2090 * Decrement ndlp reference count to release ndlp reference held
2091 * for the failed command's callback function.
2093 lpfc_nlp_put(ndlp);
2095 fdmi_cmd_free_bmpvirt:
2096 lpfc_mbuf_free(phba, bmp->virt, bmp->phys);
2097 fdmi_cmd_free_bmp:
2098 kfree(bmp);
2099 fdmi_cmd_free_mpvirt:
2100 lpfc_mbuf_free(phba, mp->virt, mp->phys);
2101 fdmi_cmd_free_mp:
2102 kfree(mp);
2103 fdmi_cmd_exit:
2104 /* Issue FDMI request failed */
2105 lpfc_printf_vlog(vport, KERN_INFO, LOG_DISCOVERY,
2106 "0244 Issue FDMI request failed Data: x%x\n",
2107 cmdcode);
2108 return 1;
2112 * lpfc_delayed_disc_tmo - Timeout handler for delayed discovery timer.
2113 * @ptr - Context object of the timer.
2115 * This function set the WORKER_DELAYED_DISC_TMO flag and wake up
2116 * the worker thread.
2118 void
2119 lpfc_delayed_disc_tmo(unsigned long ptr)
2121 struct lpfc_vport *vport = (struct lpfc_vport *)ptr;
2122 struct lpfc_hba *phba = vport->phba;
2123 uint32_t tmo_posted;
2124 unsigned long iflag;
2126 spin_lock_irqsave(&vport->work_port_lock, iflag);
2127 tmo_posted = vport->work_port_events & WORKER_DELAYED_DISC_TMO;
2128 if (!tmo_posted)
2129 vport->work_port_events |= WORKER_DELAYED_DISC_TMO;
2130 spin_unlock_irqrestore(&vport->work_port_lock, iflag);
2132 if (!tmo_posted)
2133 lpfc_worker_wake_up(phba);
2134 return;
2138 * lpfc_delayed_disc_timeout_handler - Function called by worker thread to
2139 * handle delayed discovery.
2140 * @vport: pointer to a host virtual N_Port data structure.
2142 * This function start nport discovery of the vport.
2144 void
2145 lpfc_delayed_disc_timeout_handler(struct lpfc_vport *vport)
2147 struct Scsi_Host *shost = lpfc_shost_from_vport(vport);
2149 spin_lock_irq(shost->host_lock);
2150 if (!(vport->fc_flag & FC_DISC_DELAYED)) {
2151 spin_unlock_irq(shost->host_lock);
2152 return;
2154 vport->fc_flag &= ~FC_DISC_DELAYED;
2155 spin_unlock_irq(shost->host_lock);
2157 lpfc_do_scr_ns_plogi(vport->phba, vport);
2160 void
2161 lpfc_fdmi_tmo(unsigned long ptr)
2163 struct lpfc_vport *vport = (struct lpfc_vport *)ptr;
2164 struct lpfc_hba *phba = vport->phba;
2165 uint32_t tmo_posted;
2166 unsigned long iflag;
2168 spin_lock_irqsave(&vport->work_port_lock, iflag);
2169 tmo_posted = vport->work_port_events & WORKER_FDMI_TMO;
2170 if (!tmo_posted)
2171 vport->work_port_events |= WORKER_FDMI_TMO;
2172 spin_unlock_irqrestore(&vport->work_port_lock, iflag);
2174 if (!tmo_posted)
2175 lpfc_worker_wake_up(phba);
2176 return;
2179 void
2180 lpfc_fdmi_timeout_handler(struct lpfc_vport *vport)
2182 struct lpfc_nodelist *ndlp;
2184 ndlp = lpfc_findnode_did(vport, FDMI_DID);
2185 if (ndlp && NLP_CHK_NODE_ACT(ndlp)) {
2186 if (init_utsname()->nodename[0] != '\0')
2187 lpfc_fdmi_cmd(vport, ndlp, SLI_MGMT_DHBA);
2188 else
2189 mod_timer(&vport->fc_fdmitmo, jiffies +
2190 msecs_to_jiffies(1000 * 60));
2192 return;
2195 void
2196 lpfc_decode_firmware_rev(struct lpfc_hba *phba, char *fwrevision, int flag)
2198 struct lpfc_sli *psli = &phba->sli;
2199 lpfc_vpd_t *vp = &phba->vpd;
2200 uint32_t b1, b2, b3, b4, i, rev;
2201 char c;
2202 uint32_t *ptr, str[4];
2203 uint8_t *fwname;
2205 if (phba->sli_rev == LPFC_SLI_REV4)
2206 snprintf(fwrevision, FW_REV_STR_SIZE, "%s", vp->rev.opFwName);
2207 else if (vp->rev.rBit) {
2208 if (psli->sli_flag & LPFC_SLI_ACTIVE)
2209 rev = vp->rev.sli2FwRev;
2210 else
2211 rev = vp->rev.sli1FwRev;
2213 b1 = (rev & 0x0000f000) >> 12;
2214 b2 = (rev & 0x00000f00) >> 8;
2215 b3 = (rev & 0x000000c0) >> 6;
2216 b4 = (rev & 0x00000030) >> 4;
2218 switch (b4) {
2219 case 0:
2220 c = 'N';
2221 break;
2222 case 1:
2223 c = 'A';
2224 break;
2225 case 2:
2226 c = 'B';
2227 break;
2228 case 3:
2229 c = 'X';
2230 break;
2231 default:
2232 c = 0;
2233 break;
2235 b4 = (rev & 0x0000000f);
2237 if (psli->sli_flag & LPFC_SLI_ACTIVE)
2238 fwname = vp->rev.sli2FwName;
2239 else
2240 fwname = vp->rev.sli1FwName;
2242 for (i = 0; i < 16; i++)
2243 if (fwname[i] == 0x20)
2244 fwname[i] = 0;
2246 ptr = (uint32_t*)fwname;
2248 for (i = 0; i < 3; i++)
2249 str[i] = be32_to_cpu(*ptr++);
2251 if (c == 0) {
2252 if (flag)
2253 sprintf(fwrevision, "%d.%d%d (%s)",
2254 b1, b2, b3, (char *)str);
2255 else
2256 sprintf(fwrevision, "%d.%d%d", b1,
2257 b2, b3);
2258 } else {
2259 if (flag)
2260 sprintf(fwrevision, "%d.%d%d%c%d (%s)",
2261 b1, b2, b3, c,
2262 b4, (char *)str);
2263 else
2264 sprintf(fwrevision, "%d.%d%d%c%d",
2265 b1, b2, b3, c, b4);
2267 } else {
2268 rev = vp->rev.smFwRev;
2270 b1 = (rev & 0xff000000) >> 24;
2271 b2 = (rev & 0x00f00000) >> 20;
2272 b3 = (rev & 0x000f0000) >> 16;
2273 c = (rev & 0x0000ff00) >> 8;
2274 b4 = (rev & 0x000000ff);
2276 sprintf(fwrevision, "%d.%d%d%c%d", b1, b2, b3, c, b4);
2278 return;