Linux Kernel  3.7.1
 All Data Structures Namespaces Files Functions Variables Typedefs Enumerations Enumerator Macros Groups Pages
bfad_attr.c
Go to the documentation of this file.
1 /*
2  * Copyright (c) 2005-2010 Brocade Communications Systems, Inc.
3  * All rights reserved
4  * www.brocade.com
5  *
6  * Linux driver for Brocade Fibre Channel Host Bus Adapter.
7  *
8  * This program is free software; you can redistribute it and/or modify it
9  * under the terms of the GNU General Public License (GPL) Version 2 as
10  * published by the Free Software Foundation
11  *
12  * This program is distributed in the hope that it will be useful, but
13  * WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15  * General Public License for more details.
16  */
17 
18 /*
19  * bfa_attr.c Linux driver configuration interface module.
20  */
21 
22 #include "bfad_drv.h"
23 #include "bfad_im.h"
24 
25 /*
26  * FC transport template entry, get SCSI target port ID.
27  */
28 static void
29 bfad_im_get_starget_port_id(struct scsi_target *starget)
30 {
31  struct Scsi_Host *shost;
32  struct bfad_im_port_s *im_port;
33  struct bfad_s *bfad;
34  struct bfad_itnim_s *itnim = NULL;
35  u32 fc_id = -1;
36  unsigned long flags;
37 
38  shost = dev_to_shost(starget->dev.parent);
39  im_port = (struct bfad_im_port_s *) shost->hostdata[0];
40  bfad = im_port->bfad;
41  spin_lock_irqsave(&bfad->bfad_lock, flags);
42 
43  itnim = bfad_get_itnim(im_port, starget->id);
44  if (itnim)
45  fc_id = bfa_fcs_itnim_get_fcid(&itnim->fcs_itnim);
46 
47  fc_starget_port_id(starget) = fc_id;
48  spin_unlock_irqrestore(&bfad->bfad_lock, flags);
49 }
50 
51 /*
52  * FC transport template entry, get SCSI target nwwn.
53  */
54 static void
55 bfad_im_get_starget_node_name(struct scsi_target *starget)
56 {
57  struct Scsi_Host *shost;
58  struct bfad_im_port_s *im_port;
59  struct bfad_s *bfad;
60  struct bfad_itnim_s *itnim = NULL;
61  u64 node_name = 0;
62  unsigned long flags;
63 
64  shost = dev_to_shost(starget->dev.parent);
65  im_port = (struct bfad_im_port_s *) shost->hostdata[0];
66  bfad = im_port->bfad;
67  spin_lock_irqsave(&bfad->bfad_lock, flags);
68 
69  itnim = bfad_get_itnim(im_port, starget->id);
70  if (itnim)
71  node_name = bfa_fcs_itnim_get_nwwn(&itnim->fcs_itnim);
72 
73  fc_starget_node_name(starget) = cpu_to_be64(node_name);
74  spin_unlock_irqrestore(&bfad->bfad_lock, flags);
75 }
76 
77 /*
78  * FC transport template entry, get SCSI target pwwn.
79  */
80 static void
81 bfad_im_get_starget_port_name(struct scsi_target *starget)
82 {
83  struct Scsi_Host *shost;
84  struct bfad_im_port_s *im_port;
85  struct bfad_s *bfad;
86  struct bfad_itnim_s *itnim = NULL;
87  u64 port_name = 0;
88  unsigned long flags;
89 
90  shost = dev_to_shost(starget->dev.parent);
91  im_port = (struct bfad_im_port_s *) shost->hostdata[0];
92  bfad = im_port->bfad;
93  spin_lock_irqsave(&bfad->bfad_lock, flags);
94 
95  itnim = bfad_get_itnim(im_port, starget->id);
96  if (itnim)
97  port_name = bfa_fcs_itnim_get_pwwn(&itnim->fcs_itnim);
98 
99  fc_starget_port_name(starget) = cpu_to_be64(port_name);
100  spin_unlock_irqrestore(&bfad->bfad_lock, flags);
101 }
102 
103 /*
104  * FC transport template entry, get SCSI host port ID.
105  */
106 static void
107 bfad_im_get_host_port_id(struct Scsi_Host *shost)
108 {
109  struct bfad_im_port_s *im_port =
110  (struct bfad_im_port_s *) shost->hostdata[0];
111  struct bfad_port_s *port = im_port->port;
112 
113  fc_host_port_id(shost) =
115 }
116 
117 /*
118  * FC transport template entry, get SCSI host port type.
119  */
120 static void
121 bfad_im_get_host_port_type(struct Scsi_Host *shost)
122 {
123  struct bfad_im_port_s *im_port =
124  (struct bfad_im_port_s *) shost->hostdata[0];
125  struct bfad_s *bfad = im_port->bfad;
126  struct bfa_lport_attr_s port_attr;
127 
128  bfa_fcs_lport_get_attr(&bfad->bfa_fcs.fabric.bport, &port_attr);
129 
130  switch (port_attr.port_type) {
131  case BFA_PORT_TYPE_NPORT:
133  break;
136  break;
137  case BFA_PORT_TYPE_P2P:
139  break;
140  case BFA_PORT_TYPE_LPORT:
142  break;
143  default:
145  break;
146  }
147 }
148 
149 /*
150  * FC transport template entry, get SCSI host port state.
151  */
152 static void
153 bfad_im_get_host_port_state(struct Scsi_Host *shost)
154 {
155  struct bfad_im_port_s *im_port =
156  (struct bfad_im_port_s *) shost->hostdata[0];
157  struct bfad_s *bfad = im_port->bfad;
158  struct bfa_port_attr_s attr;
159 
160  bfa_fcport_get_attr(&bfad->bfa, &attr);
161 
162  switch (attr.port_state) {
165  break;
166  case BFA_PORT_ST_LINKUP:
168  break;
170  case BFA_PORT_ST_STOPPED:
171  case BFA_PORT_ST_IOCDOWN:
172  case BFA_PORT_ST_IOCDIS:
174  break;
175  case BFA_PORT_ST_UNINIT:
180  default:
182  break;
183  }
184 }
185 
186 /*
187  * FC transport template entry, get SCSI host active fc4s.
188  */
189 static void
190 bfad_im_get_host_active_fc4s(struct Scsi_Host *shost)
191 {
192  struct bfad_im_port_s *im_port =
193  (struct bfad_im_port_s *) shost->hostdata[0];
194  struct bfad_port_s *port = im_port->port;
195 
196  memset(fc_host_active_fc4s(shost), 0,
197  sizeof(fc_host_active_fc4s(shost)));
198 
199  if (port->supported_fc4s & BFA_LPORT_ROLE_FCP_IM)
200  fc_host_active_fc4s(shost)[2] = 1;
201 
202  fc_host_active_fc4s(shost)[7] = 1;
203 }
204 
205 /*
206  * FC transport template entry, get SCSI host link speed.
207  */
208 static void
209 bfad_im_get_host_speed(struct Scsi_Host *shost)
210 {
211  struct bfad_im_port_s *im_port =
212  (struct bfad_im_port_s *) shost->hostdata[0];
213  struct bfad_s *bfad = im_port->bfad;
214  struct bfa_port_attr_s attr;
215 
216  bfa_fcport_get_attr(&bfad->bfa, &attr);
217  switch (attr.speed) {
220  break;
223  break;
226  break;
229  break;
232  break;
235  break;
236  default:
238  break;
239  }
240 }
241 
242 /*
243  * FC transport template entry, get SCSI host port type.
244  */
245 static void
246 bfad_im_get_host_fabric_name(struct Scsi_Host *shost)
247 {
248  struct bfad_im_port_s *im_port =
249  (struct bfad_im_port_s *) shost->hostdata[0];
250  struct bfad_port_s *port = im_port->port;
251  wwn_t fabric_nwwn = 0;
252 
253  fabric_nwwn = bfa_fcs_lport_get_fabric_name(port->fcs_port);
254 
255  fc_host_fabric_name(shost) = cpu_to_be64(fabric_nwwn);
256 
257 }
258 
259 /*
260  * FC transport template entry, get BFAD statistics.
261  */
262 static struct fc_host_statistics *
263 bfad_im_get_stats(struct Scsi_Host *shost)
264 {
265  struct bfad_im_port_s *im_port =
266  (struct bfad_im_port_s *) shost->hostdata[0];
267  struct bfad_s *bfad = im_port->bfad;
268  struct bfad_hal_comp fcomp;
269  union bfa_port_stats_u *fcstats;
270  struct fc_host_statistics *hstats;
272  unsigned long flags;
273 
274  fcstats = kzalloc(sizeof(union bfa_port_stats_u), GFP_KERNEL);
275  if (fcstats == NULL)
276  return NULL;
277 
278  hstats = &bfad->link_stats;
279  init_completion(&fcomp.comp);
280  spin_lock_irqsave(&bfad->bfad_lock, flags);
281  memset(hstats, 0, sizeof(struct fc_host_statistics));
283  fcstats, bfad_hcb_comp, &fcomp);
284  spin_unlock_irqrestore(&bfad->bfad_lock, flags);
285  if (rc != BFA_STATUS_OK)
286  return NULL;
287 
288  wait_for_completion(&fcomp.comp);
289 
290  /* Fill the fc_host_statistics structure */
291  hstats->seconds_since_last_reset = fcstats->fc.secs_reset;
292  hstats->tx_frames = fcstats->fc.tx_frames;
293  hstats->tx_words = fcstats->fc.tx_words;
294  hstats->rx_frames = fcstats->fc.rx_frames;
295  hstats->rx_words = fcstats->fc.rx_words;
296  hstats->lip_count = fcstats->fc.lip_count;
297  hstats->nos_count = fcstats->fc.nos_count;
298  hstats->error_frames = fcstats->fc.error_frames;
299  hstats->dumped_frames = fcstats->fc.dropped_frames;
300  hstats->link_failure_count = fcstats->fc.link_failures;
301  hstats->loss_of_sync_count = fcstats->fc.loss_of_syncs;
302  hstats->loss_of_signal_count = fcstats->fc.loss_of_signals;
303  hstats->prim_seq_protocol_err_count = fcstats->fc.primseq_errs;
304  hstats->invalid_crc_count = fcstats->fc.invalid_crcs;
305 
306  kfree(fcstats);
307  return hstats;
308 }
309 
310 /*
311  * FC transport template entry, reset BFAD statistics.
312  */
313 static void
314 bfad_im_reset_stats(struct Scsi_Host *shost)
315 {
316  struct bfad_im_port_s *im_port =
317  (struct bfad_im_port_s *) shost->hostdata[0];
318  struct bfad_s *bfad = im_port->bfad;
319  struct bfad_hal_comp fcomp;
320  unsigned long flags;
322 
323  init_completion(&fcomp.comp);
324  spin_lock_irqsave(&bfad->bfad_lock, flags);
326  &fcomp);
327  spin_unlock_irqrestore(&bfad->bfad_lock, flags);
328 
329  if (rc != BFA_STATUS_OK)
330  return;
331 
332  wait_for_completion(&fcomp.comp);
333 
334  return;
335 }
336 
337 /*
338  * FC transport template entry, get rport loss timeout.
339  */
340 static void
341 bfad_im_get_rport_loss_tmo(struct fc_rport *rport)
342 {
343  struct bfad_itnim_data_s *itnim_data = rport->dd_data;
344  struct bfad_itnim_s *itnim = itnim_data->itnim;
345  struct bfad_s *bfad = itnim->im->bfad;
346  unsigned long flags;
347 
348  spin_lock_irqsave(&bfad->bfad_lock, flags);
349  rport->dev_loss_tmo = bfa_fcpim_path_tov_get(&bfad->bfa);
350  spin_unlock_irqrestore(&bfad->bfad_lock, flags);
351 }
352 
353 /*
354  * FC transport template entry, set rport loss timeout.
355  */
356 static void
357 bfad_im_set_rport_loss_tmo(struct fc_rport *rport, u32 timeout)
358 {
359  struct bfad_itnim_data_s *itnim_data = rport->dd_data;
360  struct bfad_itnim_s *itnim = itnim_data->itnim;
361  struct bfad_s *bfad = itnim->im->bfad;
362  unsigned long flags;
363 
364  if (timeout > 0) {
365  spin_lock_irqsave(&bfad->bfad_lock, flags);
366  bfa_fcpim_path_tov_set(&bfad->bfa, timeout);
367  rport->dev_loss_tmo = bfa_fcpim_path_tov_get(&bfad->bfa);
368  spin_unlock_irqrestore(&bfad->bfad_lock, flags);
369  }
370 
371 }
372 
373 static int
374 bfad_im_vport_create(struct fc_vport *fc_vport, bool disable)
375 {
376  char *vname = fc_vport->symbolic_name;
377  struct Scsi_Host *shost = fc_vport->shost;
378  struct bfad_im_port_s *im_port =
379  (struct bfad_im_port_s *) shost->hostdata[0];
380  struct bfad_s *bfad = im_port->bfad;
381  struct bfa_lport_cfg_s port_cfg;
382  struct bfad_vport_s *vp;
383  int status = 0, rc;
384  unsigned long flags;
385 
386  memset(&port_cfg, 0, sizeof(port_cfg));
387  u64_to_wwn(fc_vport->node_name, (u8 *)&port_cfg.nwwn);
388  u64_to_wwn(fc_vport->port_name, (u8 *)&port_cfg.pwwn);
389  if (strlen(vname) > 0)
390  strcpy((char *)&port_cfg.sym_name, vname);
392 
393  spin_lock_irqsave(&bfad->bfad_lock, flags);
395  if (port_cfg.pwwn ==
396  vp->fcs_vport.lport.port_cfg.pwwn) {
397  port_cfg.preboot_vp =
398  vp->fcs_vport.lport.port_cfg.preboot_vp;
399  break;
400  }
401  }
402  spin_unlock_irqrestore(&bfad->bfad_lock, flags);
403 
404  rc = bfad_vport_create(bfad, 0, &port_cfg, &fc_vport->dev);
405  if (rc == BFA_STATUS_OK) {
406  struct bfad_vport_s *vport;
407  struct bfa_fcs_vport_s *fcs_vport;
408  struct Scsi_Host *vshost;
409 
410  spin_lock_irqsave(&bfad->bfad_lock, flags);
411  fcs_vport = bfa_fcs_vport_lookup(&bfad->bfa_fcs, 0,
412  port_cfg.pwwn);
413  spin_unlock_irqrestore(&bfad->bfad_lock, flags);
414  if (fcs_vport == NULL)
415  return VPCERR_BAD_WWN;
416 
417  fc_vport_set_state(fc_vport, FC_VPORT_ACTIVE);
418  if (disable) {
419  spin_lock_irqsave(&bfad->bfad_lock, flags);
420  bfa_fcs_vport_stop(fcs_vport);
421  spin_unlock_irqrestore(&bfad->bfad_lock, flags);
422  fc_vport_set_state(fc_vport, FC_VPORT_DISABLED);
423  }
424 
425  vport = fcs_vport->vport_drv;
426  vshost = vport->drv_port.im_port->shost;
427  fc_host_node_name(vshost) = wwn_to_u64((u8 *)&port_cfg.nwwn);
428  fc_host_port_name(vshost) = wwn_to_u64((u8 *)&port_cfg.pwwn);
430 
431  memset(fc_host_supported_fc4s(vshost), 0,
432  sizeof(fc_host_supported_fc4s(vshost)));
433 
434  /* For FCP type 0x08 */
436  fc_host_supported_fc4s(vshost)[2] = 1;
437 
438  /* For fibre channel services type 0x20 */
439  fc_host_supported_fc4s(vshost)[7] = 1;
440 
441  fc_host_supported_speeds(vshost) =
443  fc_host_maxframe_size(vshost) =
445 
446  fc_vport->dd_data = vport;
447  vport->drv_port.im_port->fc_vport = fc_vport;
448  } else if (rc == BFA_STATUS_INVALID_WWN)
449  return VPCERR_BAD_WWN;
450  else if (rc == BFA_STATUS_VPORT_EXISTS)
451  return VPCERR_BAD_WWN;
452  else if (rc == BFA_STATUS_VPORT_MAX)
453  return VPCERR_NO_FABRIC_SUPP;
454  else if (rc == BFA_STATUS_VPORT_WWN_BP)
455  return VPCERR_BAD_WWN;
456  else
457  return FC_VPORT_FAILED;
458 
459  return status;
460 }
461 
462 int
464 {
465  struct bfad_im_port_s *im_port =
466  (struct bfad_im_port_s *) shost->hostdata[0];
467  struct bfad_s *bfad = im_port->bfad;
468  struct bfad_hal_comp fcomp;
469  unsigned long flags;
471 
472  init_completion(&fcomp.comp);
473  spin_lock_irqsave(&bfad->bfad_lock, flags);
474  status = bfa_port_disable(&bfad->bfa.modules.port,
475  bfad_hcb_comp, &fcomp);
476  spin_unlock_irqrestore(&bfad->bfad_lock, flags);
477 
478  if (status != BFA_STATUS_OK)
479  return -EIO;
480 
481  wait_for_completion(&fcomp.comp);
482  if (fcomp.status != BFA_STATUS_OK)
483  return -EIO;
484 
485  spin_lock_irqsave(&bfad->bfad_lock, flags);
486  status = bfa_port_enable(&bfad->bfa.modules.port,
487  bfad_hcb_comp, &fcomp);
488  spin_unlock_irqrestore(&bfad->bfad_lock, flags);
489  if (status != BFA_STATUS_OK)
490  return -EIO;
491 
492  wait_for_completion(&fcomp.comp);
493  if (fcomp.status != BFA_STATUS_OK)
494  return -EIO;
495 
496  return 0;
497 }
498 
499 static int
500 bfad_im_vport_delete(struct fc_vport *fc_vport)
501 {
502  struct bfad_vport_s *vport = (struct bfad_vport_s *)fc_vport->dd_data;
503  struct bfad_im_port_s *im_port =
504  (struct bfad_im_port_s *) vport->drv_port.im_port;
505  struct bfad_s *bfad = im_port->bfad;
506  struct bfad_port_s *port;
507  struct bfa_fcs_vport_s *fcs_vport;
508  struct Scsi_Host *vshost;
509  wwn_t pwwn;
510  int rc;
511  unsigned long flags;
512  struct completion fcomp;
513 
514  if (im_port->flags & BFAD_PORT_DELETE) {
515  bfad_scsi_host_free(bfad, im_port);
516  list_del(&vport->list_entry);
517  kfree(vport);
518  return 0;
519  }
520 
521  port = im_port->port;
522 
523  vshost = vport->drv_port.im_port->shost;
524  u64_to_wwn(fc_host_port_name(vshost), (u8 *)&pwwn);
525 
526  spin_lock_irqsave(&bfad->bfad_lock, flags);
527  fcs_vport = bfa_fcs_vport_lookup(&bfad->bfa_fcs, 0, pwwn);
528  spin_unlock_irqrestore(&bfad->bfad_lock, flags);
529 
530  if (fcs_vport == NULL)
531  return VPCERR_BAD_WWN;
532 
533  vport->drv_port.flags |= BFAD_PORT_DELETE;
534 
535  vport->comp_del = &fcomp;
536  init_completion(vport->comp_del);
537 
538  spin_lock_irqsave(&bfad->bfad_lock, flags);
539  rc = bfa_fcs_vport_delete(&vport->fcs_vport);
540  spin_unlock_irqrestore(&bfad->bfad_lock, flags);
541 
542  if (rc == BFA_STATUS_PBC) {
543  vport->drv_port.flags &= ~BFAD_PORT_DELETE;
544  vport->comp_del = NULL;
545  return -1;
546  }
547 
549 
550  bfad_scsi_host_free(bfad, im_port);
551  list_del(&vport->list_entry);
552  kfree(vport);
553 
554  return 0;
555 }
556 
557 static int
558 bfad_im_vport_disable(struct fc_vport *fc_vport, bool disable)
559 {
560  struct bfad_vport_s *vport;
561  struct bfad_s *bfad;
562  struct bfa_fcs_vport_s *fcs_vport;
563  struct Scsi_Host *vshost;
564  wwn_t pwwn;
565  unsigned long flags;
566 
567  vport = (struct bfad_vport_s *)fc_vport->dd_data;
568  bfad = vport->drv_port.bfad;
569  vshost = vport->drv_port.im_port->shost;
570  u64_to_wwn(fc_host_port_name(vshost), (u8 *)&pwwn);
571 
572  spin_lock_irqsave(&bfad->bfad_lock, flags);
573  fcs_vport = bfa_fcs_vport_lookup(&bfad->bfa_fcs, 0, pwwn);
574  spin_unlock_irqrestore(&bfad->bfad_lock, flags);
575 
576  if (fcs_vport == NULL)
577  return VPCERR_BAD_WWN;
578 
579  if (disable) {
580  bfa_fcs_vport_stop(fcs_vport);
581  fc_vport_set_state(fc_vport, FC_VPORT_DISABLED);
582  } else {
583  bfa_fcs_vport_start(fcs_vport);
584  fc_vport_set_state(fc_vport, FC_VPORT_ACTIVE);
585  }
586 
587  return 0;
588 }
589 
590 void
591 bfad_im_vport_set_symbolic_name(struct fc_vport *fc_vport)
592 {
593  struct bfad_vport_s *vport = (struct bfad_vport_s *)fc_vport->dd_data;
594  struct bfad_im_port_s *im_port =
595  (struct bfad_im_port_s *)vport->drv_port.im_port;
596  struct bfad_s *bfad = im_port->bfad;
597  struct Scsi_Host *vshost = vport->drv_port.im_port->shost;
598  char *sym_name = fc_vport->symbolic_name;
599  struct bfa_fcs_vport_s *fcs_vport;
600  wwn_t pwwn;
601  unsigned long flags;
602 
603  u64_to_wwn(fc_host_port_name(vshost), (u8 *)&pwwn);
604 
605  spin_lock_irqsave(&bfad->bfad_lock, flags);
606  fcs_vport = bfa_fcs_vport_lookup(&bfad->bfa_fcs, 0, pwwn);
607  spin_unlock_irqrestore(&bfad->bfad_lock, flags);
608 
609  if (fcs_vport == NULL)
610  return;
611 
612  spin_lock_irqsave(&bfad->bfad_lock, flags);
613  if (strlen(sym_name) > 0) {
614  strcpy(fcs_vport->lport.port_cfg.sym_name.symname, sym_name);
616  BFA_FCS_GET_NS_FROM_PORT((&fcs_vport->lport)), NULL);
617  }
618  spin_unlock_irqrestore(&bfad->bfad_lock, flags);
619 }
620 
622 
623  /* Target dynamic attributes */
624  .get_starget_port_id = bfad_im_get_starget_port_id,
625  .show_starget_port_id = 1,
626  .get_starget_node_name = bfad_im_get_starget_node_name,
627  .show_starget_node_name = 1,
628  .get_starget_port_name = bfad_im_get_starget_port_name,
629  .show_starget_port_name = 1,
630 
631  /* Host dynamic attribute */
632  .get_host_port_id = bfad_im_get_host_port_id,
633  .show_host_port_id = 1,
634 
635  /* Host fixed attributes */
636  .show_host_node_name = 1,
637  .show_host_port_name = 1,
638  .show_host_supported_classes = 1,
639  .show_host_supported_fc4s = 1,
640  .show_host_supported_speeds = 1,
641  .show_host_maxframe_size = 1,
642 
643  /* More host dynamic attributes */
644  .show_host_port_type = 1,
645  .get_host_port_type = bfad_im_get_host_port_type,
646  .show_host_port_state = 1,
647  .get_host_port_state = bfad_im_get_host_port_state,
648  .show_host_active_fc4s = 1,
649  .get_host_active_fc4s = bfad_im_get_host_active_fc4s,
650  .show_host_speed = 1,
651  .get_host_speed = bfad_im_get_host_speed,
652  .show_host_fabric_name = 1,
653  .get_host_fabric_name = bfad_im_get_host_fabric_name,
654 
655  .show_host_symbolic_name = 1,
656 
657  /* Statistics */
658  .get_fc_host_stats = bfad_im_get_stats,
659  .reset_fc_host_stats = bfad_im_reset_stats,
660 
661  /* Allocation length for host specific data */
662  .dd_fcrport_size = sizeof(struct bfad_itnim_data_s *),
663 
664  /* Remote port fixed attributes */
665  .show_rport_maxframe_size = 1,
666  .show_rport_supported_classes = 1,
667  .show_rport_dev_loss_tmo = 1,
668  .get_rport_dev_loss_tmo = bfad_im_get_rport_loss_tmo,
669  .set_rport_dev_loss_tmo = bfad_im_set_rport_loss_tmo,
670  .issue_fc_host_lip = bfad_im_issue_fc_host_lip,
671  .vport_create = bfad_im_vport_create,
672  .vport_delete = bfad_im_vport_delete,
673  .vport_disable = bfad_im_vport_disable,
674  .set_vport_symbolic_name = bfad_im_vport_set_symbolic_name,
675  .bsg_request = bfad_im_bsg_request,
676  .bsg_timeout = bfad_im_bsg_timeout,
677 };
678 
680 
681  /* Target dynamic attributes */
682  .get_starget_port_id = bfad_im_get_starget_port_id,
683  .show_starget_port_id = 1,
684  .get_starget_node_name = bfad_im_get_starget_node_name,
685  .show_starget_node_name = 1,
686  .get_starget_port_name = bfad_im_get_starget_port_name,
687  .show_starget_port_name = 1,
688 
689  /* Host dynamic attribute */
690  .get_host_port_id = bfad_im_get_host_port_id,
691  .show_host_port_id = 1,
692 
693  /* Host fixed attributes */
694  .show_host_node_name = 1,
695  .show_host_port_name = 1,
696  .show_host_supported_classes = 1,
697  .show_host_supported_fc4s = 1,
698  .show_host_supported_speeds = 1,
699  .show_host_maxframe_size = 1,
700 
701  /* More host dynamic attributes */
702  .show_host_port_type = 1,
703  .get_host_port_type = bfad_im_get_host_port_type,
704  .show_host_port_state = 1,
705  .get_host_port_state = bfad_im_get_host_port_state,
706  .show_host_active_fc4s = 1,
707  .get_host_active_fc4s = bfad_im_get_host_active_fc4s,
708  .show_host_speed = 1,
709  .get_host_speed = bfad_im_get_host_speed,
710  .show_host_fabric_name = 1,
711  .get_host_fabric_name = bfad_im_get_host_fabric_name,
712 
713  .show_host_symbolic_name = 1,
714 
715  /* Statistics */
716  .get_fc_host_stats = bfad_im_get_stats,
717  .reset_fc_host_stats = bfad_im_reset_stats,
718 
719  /* Allocation length for host specific data */
720  .dd_fcrport_size = sizeof(struct bfad_itnim_data_s *),
721 
722  /* Remote port fixed attributes */
723  .show_rport_maxframe_size = 1,
724  .show_rport_supported_classes = 1,
725  .show_rport_dev_loss_tmo = 1,
726  .get_rport_dev_loss_tmo = bfad_im_get_rport_loss_tmo,
727  .set_rport_dev_loss_tmo = bfad_im_set_rport_loss_tmo,
728 };
729 
730 /*
731  * Scsi_Host_attrs SCSI host attributes
732  */
733 static ssize_t
734 bfad_im_serial_num_show(struct device *dev, struct device_attribute *attr,
735  char *buf)
736 {
737  struct Scsi_Host *shost = class_to_shost(dev);
738  struct bfad_im_port_s *im_port =
739  (struct bfad_im_port_s *) shost->hostdata[0];
740  struct bfad_s *bfad = im_port->bfad;
742 
744  return snprintf(buf, PAGE_SIZE, "%s\n", serial_num);
745 }
746 
747 static ssize_t
748 bfad_im_model_show(struct device *dev, struct device_attribute *attr,
749  char *buf)
750 {
751  struct Scsi_Host *shost = class_to_shost(dev);
752  struct bfad_im_port_s *im_port =
753  (struct bfad_im_port_s *) shost->hostdata[0];
754  struct bfad_s *bfad = im_port->bfad;
756 
758  return snprintf(buf, PAGE_SIZE, "%s\n", model);
759 }
760 
761 static ssize_t
762 bfad_im_model_desc_show(struct device *dev, struct device_attribute *attr,
763  char *buf)
764 {
765  struct Scsi_Host *shost = class_to_shost(dev);
766  struct bfad_im_port_s *im_port =
767  (struct bfad_im_port_s *) shost->hostdata[0];
768  struct bfad_s *bfad = im_port->bfad;
770  char model_descr[BFA_ADAPTER_MODEL_DESCR_LEN];
771  int nports = 0;
772 
774  nports = bfa_get_nports(&bfad->bfa);
775  if (!strcmp(model, "Brocade-425"))
777  "Brocade 4Gbps PCIe dual port FC HBA");
778  else if (!strcmp(model, "Brocade-825"))
780  "Brocade 8Gbps PCIe dual port FC HBA");
781  else if (!strcmp(model, "Brocade-42B"))
783  "Brocade 4Gbps PCIe dual port FC HBA for HP");
784  else if (!strcmp(model, "Brocade-82B"))
786  "Brocade 8Gbps PCIe dual port FC HBA for HP");
787  else if (!strcmp(model, "Brocade-1010"))
789  "Brocade 10Gbps single port CNA");
790  else if (!strcmp(model, "Brocade-1020"))
792  "Brocade 10Gbps dual port CNA");
793  else if (!strcmp(model, "Brocade-1007"))
795  "Brocade 10Gbps CNA for IBM Blade Center");
796  else if (!strcmp(model, "Brocade-415"))
798  "Brocade 4Gbps PCIe single port FC HBA");
799  else if (!strcmp(model, "Brocade-815"))
801  "Brocade 8Gbps PCIe single port FC HBA");
802  else if (!strcmp(model, "Brocade-41B"))
804  "Brocade 4Gbps PCIe single port FC HBA for HP");
805  else if (!strcmp(model, "Brocade-81B"))
807  "Brocade 8Gbps PCIe single port FC HBA for HP");
808  else if (!strcmp(model, "Brocade-804"))
810  "Brocade 8Gbps FC HBA for HP Bladesystem C-class");
811  else if (!strcmp(model, "Brocade-1741"))
813  "Brocade 10Gbps CNA for Dell M-Series Blade Servers");
814  else if (strstr(model, "Brocade-1860")) {
815  if (nports == 1 && bfa_ioc_is_cna(&bfad->bfa.ioc))
817  "Brocade 10Gbps single port CNA");
818  else if (nports == 1 && !bfa_ioc_is_cna(&bfad->bfa.ioc))
820  "Brocade 16Gbps PCIe single port FC HBA");
821  else if (nports == 2 && bfa_ioc_is_cna(&bfad->bfa.ioc))
823  "Brocade 10Gbps dual port CNA");
824  else if (nports == 2 && !bfa_ioc_is_cna(&bfad->bfa.ioc))
826  "Brocade 16Gbps PCIe dual port FC HBA");
827  } else if (!strcmp(model, "Brocade-1867")) {
828  if (nports == 1 && !bfa_ioc_is_cna(&bfad->bfa.ioc))
830  "Brocade 16Gbps PCIe single port FC HBA for IBM");
831  else if (nports == 2 && !bfa_ioc_is_cna(&bfad->bfa.ioc))
833  "Brocade 16Gbps PCIe dual port FC HBA for IBM");
834  } else
836  "Invalid Model");
837 
838  return snprintf(buf, PAGE_SIZE, "%s\n", model_descr);
839 }
840 
841 static ssize_t
842 bfad_im_node_name_show(struct device *dev, struct device_attribute *attr,
843  char *buf)
844 {
845  struct Scsi_Host *shost = class_to_shost(dev);
846  struct bfad_im_port_s *im_port =
847  (struct bfad_im_port_s *) shost->hostdata[0];
848  struct bfad_port_s *port = im_port->port;
849  u64 nwwn;
850 
851  nwwn = bfa_fcs_lport_get_nwwn(port->fcs_port);
852  return snprintf(buf, PAGE_SIZE, "0x%llx\n", cpu_to_be64(nwwn));
853 }
854 
855 static ssize_t
856 bfad_im_symbolic_name_show(struct device *dev, struct device_attribute *attr,
857  char *buf)
858 {
859  struct Scsi_Host *shost = class_to_shost(dev);
860  struct bfad_im_port_s *im_port =
861  (struct bfad_im_port_s *) shost->hostdata[0];
862  struct bfad_s *bfad = im_port->bfad;
863  struct bfa_lport_attr_s port_attr;
864  char symname[BFA_SYMNAME_MAXLEN];
865 
866  bfa_fcs_lport_get_attr(&bfad->bfa_fcs.fabric.bport, &port_attr);
867  strncpy(symname, port_attr.port_cfg.sym_name.symname,
869  return snprintf(buf, PAGE_SIZE, "%s\n", symname);
870 }
871 
872 static ssize_t
873 bfad_im_hw_version_show(struct device *dev, struct device_attribute *attr,
874  char *buf)
875 {
876  struct Scsi_Host *shost = class_to_shost(dev);
877  struct bfad_im_port_s *im_port =
878  (struct bfad_im_port_s *) shost->hostdata[0];
879  struct bfad_s *bfad = im_port->bfad;
880  char hw_ver[BFA_VERSION_LEN];
881 
883  return snprintf(buf, PAGE_SIZE, "%s\n", hw_ver);
884 }
885 
886 static ssize_t
887 bfad_im_drv_version_show(struct device *dev, struct device_attribute *attr,
888  char *buf)
889 {
890  return snprintf(buf, PAGE_SIZE, "%s\n", BFAD_DRIVER_VERSION);
891 }
892 
893 static ssize_t
894 bfad_im_optionrom_version_show(struct device *dev,
895  struct device_attribute *attr, char *buf)
896 {
897  struct Scsi_Host *shost = class_to_shost(dev);
898  struct bfad_im_port_s *im_port =
899  (struct bfad_im_port_s *) shost->hostdata[0];
900  struct bfad_s *bfad = im_port->bfad;
901  char optrom_ver[BFA_VERSION_LEN];
902 
903  bfa_get_adapter_optrom_ver(&bfad->bfa, optrom_ver);
904  return snprintf(buf, PAGE_SIZE, "%s\n", optrom_ver);
905 }
906 
907 static ssize_t
908 bfad_im_fw_version_show(struct device *dev, struct device_attribute *attr,
909  char *buf)
910 {
911  struct Scsi_Host *shost = class_to_shost(dev);
912  struct bfad_im_port_s *im_port =
913  (struct bfad_im_port_s *) shost->hostdata[0];
914  struct bfad_s *bfad = im_port->bfad;
915  char fw_ver[BFA_VERSION_LEN];
916 
917  bfa_get_adapter_fw_ver(&bfad->bfa, fw_ver);
918  return snprintf(buf, PAGE_SIZE, "%s\n", fw_ver);
919 }
920 
921 static ssize_t
922 bfad_im_num_of_ports_show(struct device *dev, struct device_attribute *attr,
923  char *buf)
924 {
925  struct Scsi_Host *shost = class_to_shost(dev);
926  struct bfad_im_port_s *im_port =
927  (struct bfad_im_port_s *) shost->hostdata[0];
928  struct bfad_s *bfad = im_port->bfad;
929 
930  return snprintf(buf, PAGE_SIZE, "%d\n",
931  bfa_get_nports(&bfad->bfa));
932 }
933 
934 static ssize_t
935 bfad_im_drv_name_show(struct device *dev, struct device_attribute *attr,
936  char *buf)
937 {
938  return snprintf(buf, PAGE_SIZE, "%s\n", BFAD_DRIVER_NAME);
939 }
940 
941 static ssize_t
942 bfad_im_num_of_discovered_ports_show(struct device *dev,
943  struct device_attribute *attr, char *buf)
944 {
945  struct Scsi_Host *shost = class_to_shost(dev);
946  struct bfad_im_port_s *im_port =
947  (struct bfad_im_port_s *) shost->hostdata[0];
948  struct bfad_port_s *port = im_port->port;
949  struct bfad_s *bfad = im_port->bfad;
950  int nrports = 2048;
951  struct bfa_rport_qualifier_s *rports = NULL;
952  unsigned long flags;
953 
954  rports = kzalloc(sizeof(struct bfa_rport_qualifier_s) * nrports,
955  GFP_ATOMIC);
956  if (rports == NULL)
957  return snprintf(buf, PAGE_SIZE, "Failed\n");
958 
959  spin_lock_irqsave(&bfad->bfad_lock, flags);
960  bfa_fcs_lport_get_rport_quals(port->fcs_port, rports, &nrports);
961  spin_unlock_irqrestore(&bfad->bfad_lock, flags);
962  kfree(rports);
963 
964  return snprintf(buf, PAGE_SIZE, "%d\n", nrports);
965 }
966 
968  bfad_im_serial_num_show, NULL);
969 static DEVICE_ATTR(model, S_IRUGO, bfad_im_model_show, NULL);
970 static DEVICE_ATTR(model_description, S_IRUGO,
971  bfad_im_model_desc_show, NULL);
972 static DEVICE_ATTR(node_name, S_IRUGO, bfad_im_node_name_show, NULL);
974  bfad_im_symbolic_name_show, NULL);
976  bfad_im_hw_version_show, NULL);
978  bfad_im_drv_version_show, NULL);
979 static DEVICE_ATTR(option_rom_version, S_IRUGO,
980  bfad_im_optionrom_version_show, NULL);
982  bfad_im_fw_version_show, NULL);
983 static DEVICE_ATTR(number_of_ports, S_IRUGO,
984  bfad_im_num_of_ports_show, NULL);
985 static DEVICE_ATTR(driver_name, S_IRUGO, bfad_im_drv_name_show, NULL);
986 static DEVICE_ATTR(number_of_discovered_ports, S_IRUGO,
987  bfad_im_num_of_discovered_ports_show, NULL);
988 
990  &dev_attr_serial_number,
991  &dev_attr_model,
992  &dev_attr_model_description,
993  &dev_attr_node_name,
994  &dev_attr_symbolic_name,
995  &dev_attr_hardware_version,
996  &dev_attr_driver_version,
997  &dev_attr_option_rom_version,
998  &dev_attr_firmware_version,
999  &dev_attr_number_of_ports,
1000  &dev_attr_driver_name,
1001  &dev_attr_number_of_discovered_ports,
1002  NULL,
1003 };
1004 
1006  &dev_attr_serial_number,
1007  &dev_attr_model,
1008  &dev_attr_model_description,
1009  &dev_attr_node_name,
1010  &dev_attr_symbolic_name,
1011  &dev_attr_hardware_version,
1012  &dev_attr_driver_version,
1013  &dev_attr_option_rom_version,
1014  &dev_attr_firmware_version,
1015  &dev_attr_number_of_ports,
1016  &dev_attr_driver_name,
1017  &dev_attr_number_of_discovered_ports,
1018  NULL,
1019 };
1020 
1021