1
2
3
4
5
6
7
8
9
10
11
12#include <linux/module.h>
13#include <linux/init.h>
14#include <linux/slab.h>
15#include <linux/delay.h>
16#include <linux/kernel.h>
17#include <linux/bsg-lib.h>
18#include <scsi/scsi_device.h>
19#include <scsi/scsi_host.h>
20#include <scsi/scsi_transport.h>
21#include <scsi/scsi_transport_fc.h>
22#include <scsi/scsi_cmnd.h>
23#include <net/netlink.h>
24#include <scsi/scsi_netlink_fc.h>
25#include <scsi/scsi_bsg_fc.h>
26#include <uapi/scsi/fc/fc_els.h>
27#include "scsi_priv.h"
28
29static int fc_queue_work(struct Scsi_Host *, struct work_struct *);
30static void fc_vport_sched_delete(struct work_struct *work);
31static int fc_vport_setup(struct Scsi_Host *shost, int channel,
32 struct device *pdev, struct fc_vport_identifiers *ids,
33 struct fc_vport **vport);
34static int fc_bsg_hostadd(struct Scsi_Host *, struct fc_host_attrs *);
35static int fc_bsg_rportadd(struct Scsi_Host *, struct fc_rport *);
36static void fc_bsg_remove(struct request_queue *);
37static void fc_bsg_goose_queue(struct fc_rport *);
38static void fc_li_stats_update(struct fc_fn_li_desc *li_desc,
39 struct fc_fpin_stats *stats);
40static void fc_delivery_stats_update(u32 reason_code,
41 struct fc_fpin_stats *stats);
42static void fc_cn_stats_update(u16 event_type, struct fc_fpin_stats *stats);
43
44
45
46
47
48
49
50
51
52
53static unsigned int fc_dev_loss_tmo = 60;
54
55module_param_named(dev_loss_tmo, fc_dev_loss_tmo, uint, S_IRUGO|S_IWUSR);
56MODULE_PARM_DESC(dev_loss_tmo,
57 "Maximum number of seconds that the FC transport should"
58 " insulate the loss of a remote port. Once this value is"
59 " exceeded, the scsi target is removed. Value should be"
60 " between 1 and SCSI_DEVICE_BLOCK_MAX_TIMEOUT if"
61 " fast_io_fail_tmo is not set.");
62
63
64
65
66
67#define FC_DEVICE_ATTR(_prefix,_name,_mode,_show,_store) \
68struct device_attribute device_attr_##_prefix##_##_name = \
69 __ATTR(_name,_mode,_show,_store)
70
71#define fc_enum_name_search(title, table_type, table) \
72static const char *get_fc_##title##_name(enum table_type table_key) \
73{ \
74 int i; \
75 char *name = NULL; \
76 \
77 for (i = 0; i < ARRAY_SIZE(table); i++) { \
78 if (table[i].value == table_key) { \
79 name = table[i].name; \
80 break; \
81 } \
82 } \
83 return name; \
84}
85
86#define fc_enum_name_match(title, table_type, table) \
87static int get_fc_##title##_match(const char *table_key, \
88 enum table_type *value) \
89{ \
90 int i; \
91 \
92 for (i = 0; i < ARRAY_SIZE(table); i++) { \
93 if (strncmp(table_key, table[i].name, \
94 table[i].matchlen) == 0) { \
95 *value = table[i].value; \
96 return 0; \
97 } \
98 } \
99 return 1; \
100}
101
102
103
104static struct {
105 enum fc_port_type value;
106 char *name;
107} fc_port_type_names[] = {
108 { FC_PORTTYPE_UNKNOWN, "Unknown" },
109 { FC_PORTTYPE_OTHER, "Other" },
110 { FC_PORTTYPE_NOTPRESENT, "Not Present" },
111 { FC_PORTTYPE_NPORT, "NPort (fabric via point-to-point)" },
112 { FC_PORTTYPE_NLPORT, "NLPort (fabric via loop)" },
113 { FC_PORTTYPE_LPORT, "LPort (private loop)" },
114 { FC_PORTTYPE_PTP, "Point-To-Point (direct nport connection)" },
115 { FC_PORTTYPE_NPIV, "NPIV VPORT" },
116};
117fc_enum_name_search(port_type, fc_port_type, fc_port_type_names)
118#define FC_PORTTYPE_MAX_NAMELEN 50
119
120
121#define get_fc_vport_type_name get_fc_port_type_name
122
123
124
125static const struct {
126 enum fc_host_event_code value;
127 char *name;
128} fc_host_event_code_names[] = {
129 { FCH_EVT_LIP, "lip" },
130 { FCH_EVT_LINKUP, "link_up" },
131 { FCH_EVT_LINKDOWN, "link_down" },
132 { FCH_EVT_LIPRESET, "lip_reset" },
133 { FCH_EVT_RSCN, "rscn" },
134 { FCH_EVT_ADAPTER_CHANGE, "adapter_chg" },
135 { FCH_EVT_PORT_UNKNOWN, "port_unknown" },
136 { FCH_EVT_PORT_ONLINE, "port_online" },
137 { FCH_EVT_PORT_OFFLINE, "port_offline" },
138 { FCH_EVT_PORT_FABRIC, "port_fabric" },
139 { FCH_EVT_LINK_UNKNOWN, "link_unknown" },
140 { FCH_EVT_LINK_FPIN, "link_FPIN" },
141 { FCH_EVT_VENDOR_UNIQUE, "vendor_unique" },
142};
143fc_enum_name_search(host_event_code, fc_host_event_code,
144 fc_host_event_code_names)
145#define FC_HOST_EVENT_CODE_MAX_NAMELEN 30
146
147
148
149static struct {
150 enum fc_port_state value;
151 char *name;
152 int matchlen;
153} fc_port_state_names[] = {
154 { FC_PORTSTATE_UNKNOWN, "Unknown", 7},
155 { FC_PORTSTATE_NOTPRESENT, "Not Present", 11 },
156 { FC_PORTSTATE_ONLINE, "Online", 6 },
157 { FC_PORTSTATE_OFFLINE, "Offline", 7 },
158 { FC_PORTSTATE_BLOCKED, "Blocked", 7 },
159 { FC_PORTSTATE_BYPASSED, "Bypassed", 8 },
160 { FC_PORTSTATE_DIAGNOSTICS, "Diagnostics", 11 },
161 { FC_PORTSTATE_LINKDOWN, "Linkdown", 8 },
162 { FC_PORTSTATE_ERROR, "Error", 5 },
163 { FC_PORTSTATE_LOOPBACK, "Loopback", 8 },
164 { FC_PORTSTATE_DELETED, "Deleted", 7 },
165 { FC_PORTSTATE_MARGINAL, "Marginal", 8 },
166};
167fc_enum_name_search(port_state, fc_port_state, fc_port_state_names)
168fc_enum_name_match(port_state, fc_port_state, fc_port_state_names)
169#define FC_PORTSTATE_MAX_NAMELEN 20
170
171
172
173static struct {
174 enum fc_vport_state value;
175 char *name;
176} fc_vport_state_names[] = {
177 { FC_VPORT_UNKNOWN, "Unknown" },
178 { FC_VPORT_ACTIVE, "Active" },
179 { FC_VPORT_DISABLED, "Disabled" },
180 { FC_VPORT_LINKDOWN, "Linkdown" },
181 { FC_VPORT_INITIALIZING, "Initializing" },
182 { FC_VPORT_NO_FABRIC_SUPP, "No Fabric Support" },
183 { FC_VPORT_NO_FABRIC_RSCS, "No Fabric Resources" },
184 { FC_VPORT_FABRIC_LOGOUT, "Fabric Logout" },
185 { FC_VPORT_FABRIC_REJ_WWN, "Fabric Rejected WWN" },
186 { FC_VPORT_FAILED, "VPort Failed" },
187};
188fc_enum_name_search(vport_state, fc_vport_state, fc_vport_state_names)
189#define FC_VPORTSTATE_MAX_NAMELEN 24
190
191
192#define get_fc_vport_last_state_name get_fc_vport_state_name
193
194
195
196static const struct {
197 enum fc_tgtid_binding_type value;
198 char *name;
199 int matchlen;
200} fc_tgtid_binding_type_names[] = {
201 { FC_TGTID_BIND_NONE, "none", 4 },
202 { FC_TGTID_BIND_BY_WWPN, "wwpn (World Wide Port Name)", 4 },
203 { FC_TGTID_BIND_BY_WWNN, "wwnn (World Wide Node Name)", 4 },
204 { FC_TGTID_BIND_BY_ID, "port_id (FC Address)", 7 },
205};
206fc_enum_name_search(tgtid_bind_type, fc_tgtid_binding_type,
207 fc_tgtid_binding_type_names)
208fc_enum_name_match(tgtid_bind_type, fc_tgtid_binding_type,
209 fc_tgtid_binding_type_names)
210#define FC_BINDTYPE_MAX_NAMELEN 30
211
212
213#define fc_bitfield_name_search(title, table) \
214static ssize_t \
215get_fc_##title##_names(u32 table_key, char *buf) \
216{ \
217 char *prefix = ""; \
218 ssize_t len = 0; \
219 int i; \
220 \
221 for (i = 0; i < ARRAY_SIZE(table); i++) { \
222 if (table[i].value & table_key) { \
223 len += sprintf(buf + len, "%s%s", \
224 prefix, table[i].name); \
225 prefix = ", "; \
226 } \
227 } \
228 len += sprintf(buf + len, "\n"); \
229 return len; \
230}
231
232
233
234static const struct {
235 u32 value;
236 char *name;
237} fc_cos_names[] = {
238 { FC_COS_CLASS1, "Class 1" },
239 { FC_COS_CLASS2, "Class 2" },
240 { FC_COS_CLASS3, "Class 3" },
241 { FC_COS_CLASS4, "Class 4" },
242 { FC_COS_CLASS6, "Class 6" },
243};
244fc_bitfield_name_search(cos, fc_cos_names)
245
246
247
248static const struct {
249 u32 value;
250 char *name;
251} fc_port_speed_names[] = {
252 { FC_PORTSPEED_1GBIT, "1 Gbit" },
253 { FC_PORTSPEED_2GBIT, "2 Gbit" },
254 { FC_PORTSPEED_4GBIT, "4 Gbit" },
255 { FC_PORTSPEED_10GBIT, "10 Gbit" },
256 { FC_PORTSPEED_8GBIT, "8 Gbit" },
257 { FC_PORTSPEED_16GBIT, "16 Gbit" },
258 { FC_PORTSPEED_32GBIT, "32 Gbit" },
259 { FC_PORTSPEED_20GBIT, "20 Gbit" },
260 { FC_PORTSPEED_40GBIT, "40 Gbit" },
261 { FC_PORTSPEED_50GBIT, "50 Gbit" },
262 { FC_PORTSPEED_100GBIT, "100 Gbit" },
263 { FC_PORTSPEED_25GBIT, "25 Gbit" },
264 { FC_PORTSPEED_64GBIT, "64 Gbit" },
265 { FC_PORTSPEED_128GBIT, "128 Gbit" },
266 { FC_PORTSPEED_256GBIT, "256 Gbit" },
267 { FC_PORTSPEED_NOT_NEGOTIATED, "Not Negotiated" },
268};
269fc_bitfield_name_search(port_speed, fc_port_speed_names)
270
271
272static int
273show_fc_fc4s (char *buf, u8 *fc4_list)
274{
275 int i, len=0;
276
277 for (i = 0; i < FC_FC4_LIST_SIZE; i++, fc4_list++)
278 len += sprintf(buf + len , "0x%02x ", *fc4_list);
279 len += sprintf(buf + len, "\n");
280 return len;
281}
282
283
284
285static const struct {
286 u32 value;
287 char *name;
288} fc_port_role_names[] = {
289 { FC_PORT_ROLE_FCP_TARGET, "FCP Target" },
290 { FC_PORT_ROLE_FCP_INITIATOR, "FCP Initiator" },
291 { FC_PORT_ROLE_IP_PORT, "IP Port" },
292 { FC_PORT_ROLE_FCP_DUMMY_INITIATOR, "FCP Dummy Initiator" },
293 { FC_PORT_ROLE_NVME_INITIATOR, "NVMe Initiator" },
294 { FC_PORT_ROLE_NVME_TARGET, "NVMe Target" },
295 { FC_PORT_ROLE_NVME_DISCOVERY, "NVMe Discovery" },
296};
297fc_bitfield_name_search(port_roles, fc_port_role_names)
298
299
300
301
302#define FC_WELLKNOWN_PORTID_MASK 0xfffff0
303#define FC_WELLKNOWN_ROLE_MASK 0x00000f
304#define FC_FPORT_PORTID 0x00000e
305#define FC_FABCTLR_PORTID 0x00000d
306#define FC_DIRSRVR_PORTID 0x00000c
307#define FC_TIMESRVR_PORTID 0x00000b
308#define FC_MGMTSRVR_PORTID 0x00000a
309
310
311static void fc_timeout_deleted_rport(struct work_struct *work);
312static void fc_timeout_fail_rport_io(struct work_struct *work);
313static void fc_scsi_scan_rport(struct work_struct *work);
314
315
316
317
318
319#define FC_STARGET_NUM_ATTRS 3
320#define FC_RPORT_NUM_ATTRS 10
321#define FC_VPORT_NUM_ATTRS 9
322#define FC_HOST_NUM_ATTRS 29
323
324struct fc_internal {
325 struct scsi_transport_template t;
326 struct fc_function_template *f;
327
328
329
330
331
332
333
334
335
336
337
338 struct device_attribute private_starget_attrs[
339 FC_STARGET_NUM_ATTRS];
340 struct device_attribute *starget_attrs[FC_STARGET_NUM_ATTRS + 1];
341
342 struct device_attribute private_host_attrs[FC_HOST_NUM_ATTRS];
343 struct device_attribute *host_attrs[FC_HOST_NUM_ATTRS + 1];
344
345 struct transport_container rport_attr_cont;
346 struct device_attribute private_rport_attrs[FC_RPORT_NUM_ATTRS];
347 struct device_attribute *rport_attrs[FC_RPORT_NUM_ATTRS + 1];
348
349 struct transport_container vport_attr_cont;
350 struct device_attribute private_vport_attrs[FC_VPORT_NUM_ATTRS];
351 struct device_attribute *vport_attrs[FC_VPORT_NUM_ATTRS + 1];
352};
353
354#define to_fc_internal(tmpl) container_of(tmpl, struct fc_internal, t)
355
356static int fc_target_setup(struct transport_container *tc, struct device *dev,
357 struct device *cdev)
358{
359 struct scsi_target *starget = to_scsi_target(dev);
360 struct fc_rport *rport = starget_to_rport(starget);
361
362
363
364
365
366
367 if (rport) {
368 fc_starget_node_name(starget) = rport->node_name;
369 fc_starget_port_name(starget) = rport->port_name;
370 fc_starget_port_id(starget) = rport->port_id;
371 } else {
372 fc_starget_node_name(starget) = -1;
373 fc_starget_port_name(starget) = -1;
374 fc_starget_port_id(starget) = -1;
375 }
376
377 return 0;
378}
379
380static DECLARE_TRANSPORT_CLASS(fc_transport_class,
381 "fc_transport",
382 fc_target_setup,
383 NULL,
384 NULL);
385
386static int fc_host_setup(struct transport_container *tc, struct device *dev,
387 struct device *cdev)
388{
389 struct Scsi_Host *shost = dev_to_shost(dev);
390 struct fc_host_attrs *fc_host = shost_to_fc_host(shost);
391
392
393
394
395
396
397 fc_host->node_name = -1;
398 fc_host->port_name = -1;
399 fc_host->permanent_port_name = -1;
400 fc_host->supported_classes = FC_COS_UNSPECIFIED;
401 memset(fc_host->supported_fc4s, 0,
402 sizeof(fc_host->supported_fc4s));
403 fc_host->supported_speeds = FC_PORTSPEED_UNKNOWN;
404 fc_host->maxframe_size = -1;
405 fc_host->max_npiv_vports = 0;
406 memset(fc_host->serial_number, 0,
407 sizeof(fc_host->serial_number));
408 memset(fc_host->manufacturer, 0,
409 sizeof(fc_host->manufacturer));
410 memset(fc_host->model, 0,
411 sizeof(fc_host->model));
412 memset(fc_host->model_description, 0,
413 sizeof(fc_host->model_description));
414 memset(fc_host->hardware_version, 0,
415 sizeof(fc_host->hardware_version));
416 memset(fc_host->driver_version, 0,
417 sizeof(fc_host->driver_version));
418 memset(fc_host->firmware_version, 0,
419 sizeof(fc_host->firmware_version));
420 memset(fc_host->optionrom_version, 0,
421 sizeof(fc_host->optionrom_version));
422
423 fc_host->port_id = -1;
424 fc_host->port_type = FC_PORTTYPE_UNKNOWN;
425 fc_host->port_state = FC_PORTSTATE_UNKNOWN;
426 memset(fc_host->active_fc4s, 0,
427 sizeof(fc_host->active_fc4s));
428 fc_host->speed = FC_PORTSPEED_UNKNOWN;
429 fc_host->fabric_name = -1;
430 memset(fc_host->symbolic_name, 0, sizeof(fc_host->symbolic_name));
431 memset(fc_host->system_hostname, 0, sizeof(fc_host->system_hostname));
432 memset(&fc_host->fpin_stats, 0, sizeof(fc_host->fpin_stats));
433
434 fc_host->tgtid_bind_type = FC_TGTID_BIND_BY_WWPN;
435
436 INIT_LIST_HEAD(&fc_host->rports);
437 INIT_LIST_HEAD(&fc_host->rport_bindings);
438 INIT_LIST_HEAD(&fc_host->vports);
439 fc_host->next_rport_number = 0;
440 fc_host->next_target_id = 0;
441 fc_host->next_vport_number = 0;
442 fc_host->npiv_vports_inuse = 0;
443
444 snprintf(fc_host->work_q_name, sizeof(fc_host->work_q_name),
445 "fc_wq_%d", shost->host_no);
446 fc_host->work_q = alloc_workqueue("%s", 0, 0, fc_host->work_q_name);
447 if (!fc_host->work_q)
448 return -ENOMEM;
449
450 fc_host->dev_loss_tmo = fc_dev_loss_tmo;
451 snprintf(fc_host->devloss_work_q_name,
452 sizeof(fc_host->devloss_work_q_name),
453 "fc_dl_%d", shost->host_no);
454 fc_host->devloss_work_q = alloc_workqueue("%s", 0, 0,
455 fc_host->devloss_work_q_name);
456 if (!fc_host->devloss_work_q) {
457 destroy_workqueue(fc_host->work_q);
458 fc_host->work_q = NULL;
459 return -ENOMEM;
460 }
461
462 fc_bsg_hostadd(shost, fc_host);
463
464
465 return 0;
466}
467
468static int fc_host_remove(struct transport_container *tc, struct device *dev,
469 struct device *cdev)
470{
471 struct Scsi_Host *shost = dev_to_shost(dev);
472 struct fc_host_attrs *fc_host = shost_to_fc_host(shost);
473
474 fc_bsg_remove(fc_host->rqst_q);
475 return 0;
476}
477
478static DECLARE_TRANSPORT_CLASS(fc_host_class,
479 "fc_host",
480 fc_host_setup,
481 fc_host_remove,
482 NULL);
483
484
485
486
487
488static DECLARE_TRANSPORT_CLASS(fc_rport_class,
489 "fc_remote_ports",
490 NULL,
491 NULL,
492 NULL);
493
494
495
496
497
498static DECLARE_TRANSPORT_CLASS(fc_vport_class,
499 "fc_vports",
500 NULL,
501 NULL,
502 NULL);
503
504
505
506
507
508static atomic_t fc_event_seq;
509
510
511
512
513
514
515
516
517
518u32
519fc_get_event_number(void)
520{
521 return atomic_add_return(1, &fc_event_seq);
522}
523EXPORT_SYMBOL(fc_get_event_number);
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538void
539fc_host_post_fc_event(struct Scsi_Host *shost, u32 event_number,
540 enum fc_host_event_code event_code,
541 u32 data_len, char *data_buf, u64 vendor_id)
542{
543 struct sk_buff *skb;
544 struct nlmsghdr *nlh;
545 struct fc_nl_event *event;
546 const char *name;
547 u32 len;
548 int err;
549
550 if (!data_buf || data_len < 4)
551 data_len = 0;
552
553 if (!scsi_nl_sock) {
554 err = -ENOENT;
555 goto send_fail;
556 }
557
558 len = FC_NL_MSGALIGN(sizeof(*event) + data_len);
559
560 skb = nlmsg_new(len, GFP_KERNEL);
561 if (!skb) {
562 err = -ENOBUFS;
563 goto send_fail;
564 }
565
566 nlh = nlmsg_put(skb, 0, 0, SCSI_TRANSPORT_MSG, len, 0);
567 if (!nlh) {
568 err = -ENOBUFS;
569 goto send_fail_skb;
570 }
571 event = nlmsg_data(nlh);
572
573 INIT_SCSI_NL_HDR(&event->snlh, SCSI_NL_TRANSPORT_FC,
574 FC_NL_ASYNC_EVENT, len);
575 event->seconds = ktime_get_real_seconds();
576 event->vendor_id = vendor_id;
577 event->host_no = shost->host_no;
578 event->event_datalen = data_len;
579 event->event_num = event_number;
580 event->event_code = event_code;
581 if (data_len)
582 memcpy(&event->event_data, data_buf, data_len);
583
584 nlmsg_multicast(scsi_nl_sock, skb, 0, SCSI_NL_GRP_FC_EVENTS,
585 GFP_KERNEL);
586 return;
587
588send_fail_skb:
589 kfree_skb(skb);
590send_fail:
591 name = get_fc_host_event_code_name(event_code);
592 printk(KERN_WARNING
593 "%s: Dropped Event : host %d %s data 0x%08x - err %d\n",
594 __func__, shost->host_no,
595 (name) ? name : "<unknown>",
596 (data_len) ? *((u32 *)data_buf) : 0xFFFFFFFF, err);
597 return;
598}
599EXPORT_SYMBOL(fc_host_post_fc_event);
600
601
602
603
604
605
606
607
608
609
610
611void
612fc_host_post_event(struct Scsi_Host *shost, u32 event_number,
613 enum fc_host_event_code event_code, u32 event_data)
614{
615 fc_host_post_fc_event(shost, event_number, event_code,
616 (u32)sizeof(u32), (char *)&event_data, 0);
617}
618EXPORT_SYMBOL(fc_host_post_event);
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633void
634fc_host_post_vendor_event(struct Scsi_Host *shost, u32 event_number,
635 u32 data_len, char * data_buf, u64 vendor_id)
636{
637 fc_host_post_fc_event(shost, event_number, FCH_EVT_VENDOR_UNIQUE,
638 data_len, data_buf, vendor_id);
639}
640EXPORT_SYMBOL(fc_host_post_vendor_event);
641
642
643
644
645
646
647
648
649
650struct fc_rport *
651fc_find_rport_by_wwpn(struct Scsi_Host *shost, u64 wwpn)
652{
653 struct fc_rport *rport;
654 unsigned long flags;
655
656 spin_lock_irqsave(shost->host_lock, flags);
657
658 list_for_each_entry(rport, &fc_host_rports(shost), peers) {
659 if (rport->port_state != FC_PORTSTATE_ONLINE)
660 continue;
661
662 if (rport->port_name == wwpn) {
663 spin_unlock_irqrestore(shost->host_lock, flags);
664 return rport;
665 }
666 }
667
668 spin_unlock_irqrestore(shost->host_lock, flags);
669 return NULL;
670}
671EXPORT_SYMBOL(fc_find_rport_by_wwpn);
672
673static void
674fc_li_stats_update(struct fc_fn_li_desc *li_desc,
675 struct fc_fpin_stats *stats)
676{
677 stats->li += be32_to_cpu(li_desc->event_count);
678 switch (be16_to_cpu(li_desc->event_type)) {
679 case FPIN_LI_UNKNOWN:
680 stats->li_failure_unknown +=
681 be32_to_cpu(li_desc->event_count);
682 break;
683 case FPIN_LI_LINK_FAILURE:
684 stats->li_link_failure_count +=
685 be32_to_cpu(li_desc->event_count);
686 break;
687 case FPIN_LI_LOSS_OF_SYNC:
688 stats->li_loss_of_sync_count +=
689 be32_to_cpu(li_desc->event_count);
690 break;
691 case FPIN_LI_LOSS_OF_SIG:
692 stats->li_loss_of_signals_count +=
693 be32_to_cpu(li_desc->event_count);
694 break;
695 case FPIN_LI_PRIM_SEQ_ERR:
696 stats->li_prim_seq_err_count +=
697 be32_to_cpu(li_desc->event_count);
698 break;
699 case FPIN_LI_INVALID_TX_WD:
700 stats->li_invalid_tx_word_count +=
701 be32_to_cpu(li_desc->event_count);
702 break;
703 case FPIN_LI_INVALID_CRC:
704 stats->li_invalid_crc_count +=
705 be32_to_cpu(li_desc->event_count);
706 break;
707 case FPIN_LI_DEVICE_SPEC:
708 stats->li_device_specific +=
709 be32_to_cpu(li_desc->event_count);
710 break;
711 }
712}
713
714static void
715fc_delivery_stats_update(u32 reason_code, struct fc_fpin_stats *stats)
716{
717 stats->dn++;
718 switch (reason_code) {
719 case FPIN_DELI_UNKNOWN:
720 stats->dn_unknown++;
721 break;
722 case FPIN_DELI_TIMEOUT:
723 stats->dn_timeout++;
724 break;
725 case FPIN_DELI_UNABLE_TO_ROUTE:
726 stats->dn_unable_to_route++;
727 break;
728 case FPIN_DELI_DEVICE_SPEC:
729 stats->dn_device_specific++;
730 break;
731 }
732}
733
734static void
735fc_cn_stats_update(u16 event_type, struct fc_fpin_stats *stats)
736{
737 stats->cn++;
738 switch (event_type) {
739 case FPIN_CONGN_CLEAR:
740 stats->cn_clear++;
741 break;
742 case FPIN_CONGN_LOST_CREDIT:
743 stats->cn_lost_credit++;
744 break;
745 case FPIN_CONGN_CREDIT_STALL:
746 stats->cn_credit_stall++;
747 break;
748 case FPIN_CONGN_OVERSUBSCRIPTION:
749 stats->cn_oversubscription++;
750 break;
751 case FPIN_CONGN_DEVICE_SPEC:
752 stats->cn_device_specific++;
753 }
754}
755
756
757
758
759
760
761
762
763static void
764fc_fpin_li_stats_update(struct Scsi_Host *shost, struct fc_tlv_desc *tlv)
765{
766 u8 i;
767 struct fc_rport *rport = NULL;
768 struct fc_rport *attach_rport = NULL;
769 struct fc_host_attrs *fc_host = shost_to_fc_host(shost);
770 struct fc_fn_li_desc *li_desc = (struct fc_fn_li_desc *)tlv;
771 u64 wwpn;
772
773 rport = fc_find_rport_by_wwpn(shost,
774 be64_to_cpu(li_desc->attached_wwpn));
775 if (rport &&
776 (rport->roles & FC_PORT_ROLE_FCP_TARGET ||
777 rport->roles & FC_PORT_ROLE_NVME_TARGET)) {
778 attach_rport = rport;
779 fc_li_stats_update(li_desc, &attach_rport->fpin_stats);
780 }
781
782 if (be32_to_cpu(li_desc->pname_count) > 0) {
783 for (i = 0;
784 i < be32_to_cpu(li_desc->pname_count);
785 i++) {
786 wwpn = be64_to_cpu(li_desc->pname_list[i]);
787 rport = fc_find_rport_by_wwpn(shost, wwpn);
788 if (rport &&
789 (rport->roles & FC_PORT_ROLE_FCP_TARGET ||
790 rport->roles & FC_PORT_ROLE_NVME_TARGET)) {
791 if (rport == attach_rport)
792 continue;
793 fc_li_stats_update(li_desc,
794 &rport->fpin_stats);
795 }
796 }
797 }
798
799 if (fc_host->port_name == be64_to_cpu(li_desc->attached_wwpn))
800 fc_li_stats_update(li_desc, &fc_host->fpin_stats);
801}
802
803
804
805
806
807
808
809
810static void
811fc_fpin_delivery_stats_update(struct Scsi_Host *shost,
812 struct fc_tlv_desc *tlv)
813{
814 struct fc_rport *rport = NULL;
815 struct fc_rport *attach_rport = NULL;
816 struct fc_host_attrs *fc_host = shost_to_fc_host(shost);
817 struct fc_fn_deli_desc *dn_desc = (struct fc_fn_deli_desc *)tlv;
818 u32 reason_code = be32_to_cpu(dn_desc->deli_reason_code);
819
820 rport = fc_find_rport_by_wwpn(shost,
821 be64_to_cpu(dn_desc->attached_wwpn));
822 if (rport &&
823 (rport->roles & FC_PORT_ROLE_FCP_TARGET ||
824 rport->roles & FC_PORT_ROLE_NVME_TARGET)) {
825 attach_rport = rport;
826 fc_delivery_stats_update(reason_code,
827 &attach_rport->fpin_stats);
828 }
829
830 if (fc_host->port_name == be64_to_cpu(dn_desc->attached_wwpn))
831 fc_delivery_stats_update(reason_code, &fc_host->fpin_stats);
832}
833
834
835
836
837
838
839
840
841static void
842fc_fpin_peer_congn_stats_update(struct Scsi_Host *shost,
843 struct fc_tlv_desc *tlv)
844{
845 u8 i;
846 struct fc_rport *rport = NULL;
847 struct fc_rport *attach_rport = NULL;
848 struct fc_fn_peer_congn_desc *pc_desc =
849 (struct fc_fn_peer_congn_desc *)tlv;
850 u16 event_type = be16_to_cpu(pc_desc->event_type);
851 u64 wwpn;
852
853 rport = fc_find_rport_by_wwpn(shost,
854 be64_to_cpu(pc_desc->attached_wwpn));
855 if (rport &&
856 (rport->roles & FC_PORT_ROLE_FCP_TARGET ||
857 rport->roles & FC_PORT_ROLE_NVME_TARGET)) {
858 attach_rport = rport;
859 fc_cn_stats_update(event_type, &attach_rport->fpin_stats);
860 }
861
862 if (be32_to_cpu(pc_desc->pname_count) > 0) {
863 for (i = 0;
864 i < be32_to_cpu(pc_desc->pname_count);
865 i++) {
866 wwpn = be64_to_cpu(pc_desc->pname_list[i]);
867 rport = fc_find_rport_by_wwpn(shost, wwpn);
868 if (rport &&
869 (rport->roles & FC_PORT_ROLE_FCP_TARGET ||
870 rport->roles & FC_PORT_ROLE_NVME_TARGET)) {
871 if (rport == attach_rport)
872 continue;
873 fc_cn_stats_update(event_type,
874 &rport->fpin_stats);
875 }
876 }
877 }
878}
879
880
881
882
883
884
885
886
887static void
888fc_fpin_congn_stats_update(struct Scsi_Host *shost,
889 struct fc_tlv_desc *tlv)
890{
891 struct fc_host_attrs *fc_host = shost_to_fc_host(shost);
892 struct fc_fn_congn_desc *congn = (struct fc_fn_congn_desc *)tlv;
893
894 fc_cn_stats_update(be16_to_cpu(congn->event_type),
895 &fc_host->fpin_stats);
896}
897
898
899
900
901
902
903
904
905
906
907void
908fc_host_fpin_rcv(struct Scsi_Host *shost, u32 fpin_len, char *fpin_buf)
909{
910 struct fc_els_fpin *fpin = (struct fc_els_fpin *)fpin_buf;
911 struct fc_tlv_desc *tlv;
912 u32 desc_cnt = 0, bytes_remain;
913 u32 dtag;
914
915
916 tlv = (struct fc_tlv_desc *)&fpin->fpin_desc[0];
917 bytes_remain = fpin_len - offsetof(struct fc_els_fpin, fpin_desc);
918 bytes_remain = min_t(u32, bytes_remain, be32_to_cpu(fpin->desc_len));
919
920 while (bytes_remain >= FC_TLV_DESC_HDR_SZ &&
921 bytes_remain >= FC_TLV_DESC_SZ_FROM_LENGTH(tlv)) {
922 dtag = be32_to_cpu(tlv->desc_tag);
923 switch (dtag) {
924 case ELS_DTAG_LNK_INTEGRITY:
925 fc_fpin_li_stats_update(shost, tlv);
926 break;
927 case ELS_DTAG_DELIVERY:
928 fc_fpin_delivery_stats_update(shost, tlv);
929 break;
930 case ELS_DTAG_PEER_CONGEST:
931 fc_fpin_peer_congn_stats_update(shost, tlv);
932 break;
933 case ELS_DTAG_CONGESTION:
934 fc_fpin_congn_stats_update(shost, tlv);
935 }
936
937 desc_cnt++;
938 bytes_remain -= FC_TLV_DESC_SZ_FROM_LENGTH(tlv);
939 tlv = fc_tlv_next_desc(tlv);
940 }
941
942 fc_host_post_fc_event(shost, fc_get_event_number(),
943 FCH_EVT_LINK_FPIN, fpin_len, fpin_buf, 0);
944}
945EXPORT_SYMBOL(fc_host_fpin_rcv);
946
947
948static __init int fc_transport_init(void)
949{
950 int error;
951
952 atomic_set(&fc_event_seq, 0);
953
954 error = transport_class_register(&fc_host_class);
955 if (error)
956 return error;
957 error = transport_class_register(&fc_vport_class);
958 if (error)
959 goto unreg_host_class;
960 error = transport_class_register(&fc_rport_class);
961 if (error)
962 goto unreg_vport_class;
963 error = transport_class_register(&fc_transport_class);
964 if (error)
965 goto unreg_rport_class;
966 return 0;
967
968unreg_rport_class:
969 transport_class_unregister(&fc_rport_class);
970unreg_vport_class:
971 transport_class_unregister(&fc_vport_class);
972unreg_host_class:
973 transport_class_unregister(&fc_host_class);
974 return error;
975}
976
977static void __exit fc_transport_exit(void)
978{
979 transport_class_unregister(&fc_transport_class);
980 transport_class_unregister(&fc_rport_class);
981 transport_class_unregister(&fc_host_class);
982 transport_class_unregister(&fc_vport_class);
983}
984
985
986
987
988
989#define fc_rport_show_function(field, format_string, sz, cast) \
990static ssize_t \
991show_fc_rport_##field (struct device *dev, \
992 struct device_attribute *attr, char *buf) \
993{ \
994 struct fc_rport *rport = transport_class_to_rport(dev); \
995 struct Scsi_Host *shost = rport_to_shost(rport); \
996 struct fc_internal *i = to_fc_internal(shost->transportt); \
997 if ((i->f->get_rport_##field) && \
998 !((rport->port_state == FC_PORTSTATE_BLOCKED) || \
999 (rport->port_state == FC_PORTSTATE_DELETED) || \
1000 (rport->port_state == FC_PORTSTATE_NOTPRESENT))) \
1001 i->f->get_rport_##field(rport); \
1002 return snprintf(buf, sz, format_string, cast rport->field); \
1003}
1004
1005#define fc_rport_store_function(field) \
1006static ssize_t \
1007store_fc_rport_##field(struct device *dev, \
1008 struct device_attribute *attr, \
1009 const char *buf, size_t count) \
1010{ \
1011 int val; \
1012 struct fc_rport *rport = transport_class_to_rport(dev); \
1013 struct Scsi_Host *shost = rport_to_shost(rport); \
1014 struct fc_internal *i = to_fc_internal(shost->transportt); \
1015 char *cp; \
1016 if ((rport->port_state == FC_PORTSTATE_BLOCKED) || \
1017 (rport->port_state == FC_PORTSTATE_DELETED) || \
1018 (rport->port_state == FC_PORTSTATE_NOTPRESENT)) \
1019 return -EBUSY; \
1020 val = simple_strtoul(buf, &cp, 0); \
1021 if (*cp && (*cp != '\n')) \
1022 return -EINVAL; \
1023 i->f->set_rport_##field(rport, val); \
1024 return count; \
1025}
1026
1027#define fc_rport_rd_attr(field, format_string, sz) \
1028 fc_rport_show_function(field, format_string, sz, ) \
1029static FC_DEVICE_ATTR(rport, field, S_IRUGO, \
1030 show_fc_rport_##field, NULL)
1031
1032#define fc_rport_rd_attr_cast(field, format_string, sz, cast) \
1033 fc_rport_show_function(field, format_string, sz, (cast)) \
1034static FC_DEVICE_ATTR(rport, field, S_IRUGO, \
1035 show_fc_rport_##field, NULL)
1036
1037#define fc_rport_rw_attr(field, format_string, sz) \
1038 fc_rport_show_function(field, format_string, sz, ) \
1039 fc_rport_store_function(field) \
1040static FC_DEVICE_ATTR(rport, field, S_IRUGO | S_IWUSR, \
1041 show_fc_rport_##field, \
1042 store_fc_rport_##field)
1043
1044
1045#define fc_private_rport_show_function(field, format_string, sz, cast) \
1046static ssize_t \
1047show_fc_rport_##field (struct device *dev, \
1048 struct device_attribute *attr, char *buf) \
1049{ \
1050 struct fc_rport *rport = transport_class_to_rport(dev); \
1051 return snprintf(buf, sz, format_string, cast rport->field); \
1052}
1053
1054#define fc_private_rport_rd_attr(field, format_string, sz) \
1055 fc_private_rport_show_function(field, format_string, sz, ) \
1056static FC_DEVICE_ATTR(rport, field, S_IRUGO, \
1057 show_fc_rport_##field, NULL)
1058
1059#define fc_private_rport_rd_attr_cast(field, format_string, sz, cast) \
1060 fc_private_rport_show_function(field, format_string, sz, (cast)) \
1061static FC_DEVICE_ATTR(rport, field, S_IRUGO, \
1062 show_fc_rport_##field, NULL)
1063
1064
1065#define fc_private_rport_rd_enum_attr(title, maxlen) \
1066static ssize_t \
1067show_fc_rport_##title (struct device *dev, \
1068 struct device_attribute *attr, char *buf) \
1069{ \
1070 struct fc_rport *rport = transport_class_to_rport(dev); \
1071 const char *name; \
1072 name = get_fc_##title##_name(rport->title); \
1073 if (!name) \
1074 return -EINVAL; \
1075 return snprintf(buf, maxlen, "%s\n", name); \
1076} \
1077static FC_DEVICE_ATTR(rport, title, S_IRUGO, \
1078 show_fc_rport_##title, NULL)
1079
1080
1081#define SETUP_RPORT_ATTRIBUTE_RD(field) \
1082 i->private_rport_attrs[count] = device_attr_rport_##field; \
1083 i->private_rport_attrs[count].attr.mode = S_IRUGO; \
1084 i->private_rport_attrs[count].store = NULL; \
1085 i->rport_attrs[count] = &i->private_rport_attrs[count]; \
1086 if (i->f->show_rport_##field) \
1087 count++
1088
1089#define SETUP_PRIVATE_RPORT_ATTRIBUTE_RD(field) \
1090 i->private_rport_attrs[count] = device_attr_rport_##field; \
1091 i->private_rport_attrs[count].attr.mode = S_IRUGO; \
1092 i->private_rport_attrs[count].store = NULL; \
1093 i->rport_attrs[count] = &i->private_rport_attrs[count]; \
1094 count++
1095
1096#define SETUP_RPORT_ATTRIBUTE_RW(field) \
1097 i->private_rport_attrs[count] = device_attr_rport_##field; \
1098 if (!i->f->set_rport_##field) { \
1099 i->private_rport_attrs[count].attr.mode = S_IRUGO; \
1100 i->private_rport_attrs[count].store = NULL; \
1101 } \
1102 i->rport_attrs[count] = &i->private_rport_attrs[count]; \
1103 if (i->f->show_rport_##field) \
1104 count++
1105
1106#define SETUP_PRIVATE_RPORT_ATTRIBUTE_RW(field) \
1107{ \
1108 i->private_rport_attrs[count] = device_attr_rport_##field; \
1109 i->rport_attrs[count] = &i->private_rport_attrs[count]; \
1110 count++; \
1111}
1112
1113
1114
1115
1116
1117
1118fc_private_rport_rd_attr(maxframe_size, "%u bytes\n", 20);
1119
1120static ssize_t
1121show_fc_rport_supported_classes (struct device *dev,
1122 struct device_attribute *attr, char *buf)
1123{
1124 struct fc_rport *rport = transport_class_to_rport(dev);
1125 if (rport->supported_classes == FC_COS_UNSPECIFIED)
1126 return snprintf(buf, 20, "unspecified\n");
1127 return get_fc_cos_names(rport->supported_classes, buf);
1128}
1129static FC_DEVICE_ATTR(rport, supported_classes, S_IRUGO,
1130 show_fc_rport_supported_classes, NULL);
1131
1132
1133
1134
1135
1136
1137static int fc_str_to_dev_loss(const char *buf, unsigned long *val)
1138{
1139 char *cp;
1140
1141 *val = simple_strtoul(buf, &cp, 0);
1142 if (*cp && (*cp != '\n'))
1143 return -EINVAL;
1144
1145
1146
1147 if (*val > UINT_MAX)
1148 return -EINVAL;
1149
1150 return 0;
1151}
1152
1153static int fc_rport_set_dev_loss_tmo(struct fc_rport *rport,
1154 unsigned long val)
1155{
1156 struct Scsi_Host *shost = rport_to_shost(rport);
1157 struct fc_internal *i = to_fc_internal(shost->transportt);
1158
1159 if ((rport->port_state == FC_PORTSTATE_BLOCKED) ||
1160 (rport->port_state == FC_PORTSTATE_DELETED) ||
1161 (rport->port_state == FC_PORTSTATE_NOTPRESENT))
1162 return -EBUSY;
1163
1164
1165
1166 if (val > UINT_MAX)
1167 return -EINVAL;
1168
1169
1170
1171
1172
1173 if (rport->fast_io_fail_tmo == -1 &&
1174 val > SCSI_DEVICE_BLOCK_MAX_TIMEOUT)
1175 return -EINVAL;
1176
1177 i->f->set_rport_dev_loss_tmo(rport, val);
1178 return 0;
1179}
1180
1181fc_rport_show_function(dev_loss_tmo, "%d\n", 20, )
1182static ssize_t
1183store_fc_rport_dev_loss_tmo(struct device *dev, struct device_attribute *attr,
1184 const char *buf, size_t count)
1185{
1186 struct fc_rport *rport = transport_class_to_rport(dev);
1187 unsigned long val;
1188 int rc;
1189
1190 rc = fc_str_to_dev_loss(buf, &val);
1191 if (rc)
1192 return rc;
1193
1194 rc = fc_rport_set_dev_loss_tmo(rport, val);
1195 if (rc)
1196 return rc;
1197 return count;
1198}
1199static FC_DEVICE_ATTR(rport, dev_loss_tmo, S_IRUGO | S_IWUSR,
1200 show_fc_rport_dev_loss_tmo, store_fc_rport_dev_loss_tmo);
1201
1202
1203
1204
1205fc_private_rport_rd_attr_cast(node_name, "0x%llx\n", 20, unsigned long long);
1206fc_private_rport_rd_attr_cast(port_name, "0x%llx\n", 20, unsigned long long);
1207fc_private_rport_rd_attr(port_id, "0x%06x\n", 20);
1208
1209static ssize_t
1210show_fc_rport_roles (struct device *dev, struct device_attribute *attr,
1211 char *buf)
1212{
1213 struct fc_rport *rport = transport_class_to_rport(dev);
1214
1215
1216 if ((rport->port_id != -1) &&
1217 (rport->port_id & FC_WELLKNOWN_PORTID_MASK) ==
1218 FC_WELLKNOWN_PORTID_MASK) {
1219 switch (rport->port_id & FC_WELLKNOWN_ROLE_MASK) {
1220 case FC_FPORT_PORTID:
1221 return snprintf(buf, 30, "Fabric Port\n");
1222 case FC_FABCTLR_PORTID:
1223 return snprintf(buf, 30, "Fabric Controller\n");
1224 case FC_DIRSRVR_PORTID:
1225 return snprintf(buf, 30, "Directory Server\n");
1226 case FC_TIMESRVR_PORTID:
1227 return snprintf(buf, 30, "Time Server\n");
1228 case FC_MGMTSRVR_PORTID:
1229 return snprintf(buf, 30, "Management Server\n");
1230 default:
1231 return snprintf(buf, 30, "Unknown Fabric Entity\n");
1232 }
1233 } else {
1234 if (rport->roles == FC_PORT_ROLE_UNKNOWN)
1235 return snprintf(buf, 20, "unknown\n");
1236 return get_fc_port_roles_names(rport->roles, buf);
1237 }
1238}
1239static FC_DEVICE_ATTR(rport, roles, S_IRUGO,
1240 show_fc_rport_roles, NULL);
1241
1242static ssize_t fc_rport_set_marginal_state(struct device *dev,
1243 struct device_attribute *attr,
1244 const char *buf, size_t count)
1245{
1246 struct fc_rport *rport = transport_class_to_rport(dev);
1247 enum fc_port_state port_state;
1248 int ret = 0;
1249
1250 ret = get_fc_port_state_match(buf, &port_state);
1251 if (ret)
1252 return -EINVAL;
1253 if (port_state == FC_PORTSTATE_MARGINAL) {
1254
1255
1256
1257
1258
1259 if (rport->port_state == FC_PORTSTATE_ONLINE)
1260 rport->port_state = port_state;
1261 else
1262 return -EINVAL;
1263 } else if (port_state == FC_PORTSTATE_ONLINE) {
1264
1265
1266
1267
1268
1269 if (rport->port_state == FC_PORTSTATE_MARGINAL)
1270 rport->port_state = port_state;
1271 else
1272 return -EINVAL;
1273 } else
1274 return -EINVAL;
1275 return count;
1276}
1277
1278static ssize_t
1279show_fc_rport_port_state(struct device *dev,
1280 struct device_attribute *attr, char *buf)
1281{
1282 const char *name;
1283 struct fc_rport *rport = transport_class_to_rport(dev);
1284
1285 name = get_fc_port_state_name(rport->port_state);
1286 if (!name)
1287 return -EINVAL;
1288
1289 return snprintf(buf, 20, "%s\n", name);
1290}
1291
1292static FC_DEVICE_ATTR(rport, port_state, 0444 | 0200,
1293 show_fc_rport_port_state, fc_rport_set_marginal_state);
1294
1295fc_private_rport_rd_attr(scsi_target_id, "%d\n", 20);
1296
1297
1298
1299
1300static ssize_t
1301show_fc_rport_fast_io_fail_tmo (struct device *dev,
1302 struct device_attribute *attr, char *buf)
1303{
1304 struct fc_rport *rport = transport_class_to_rport(dev);
1305
1306 if (rport->fast_io_fail_tmo == -1)
1307 return snprintf(buf, 5, "off\n");
1308 return snprintf(buf, 20, "%d\n", rport->fast_io_fail_tmo);
1309}
1310
1311static ssize_t
1312store_fc_rport_fast_io_fail_tmo(struct device *dev,
1313 struct device_attribute *attr, const char *buf,
1314 size_t count)
1315{
1316 int val;
1317 char *cp;
1318 struct fc_rport *rport = transport_class_to_rport(dev);
1319
1320 if ((rport->port_state == FC_PORTSTATE_BLOCKED) ||
1321 (rport->port_state == FC_PORTSTATE_DELETED) ||
1322 (rport->port_state == FC_PORTSTATE_NOTPRESENT))
1323 return -EBUSY;
1324 if (strncmp(buf, "off", 3) == 0)
1325 rport->fast_io_fail_tmo = -1;
1326 else {
1327 val = simple_strtoul(buf, &cp, 0);
1328 if ((*cp && (*cp != '\n')) || (val < 0))
1329 return -EINVAL;
1330
1331
1332
1333
1334 if ((val >= rport->dev_loss_tmo) ||
1335 (val > SCSI_DEVICE_BLOCK_MAX_TIMEOUT))
1336 return -EINVAL;
1337
1338 rport->fast_io_fail_tmo = val;
1339 }
1340 return count;
1341}
1342static FC_DEVICE_ATTR(rport, fast_io_fail_tmo, S_IRUGO | S_IWUSR,
1343 show_fc_rport_fast_io_fail_tmo, store_fc_rport_fast_io_fail_tmo);
1344
1345#define fc_rport_fpin_statistic(name) \
1346static ssize_t fc_rport_fpinstat_##name(struct device *cd, \
1347 struct device_attribute *attr, \
1348 char *buf) \
1349{ \
1350 struct fc_rport *rport = transport_class_to_rport(cd); \
1351 \
1352 return snprintf(buf, 20, "0x%llx\n", rport->fpin_stats.name); \
1353} \
1354static FC_DEVICE_ATTR(rport, fpin_##name, 0444, fc_rport_fpinstat_##name, NULL)
1355
1356fc_rport_fpin_statistic(dn);
1357fc_rport_fpin_statistic(dn_unknown);
1358fc_rport_fpin_statistic(dn_timeout);
1359fc_rport_fpin_statistic(dn_unable_to_route);
1360fc_rport_fpin_statistic(dn_device_specific);
1361fc_rport_fpin_statistic(cn);
1362fc_rport_fpin_statistic(cn_clear);
1363fc_rport_fpin_statistic(cn_lost_credit);
1364fc_rport_fpin_statistic(cn_credit_stall);
1365fc_rport_fpin_statistic(cn_oversubscription);
1366fc_rport_fpin_statistic(cn_device_specific);
1367fc_rport_fpin_statistic(li);
1368fc_rport_fpin_statistic(li_failure_unknown);
1369fc_rport_fpin_statistic(li_link_failure_count);
1370fc_rport_fpin_statistic(li_loss_of_sync_count);
1371fc_rport_fpin_statistic(li_loss_of_signals_count);
1372fc_rport_fpin_statistic(li_prim_seq_err_count);
1373fc_rport_fpin_statistic(li_invalid_tx_word_count);
1374fc_rport_fpin_statistic(li_invalid_crc_count);
1375fc_rport_fpin_statistic(li_device_specific);
1376
1377static struct attribute *fc_rport_statistics_attrs[] = {
1378 &device_attr_rport_fpin_dn.attr,
1379 &device_attr_rport_fpin_dn_unknown.attr,
1380 &device_attr_rport_fpin_dn_timeout.attr,
1381 &device_attr_rport_fpin_dn_unable_to_route.attr,
1382 &device_attr_rport_fpin_dn_device_specific.attr,
1383 &device_attr_rport_fpin_li.attr,
1384 &device_attr_rport_fpin_li_failure_unknown.attr,
1385 &device_attr_rport_fpin_li_link_failure_count.attr,
1386 &device_attr_rport_fpin_li_loss_of_sync_count.attr,
1387 &device_attr_rport_fpin_li_loss_of_signals_count.attr,
1388 &device_attr_rport_fpin_li_prim_seq_err_count.attr,
1389 &device_attr_rport_fpin_li_invalid_tx_word_count.attr,
1390 &device_attr_rport_fpin_li_invalid_crc_count.attr,
1391 &device_attr_rport_fpin_li_device_specific.attr,
1392 &device_attr_rport_fpin_cn.attr,
1393 &device_attr_rport_fpin_cn_clear.attr,
1394 &device_attr_rport_fpin_cn_lost_credit.attr,
1395 &device_attr_rport_fpin_cn_credit_stall.attr,
1396 &device_attr_rport_fpin_cn_oversubscription.attr,
1397 &device_attr_rport_fpin_cn_device_specific.attr,
1398 NULL
1399};
1400
1401static struct attribute_group fc_rport_statistics_group = {
1402 .name = "statistics",
1403 .attrs = fc_rport_statistics_attrs,
1404};
1405
1406
1407
1408
1409
1410
1411
1412
1413
1414
1415
1416
1417#define fc_starget_show_function(field, format_string, sz, cast) \
1418static ssize_t \
1419show_fc_starget_##field (struct device *dev, \
1420 struct device_attribute *attr, char *buf) \
1421{ \
1422 struct scsi_target *starget = transport_class_to_starget(dev); \
1423 struct Scsi_Host *shost = dev_to_shost(starget->dev.parent); \
1424 struct fc_internal *i = to_fc_internal(shost->transportt); \
1425 struct fc_rport *rport = starget_to_rport(starget); \
1426 if (rport) \
1427 fc_starget_##field(starget) = rport->field; \
1428 else if (i->f->get_starget_##field) \
1429 i->f->get_starget_##field(starget); \
1430 return snprintf(buf, sz, format_string, \
1431 cast fc_starget_##field(starget)); \
1432}
1433
1434#define fc_starget_rd_attr(field, format_string, sz) \
1435 fc_starget_show_function(field, format_string, sz, ) \
1436static FC_DEVICE_ATTR(starget, field, S_IRUGO, \
1437 show_fc_starget_##field, NULL)
1438
1439#define fc_starget_rd_attr_cast(field, format_string, sz, cast) \
1440 fc_starget_show_function(field, format_string, sz, (cast)) \
1441static FC_DEVICE_ATTR(starget, field, S_IRUGO, \
1442 show_fc_starget_##field, NULL)
1443
1444#define SETUP_STARGET_ATTRIBUTE_RD(field) \
1445 i->private_starget_attrs[count] = device_attr_starget_##field; \
1446 i->private_starget_attrs[count].attr.mode = S_IRUGO; \
1447 i->private_starget_attrs[count].store = NULL; \
1448 i->starget_attrs[count] = &i->private_starget_attrs[count]; \
1449 if (i->f->show_starget_##field) \
1450 count++
1451
1452#define SETUP_STARGET_ATTRIBUTE_RW(field) \
1453 i->private_starget_attrs[count] = device_attr_starget_##field; \
1454 if (!i->f->set_starget_##field) { \
1455 i->private_starget_attrs[count].attr.mode = S_IRUGO; \
1456 i->private_starget_attrs[count].store = NULL; \
1457 } \
1458 i->starget_attrs[count] = &i->private_starget_attrs[count]; \
1459 if (i->f->show_starget_##field) \
1460 count++
1461
1462
1463fc_starget_rd_attr_cast(node_name, "0x%llx\n", 20, unsigned long long);
1464fc_starget_rd_attr_cast(port_name, "0x%llx\n", 20, unsigned long long);
1465fc_starget_rd_attr(port_id, "0x%06x\n", 20);
1466
1467
1468
1469
1470
1471
1472#define fc_vport_show_function(field, format_string, sz, cast) \
1473static ssize_t \
1474show_fc_vport_##field (struct device *dev, \
1475 struct device_attribute *attr, char *buf) \
1476{ \
1477 struct fc_vport *vport = transport_class_to_vport(dev); \
1478 struct Scsi_Host *shost = vport_to_shost(vport); \
1479 struct fc_internal *i = to_fc_internal(shost->transportt); \
1480 if ((i->f->get_vport_##field) && \
1481 !(vport->flags & (FC_VPORT_DEL | FC_VPORT_CREATING))) \
1482 i->f->get_vport_##field(vport); \
1483 return snprintf(buf, sz, format_string, cast vport->field); \
1484}
1485
1486#define fc_vport_store_function(field) \
1487static ssize_t \
1488store_fc_vport_##field(struct device *dev, \
1489 struct device_attribute *attr, \
1490 const char *buf, size_t count) \
1491{ \
1492 int val; \
1493 struct fc_vport *vport = transport_class_to_vport(dev); \
1494 struct Scsi_Host *shost = vport_to_shost(vport); \
1495 struct fc_internal *i = to_fc_internal(shost->transportt); \
1496 char *cp; \
1497 if (vport->flags & (FC_VPORT_DEL | FC_VPORT_CREATING)) \
1498 return -EBUSY; \
1499 val = simple_strtoul(buf, &cp, 0); \
1500 if (*cp && (*cp != '\n')) \
1501 return -EINVAL; \
1502 i->f->set_vport_##field(vport, val); \
1503 return count; \
1504}
1505
1506#define fc_vport_store_str_function(field, slen) \
1507static ssize_t \
1508store_fc_vport_##field(struct device *dev, \
1509 struct device_attribute *attr, \
1510 const char *buf, size_t count) \
1511{ \
1512 struct fc_vport *vport = transport_class_to_vport(dev); \
1513 struct Scsi_Host *shost = vport_to_shost(vport); \
1514 struct fc_internal *i = to_fc_internal(shost->transportt); \
1515 unsigned int cnt=count; \
1516 \
1517 \
1518 if (buf[cnt-1] == '\n') \
1519 cnt--; \
1520 if (cnt > ((slen) - 1)) \
1521 return -EINVAL; \
1522 memcpy(vport->field, buf, cnt); \
1523 i->f->set_vport_##field(vport); \
1524 return count; \
1525}
1526
1527#define fc_vport_rd_attr(field, format_string, sz) \
1528 fc_vport_show_function(field, format_string, sz, ) \
1529static FC_DEVICE_ATTR(vport, field, S_IRUGO, \
1530 show_fc_vport_##field, NULL)
1531
1532#define fc_vport_rd_attr_cast(field, format_string, sz, cast) \
1533 fc_vport_show_function(field, format_string, sz, (cast)) \
1534static FC_DEVICE_ATTR(vport, field, S_IRUGO, \
1535 show_fc_vport_##field, NULL)
1536
1537#define fc_vport_rw_attr(field, format_string, sz) \
1538 fc_vport_show_function(field, format_string, sz, ) \
1539 fc_vport_store_function(field) \
1540static FC_DEVICE_ATTR(vport, field, S_IRUGO | S_IWUSR, \
1541 show_fc_vport_##field, \
1542 store_fc_vport_##field)
1543
1544#define fc_private_vport_show_function(field, format_string, sz, cast) \
1545static ssize_t \
1546show_fc_vport_##field (struct device *dev, \
1547 struct device_attribute *attr, char *buf) \
1548{ \
1549 struct fc_vport *vport = transport_class_to_vport(dev); \
1550 return snprintf(buf, sz, format_string, cast vport->field); \
1551}
1552
1553#define fc_private_vport_store_u32_function(field) \
1554static ssize_t \
1555store_fc_vport_##field(struct device *dev, \
1556 struct device_attribute *attr, \
1557 const char *buf, size_t count) \
1558{ \
1559 u32 val; \
1560 struct fc_vport *vport = transport_class_to_vport(dev); \
1561 char *cp; \
1562 if (vport->flags & (FC_VPORT_DEL | FC_VPORT_CREATING)) \
1563 return -EBUSY; \
1564 val = simple_strtoul(buf, &cp, 0); \
1565 if (*cp && (*cp != '\n')) \
1566 return -EINVAL; \
1567 vport->field = val; \
1568 return count; \
1569}
1570
1571
1572#define fc_private_vport_rd_attr(field, format_string, sz) \
1573 fc_private_vport_show_function(field, format_string, sz, ) \
1574static FC_DEVICE_ATTR(vport, field, S_IRUGO, \
1575 show_fc_vport_##field, NULL)
1576
1577#define fc_private_vport_rd_attr_cast(field, format_string, sz, cast) \
1578 fc_private_vport_show_function(field, format_string, sz, (cast)) \
1579static FC_DEVICE_ATTR(vport, field, S_IRUGO, \
1580 show_fc_vport_##field, NULL)
1581
1582#define fc_private_vport_rw_u32_attr(field, format_string, sz) \
1583 fc_private_vport_show_function(field, format_string, sz, ) \
1584 fc_private_vport_store_u32_function(field) \
1585static FC_DEVICE_ATTR(vport, field, S_IRUGO | S_IWUSR, \
1586 show_fc_vport_##field, \
1587 store_fc_vport_##field)
1588
1589
1590#define fc_private_vport_rd_enum_attr(title, maxlen) \
1591static ssize_t \
1592show_fc_vport_##title (struct device *dev, \
1593 struct device_attribute *attr, \
1594 char *buf) \
1595{ \
1596 struct fc_vport *vport = transport_class_to_vport(dev); \
1597 const char *name; \
1598 name = get_fc_##title##_name(vport->title); \
1599 if (!name) \
1600 return -EINVAL; \
1601 return snprintf(buf, maxlen, "%s\n", name); \
1602} \
1603static FC_DEVICE_ATTR(vport, title, S_IRUGO, \
1604 show_fc_vport_##title, NULL)
1605
1606
1607#define SETUP_VPORT_ATTRIBUTE_RD(field) \
1608 i->private_vport_attrs[count] = device_attr_vport_##field; \
1609 i->private_vport_attrs[count].attr.mode = S_IRUGO; \
1610 i->private_vport_attrs[count].store = NULL; \
1611 i->vport_attrs[count] = &i->private_vport_attrs[count]; \
1612 if (i->f->get_##field) \
1613 count++
1614
1615
1616#define SETUP_PRIVATE_VPORT_ATTRIBUTE_RD(field) \
1617 i->private_vport_attrs[count] = device_attr_vport_##field; \
1618 i->private_vport_attrs[count].attr.mode = S_IRUGO; \
1619 i->private_vport_attrs[count].store = NULL; \
1620 i->vport_attrs[count] = &i->private_vport_attrs[count]; \
1621 count++
1622
1623#define SETUP_VPORT_ATTRIBUTE_WR(field) \
1624 i->private_vport_attrs[count] = device_attr_vport_##field; \
1625 i->vport_attrs[count] = &i->private_vport_attrs[count]; \
1626 if (i->f->field) \
1627 count++
1628
1629
1630#define SETUP_VPORT_ATTRIBUTE_RW(field) \
1631 i->private_vport_attrs[count] = device_attr_vport_##field; \
1632 if (!i->f->set_vport_##field) { \
1633 i->private_vport_attrs[count].attr.mode = S_IRUGO; \
1634 i->private_vport_attrs[count].store = NULL; \
1635 } \
1636 i->vport_attrs[count] = &i->private_vport_attrs[count]; \
1637 count++
1638
1639
1640#define SETUP_PRIVATE_VPORT_ATTRIBUTE_RW(field) \
1641{ \
1642 i->private_vport_attrs[count] = device_attr_vport_##field; \
1643 i->vport_attrs[count] = &i->private_vport_attrs[count]; \
1644 count++; \
1645}
1646
1647
1648
1649
1650
1651
1652
1653
1654
1655
1656fc_private_vport_rd_enum_attr(vport_state, FC_VPORTSTATE_MAX_NAMELEN);
1657fc_private_vport_rd_enum_attr(vport_last_state, FC_VPORTSTATE_MAX_NAMELEN);
1658fc_private_vport_rd_attr_cast(node_name, "0x%llx\n", 20, unsigned long long);
1659fc_private_vport_rd_attr_cast(port_name, "0x%llx\n", 20, unsigned long long);
1660
1661static ssize_t
1662show_fc_vport_roles (struct device *dev, struct device_attribute *attr,
1663 char *buf)
1664{
1665 struct fc_vport *vport = transport_class_to_vport(dev);
1666
1667 if (vport->roles == FC_PORT_ROLE_UNKNOWN)
1668 return snprintf(buf, 20, "unknown\n");
1669 return get_fc_port_roles_names(vport->roles, buf);
1670}
1671static FC_DEVICE_ATTR(vport, roles, S_IRUGO, show_fc_vport_roles, NULL);
1672
1673fc_private_vport_rd_enum_attr(vport_type, FC_PORTTYPE_MAX_NAMELEN);
1674
1675fc_private_vport_show_function(symbolic_name, "%s\n",
1676 FC_VPORT_SYMBOLIC_NAMELEN + 1, )
1677fc_vport_store_str_function(symbolic_name, FC_VPORT_SYMBOLIC_NAMELEN)
1678static FC_DEVICE_ATTR(vport, symbolic_name, S_IRUGO | S_IWUSR,
1679 show_fc_vport_symbolic_name, store_fc_vport_symbolic_name);
1680
1681static ssize_t
1682store_fc_vport_delete(struct device *dev, struct device_attribute *attr,
1683 const char *buf, size_t count)
1684{
1685 struct fc_vport *vport = transport_class_to_vport(dev);
1686 struct Scsi_Host *shost = vport_to_shost(vport);
1687 unsigned long flags;
1688
1689 spin_lock_irqsave(shost->host_lock, flags);
1690 if (vport->flags & (FC_VPORT_DEL | FC_VPORT_CREATING | FC_VPORT_DELETING)) {
1691 spin_unlock_irqrestore(shost->host_lock, flags);
1692 return -EBUSY;
1693 }
1694 vport->flags |= FC_VPORT_DELETING;
1695 spin_unlock_irqrestore(shost->host_lock, flags);
1696
1697 fc_queue_work(shost, &vport->vport_delete_work);
1698 return count;
1699}
1700static FC_DEVICE_ATTR(vport, vport_delete, S_IWUSR,
1701 NULL, store_fc_vport_delete);
1702
1703
1704
1705
1706
1707
1708static ssize_t
1709store_fc_vport_disable(struct device *dev, struct device_attribute *attr,
1710 const char *buf,
1711 size_t count)
1712{
1713 struct fc_vport *vport = transport_class_to_vport(dev);
1714 struct Scsi_Host *shost = vport_to_shost(vport);
1715 struct fc_internal *i = to_fc_internal(shost->transportt);
1716 int stat;
1717
1718 if (vport->flags & (FC_VPORT_DEL | FC_VPORT_CREATING))
1719 return -EBUSY;
1720
1721 if (*buf == '0') {
1722 if (vport->vport_state != FC_VPORT_DISABLED)
1723 return -EALREADY;
1724 } else if (*buf == '1') {
1725 if (vport->vport_state == FC_VPORT_DISABLED)
1726 return -EALREADY;
1727 } else
1728 return -EINVAL;
1729
1730 stat = i->f->vport_disable(vport, ((*buf == '0') ? false : true));
1731 return stat ? stat : count;
1732}
1733static FC_DEVICE_ATTR(vport, vport_disable, S_IWUSR,
1734 NULL, store_fc_vport_disable);
1735
1736
1737
1738
1739
1740
1741#define fc_host_show_function(field, format_string, sz, cast) \
1742static ssize_t \
1743show_fc_host_##field (struct device *dev, \
1744 struct device_attribute *attr, char *buf) \
1745{ \
1746 struct Scsi_Host *shost = transport_class_to_shost(dev); \
1747 struct fc_internal *i = to_fc_internal(shost->transportt); \
1748 if (i->f->get_host_##field) \
1749 i->f->get_host_##field(shost); \
1750 return snprintf(buf, sz, format_string, cast fc_host_##field(shost)); \
1751}
1752
1753#define fc_host_store_function(field) \
1754static ssize_t \
1755store_fc_host_##field(struct device *dev, \
1756 struct device_attribute *attr, \
1757 const char *buf, size_t count) \
1758{ \
1759 int val; \
1760 struct Scsi_Host *shost = transport_class_to_shost(dev); \
1761 struct fc_internal *i = to_fc_internal(shost->transportt); \
1762 char *cp; \
1763 \
1764 val = simple_strtoul(buf, &cp, 0); \
1765 if (*cp && (*cp != '\n')) \
1766 return -EINVAL; \
1767 i->f->set_host_##field(shost, val); \
1768 return count; \
1769}
1770
1771#define fc_host_store_str_function(field, slen) \
1772static ssize_t \
1773store_fc_host_##field(struct device *dev, \
1774 struct device_attribute *attr, \
1775 const char *buf, size_t count) \
1776{ \
1777 struct Scsi_Host *shost = transport_class_to_shost(dev); \
1778 struct fc_internal *i = to_fc_internal(shost->transportt); \
1779 unsigned int cnt=count; \
1780 \
1781 \
1782 if (buf[cnt-1] == '\n') \
1783 cnt--; \
1784 if (cnt > ((slen) - 1)) \
1785 return -EINVAL; \
1786 memcpy(fc_host_##field(shost), buf, cnt); \
1787 i->f->set_host_##field(shost); \
1788 return count; \
1789}
1790
1791#define fc_host_rd_attr(field, format_string, sz) \
1792 fc_host_show_function(field, format_string, sz, ) \
1793static FC_DEVICE_ATTR(host, field, S_IRUGO, \
1794 show_fc_host_##field, NULL)
1795
1796#define fc_host_rd_attr_cast(field, format_string, sz, cast) \
1797 fc_host_show_function(field, format_string, sz, (cast)) \
1798static FC_DEVICE_ATTR(host, field, S_IRUGO, \
1799 show_fc_host_##field, NULL)
1800
1801#define fc_host_rw_attr(field, format_string, sz) \
1802 fc_host_show_function(field, format_string, sz, ) \
1803 fc_host_store_function(field) \
1804static FC_DEVICE_ATTR(host, field, S_IRUGO | S_IWUSR, \
1805 show_fc_host_##field, \
1806 store_fc_host_##field)
1807
1808#define fc_host_rd_enum_attr(title, maxlen) \
1809static ssize_t \
1810show_fc_host_##title (struct device *dev, \
1811 struct device_attribute *attr, char *buf) \
1812{ \
1813 struct Scsi_Host *shost = transport_class_to_shost(dev); \
1814 struct fc_internal *i = to_fc_internal(shost->transportt); \
1815 const char *name; \
1816 if (i->f->get_host_##title) \
1817 i->f->get_host_##title(shost); \
1818 name = get_fc_##title##_name(fc_host_##title(shost)); \
1819 if (!name) \
1820 return -EINVAL; \
1821 return snprintf(buf, maxlen, "%s\n", name); \
1822} \
1823static FC_DEVICE_ATTR(host, title, S_IRUGO, show_fc_host_##title, NULL)
1824
1825#define SETUP_HOST_ATTRIBUTE_RD(field) \
1826 i->private_host_attrs[count] = device_attr_host_##field; \
1827 i->private_host_attrs[count].attr.mode = S_IRUGO; \
1828 i->private_host_attrs[count].store = NULL; \
1829 i->host_attrs[count] = &i->private_host_attrs[count]; \
1830 if (i->f->show_host_##field) \
1831 count++
1832
1833#define SETUP_HOST_ATTRIBUTE_RD_NS(field) \
1834 i->private_host_attrs[count] = device_attr_host_##field; \
1835 i->private_host_attrs[count].attr.mode = S_IRUGO; \
1836 i->private_host_attrs[count].store = NULL; \
1837 i->host_attrs[count] = &i->private_host_attrs[count]; \
1838 count++
1839
1840#define SETUP_HOST_ATTRIBUTE_RW(field) \
1841 i->private_host_attrs[count] = device_attr_host_##field; \
1842 if (!i->f->set_host_##field) { \
1843 i->private_host_attrs[count].attr.mode = S_IRUGO; \
1844 i->private_host_attrs[count].store = NULL; \
1845 } \
1846 i->host_attrs[count] = &i->private_host_attrs[count]; \
1847 if (i->f->show_host_##field) \
1848 count++
1849
1850
1851#define fc_private_host_show_function(field, format_string, sz, cast) \
1852static ssize_t \
1853show_fc_host_##field (struct device *dev, \
1854 struct device_attribute *attr, char *buf) \
1855{ \
1856 struct Scsi_Host *shost = transport_class_to_shost(dev); \
1857 return snprintf(buf, sz, format_string, cast fc_host_##field(shost)); \
1858}
1859
1860#define fc_private_host_rd_attr(field, format_string, sz) \
1861 fc_private_host_show_function(field, format_string, sz, ) \
1862static FC_DEVICE_ATTR(host, field, S_IRUGO, \
1863 show_fc_host_##field, NULL)
1864
1865#define fc_private_host_rd_attr_cast(field, format_string, sz, cast) \
1866 fc_private_host_show_function(field, format_string, sz, (cast)) \
1867static FC_DEVICE_ATTR(host, field, S_IRUGO, \
1868 show_fc_host_##field, NULL)
1869
1870#define SETUP_PRIVATE_HOST_ATTRIBUTE_RD(field) \
1871 i->private_host_attrs[count] = device_attr_host_##field; \
1872 i->private_host_attrs[count].attr.mode = S_IRUGO; \
1873 i->private_host_attrs[count].store = NULL; \
1874 i->host_attrs[count] = &i->private_host_attrs[count]; \
1875 count++
1876
1877#define SETUP_PRIVATE_HOST_ATTRIBUTE_RW(field) \
1878{ \
1879 i->private_host_attrs[count] = device_attr_host_##field; \
1880 i->host_attrs[count] = &i->private_host_attrs[count]; \
1881 count++; \
1882}
1883
1884
1885
1886
1887static ssize_t
1888show_fc_host_supported_classes (struct device *dev,
1889 struct device_attribute *attr, char *buf)
1890{
1891 struct Scsi_Host *shost = transport_class_to_shost(dev);
1892
1893 if (fc_host_supported_classes(shost) == FC_COS_UNSPECIFIED)
1894 return snprintf(buf, 20, "unspecified\n");
1895
1896 return get_fc_cos_names(fc_host_supported_classes(shost), buf);
1897}
1898static FC_DEVICE_ATTR(host, supported_classes, S_IRUGO,
1899 show_fc_host_supported_classes, NULL);
1900
1901static ssize_t
1902show_fc_host_supported_fc4s (struct device *dev,
1903 struct device_attribute *attr, char *buf)
1904{
1905 struct Scsi_Host *shost = transport_class_to_shost(dev);
1906 return (ssize_t)show_fc_fc4s(buf, fc_host_supported_fc4s(shost));
1907}
1908static FC_DEVICE_ATTR(host, supported_fc4s, S_IRUGO,
1909 show_fc_host_supported_fc4s, NULL);
1910
1911static ssize_t
1912show_fc_host_supported_speeds (struct device *dev,
1913 struct device_attribute *attr, char *buf)
1914{
1915 struct Scsi_Host *shost = transport_class_to_shost(dev);
1916
1917 if (fc_host_supported_speeds(shost) == FC_PORTSPEED_UNKNOWN)
1918 return snprintf(buf, 20, "unknown\n");
1919
1920 return get_fc_port_speed_names(fc_host_supported_speeds(shost), buf);
1921}
1922static FC_DEVICE_ATTR(host, supported_speeds, S_IRUGO,
1923 show_fc_host_supported_speeds, NULL);
1924
1925
1926fc_private_host_rd_attr_cast(node_name, "0x%llx\n", 20, unsigned long long);
1927fc_private_host_rd_attr_cast(port_name, "0x%llx\n", 20, unsigned long long);
1928fc_private_host_rd_attr_cast(permanent_port_name, "0x%llx\n", 20,
1929 unsigned long long);
1930fc_private_host_rd_attr(maxframe_size, "%u bytes\n", 20);
1931fc_private_host_rd_attr(max_npiv_vports, "%u\n", 20);
1932fc_private_host_rd_attr(serial_number, "%s\n", (FC_SERIAL_NUMBER_SIZE +1));
1933fc_private_host_rd_attr(manufacturer, "%s\n", FC_SERIAL_NUMBER_SIZE + 1);
1934fc_private_host_rd_attr(model, "%s\n", FC_SYMBOLIC_NAME_SIZE + 1);
1935fc_private_host_rd_attr(model_description, "%s\n", FC_SYMBOLIC_NAME_SIZE + 1);
1936fc_private_host_rd_attr(hardware_version, "%s\n", FC_VERSION_STRING_SIZE + 1);
1937fc_private_host_rd_attr(driver_version, "%s\n", FC_VERSION_STRING_SIZE + 1);
1938fc_private_host_rd_attr(firmware_version, "%s\n", FC_VERSION_STRING_SIZE + 1);
1939fc_private_host_rd_attr(optionrom_version, "%s\n", FC_VERSION_STRING_SIZE + 1);
1940
1941
1942
1943
1944static ssize_t
1945show_fc_host_active_fc4s (struct device *dev,
1946 struct device_attribute *attr, char *buf)
1947{
1948 struct Scsi_Host *shost = transport_class_to_shost(dev);
1949 struct fc_internal *i = to_fc_internal(shost->transportt);
1950
1951 if (i->f->get_host_active_fc4s)
1952 i->f->get_host_active_fc4s(shost);
1953
1954 return (ssize_t)show_fc_fc4s(buf, fc_host_active_fc4s(shost));
1955}
1956static FC_DEVICE_ATTR(host, active_fc4s, S_IRUGO,
1957 show_fc_host_active_fc4s, NULL);
1958
1959static ssize_t
1960show_fc_host_speed (struct device *dev,
1961 struct device_attribute *attr, char *buf)
1962{
1963 struct Scsi_Host *shost = transport_class_to_shost(dev);
1964 struct fc_internal *i = to_fc_internal(shost->transportt);
1965
1966 if (i->f->get_host_speed)
1967 i->f->get_host_speed(shost);
1968
1969 if (fc_host_speed(shost) == FC_PORTSPEED_UNKNOWN)
1970 return snprintf(buf, 20, "unknown\n");
1971
1972 return get_fc_port_speed_names(fc_host_speed(shost), buf);
1973}
1974static FC_DEVICE_ATTR(host, speed, S_IRUGO,
1975 show_fc_host_speed, NULL);
1976
1977
1978fc_host_rd_attr(port_id, "0x%06x\n", 20);
1979fc_host_rd_enum_attr(port_type, FC_PORTTYPE_MAX_NAMELEN);
1980fc_host_rd_enum_attr(port_state, FC_PORTSTATE_MAX_NAMELEN);
1981fc_host_rd_attr_cast(fabric_name, "0x%llx\n", 20, unsigned long long);
1982fc_host_rd_attr(symbolic_name, "%s\n", FC_SYMBOLIC_NAME_SIZE + 1);
1983
1984fc_private_host_show_function(system_hostname, "%s\n",
1985 FC_SYMBOLIC_NAME_SIZE + 1, )
1986fc_host_store_str_function(system_hostname, FC_SYMBOLIC_NAME_SIZE)
1987static FC_DEVICE_ATTR(host, system_hostname, S_IRUGO | S_IWUSR,
1988 show_fc_host_system_hostname, store_fc_host_system_hostname);
1989
1990
1991
1992
1993static ssize_t
1994show_fc_private_host_tgtid_bind_type(struct device *dev,
1995 struct device_attribute *attr, char *buf)
1996{
1997 struct Scsi_Host *shost = transport_class_to_shost(dev);
1998 const char *name;
1999
2000 name = get_fc_tgtid_bind_type_name(fc_host_tgtid_bind_type(shost));
2001 if (!name)
2002 return -EINVAL;
2003 return snprintf(buf, FC_BINDTYPE_MAX_NAMELEN, "%s\n", name);
2004}
2005
2006#define get_list_head_entry(pos, head, member) \
2007 pos = list_entry((head)->next, typeof(*pos), member)
2008
2009static ssize_t
2010store_fc_private_host_tgtid_bind_type(struct device *dev,
2011 struct device_attribute *attr, const char *buf, size_t count)
2012{
2013 struct Scsi_Host *shost = transport_class_to_shost(dev);
2014 struct fc_rport *rport;
2015 enum fc_tgtid_binding_type val;
2016 unsigned long flags;
2017
2018 if (get_fc_tgtid_bind_type_match(buf, &val))
2019 return -EINVAL;
2020
2021
2022 if (val != fc_host_tgtid_bind_type(shost)) {
2023 spin_lock_irqsave(shost->host_lock, flags);
2024 while (!list_empty(&fc_host_rport_bindings(shost))) {
2025 get_list_head_entry(rport,
2026 &fc_host_rport_bindings(shost), peers);
2027 list_del(&rport->peers);
2028 rport->port_state = FC_PORTSTATE_DELETED;
2029 fc_queue_work(shost, &rport->rport_delete_work);
2030 }
2031 spin_unlock_irqrestore(shost->host_lock, flags);
2032 }
2033
2034 fc_host_tgtid_bind_type(shost) = val;
2035 return count;
2036}
2037
2038static FC_DEVICE_ATTR(host, tgtid_bind_type, S_IRUGO | S_IWUSR,
2039 show_fc_private_host_tgtid_bind_type,
2040 store_fc_private_host_tgtid_bind_type);
2041
2042static ssize_t
2043store_fc_private_host_issue_lip(struct device *dev,
2044 struct device_attribute *attr, const char *buf, size_t count)
2045{
2046 struct Scsi_Host *shost = transport_class_to_shost(dev);
2047 struct fc_internal *i = to_fc_internal(shost->transportt);
2048 int ret;
2049
2050
2051 if (i->f->issue_fc_host_lip) {
2052 ret = i->f->issue_fc_host_lip(shost);
2053 return ret ? ret: count;
2054 }
2055
2056 return -ENOENT;
2057}
2058
2059static FC_DEVICE_ATTR(host, issue_lip, S_IWUSR, NULL,
2060 store_fc_private_host_issue_lip);
2061
2062static ssize_t
2063store_fc_private_host_dev_loss_tmo(struct device *dev,
2064 struct device_attribute *attr,
2065 const char *buf, size_t count)
2066{
2067 struct Scsi_Host *shost = transport_class_to_shost(dev);
2068 struct fc_host_attrs *fc_host = shost_to_fc_host(shost);
2069 struct fc_rport *rport;
2070 unsigned long val, flags;
2071 int rc;
2072
2073 rc = fc_str_to_dev_loss(buf, &val);
2074 if (rc)
2075 return rc;
2076
2077 fc_host_dev_loss_tmo(shost) = val;
2078 spin_lock_irqsave(shost->host_lock, flags);
2079 list_for_each_entry(rport, &fc_host->rports, peers)
2080 fc_rport_set_dev_loss_tmo(rport, val);
2081 spin_unlock_irqrestore(shost->host_lock, flags);
2082 return count;
2083}
2084
2085fc_private_host_show_function(dev_loss_tmo, "%d\n", 20, );
2086static FC_DEVICE_ATTR(host, dev_loss_tmo, S_IRUGO | S_IWUSR,
2087 show_fc_host_dev_loss_tmo,
2088 store_fc_private_host_dev_loss_tmo);
2089
2090fc_private_host_rd_attr(npiv_vports_inuse, "%u\n", 20);
2091
2092
2093
2094
2095
2096
2097static ssize_t
2098fc_stat_show(const struct device *dev, char *buf, unsigned long offset)
2099{
2100 struct Scsi_Host *shost = transport_class_to_shost(dev);
2101 struct fc_internal *i = to_fc_internal(shost->transportt);
2102 struct fc_host_statistics *stats;
2103 ssize_t ret = -ENOENT;
2104
2105 if (offset > sizeof(struct fc_host_statistics) ||
2106 offset % sizeof(u64) != 0)
2107 WARN_ON(1);
2108
2109 if (i->f->get_fc_host_stats) {
2110 stats = (i->f->get_fc_host_stats)(shost);
2111 if (stats)
2112 ret = snprintf(buf, 20, "0x%llx\n",
2113 (unsigned long long)*(u64 *)(((u8 *) stats) + offset));
2114 }
2115 return ret;
2116}
2117
2118
2119
2120#define fc_host_statistic(name) \
2121static ssize_t show_fcstat_##name(struct device *cd, \
2122 struct device_attribute *attr, \
2123 char *buf) \
2124{ \
2125 return fc_stat_show(cd, buf, \
2126 offsetof(struct fc_host_statistics, name)); \
2127} \
2128static FC_DEVICE_ATTR(host, name, S_IRUGO, show_fcstat_##name, NULL)
2129
2130fc_host_statistic(seconds_since_last_reset);
2131fc_host_statistic(tx_frames);
2132fc_host_statistic(tx_words);
2133fc_host_statistic(rx_frames);
2134fc_host_statistic(rx_words);
2135fc_host_statistic(lip_count);
2136fc_host_statistic(nos_count);
2137fc_host_statistic(error_frames);
2138fc_host_statistic(dumped_frames);
2139fc_host_statistic(link_failure_count);
2140fc_host_statistic(loss_of_sync_count);
2141fc_host_statistic(loss_of_signal_count);
2142fc_host_statistic(prim_seq_protocol_err_count);
2143fc_host_statistic(invalid_tx_word_count);
2144fc_host_statistic(invalid_crc_count);
2145fc_host_statistic(fcp_input_requests);
2146fc_host_statistic(fcp_output_requests);
2147fc_host_statistic(fcp_control_requests);
2148fc_host_statistic(fcp_input_megabytes);
2149fc_host_statistic(fcp_output_megabytes);
2150fc_host_statistic(fcp_packet_alloc_failures);
2151fc_host_statistic(fcp_packet_aborts);
2152fc_host_statistic(fcp_frame_alloc_failures);
2153fc_host_statistic(fc_no_free_exch);
2154fc_host_statistic(fc_no_free_exch_xid);
2155fc_host_statistic(fc_xid_not_found);
2156fc_host_statistic(fc_xid_busy);
2157fc_host_statistic(fc_seq_not_found);
2158fc_host_statistic(fc_non_bls_resp);
2159fc_host_statistic(cn_sig_warn);
2160fc_host_statistic(cn_sig_alarm);
2161
2162
2163#define fc_host_fpin_statistic(name) \
2164static ssize_t fc_host_fpinstat_##name(struct device *cd, \
2165 struct device_attribute *attr, \
2166 char *buf) \
2167{ \
2168 struct Scsi_Host *shost = transport_class_to_shost(cd); \
2169 struct fc_host_attrs *fc_host = shost_to_fc_host(shost); \
2170 \
2171 return snprintf(buf, 20, "0x%llx\n", fc_host->fpin_stats.name); \
2172} \
2173static FC_DEVICE_ATTR(host, fpin_##name, 0444, fc_host_fpinstat_##name, NULL)
2174
2175fc_host_fpin_statistic(dn);
2176fc_host_fpin_statistic(dn_unknown);
2177fc_host_fpin_statistic(dn_timeout);
2178fc_host_fpin_statistic(dn_unable_to_route);
2179fc_host_fpin_statistic(dn_device_specific);
2180fc_host_fpin_statistic(cn);
2181fc_host_fpin_statistic(cn_clear);
2182fc_host_fpin_statistic(cn_lost_credit);
2183fc_host_fpin_statistic(cn_credit_stall);
2184fc_host_fpin_statistic(cn_oversubscription);
2185fc_host_fpin_statistic(cn_device_specific);
2186fc_host_fpin_statistic(li);
2187fc_host_fpin_statistic(li_failure_unknown);
2188fc_host_fpin_statistic(li_link_failure_count);
2189fc_host_fpin_statistic(li_loss_of_sync_count);
2190fc_host_fpin_statistic(li_loss_of_signals_count);
2191fc_host_fpin_statistic(li_prim_seq_err_count);
2192fc_host_fpin_statistic(li_invalid_tx_word_count);
2193fc_host_fpin_statistic(li_invalid_crc_count);
2194fc_host_fpin_statistic(li_device_specific);
2195
2196static ssize_t
2197fc_reset_statistics(struct device *dev, struct device_attribute *attr,
2198 const char *buf, size_t count)
2199{
2200 struct Scsi_Host *shost = transport_class_to_shost(dev);
2201 struct fc_internal *i = to_fc_internal(shost->transportt);
2202
2203
2204 if (i->f->reset_fc_host_stats) {
2205 i->f->reset_fc_host_stats(shost);
2206 return count;
2207 }
2208
2209 return -ENOENT;
2210}
2211static FC_DEVICE_ATTR(host, reset_statistics, S_IWUSR, NULL,
2212 fc_reset_statistics);
2213
2214static struct attribute *fc_statistics_attrs[] = {
2215 &device_attr_host_seconds_since_last_reset.attr,
2216 &device_attr_host_tx_frames.attr,
2217 &device_attr_host_tx_words.attr,
2218 &device_attr_host_rx_frames.attr,
2219 &device_attr_host_rx_words.attr,
2220 &device_attr_host_lip_count.attr,
2221 &device_attr_host_nos_count.attr,
2222 &device_attr_host_error_frames.attr,
2223 &device_attr_host_dumped_frames.attr,
2224 &device_attr_host_link_failure_count.attr,
2225 &device_attr_host_loss_of_sync_count.attr,
2226 &device_attr_host_loss_of_signal_count.attr,
2227 &device_attr_host_prim_seq_protocol_err_count.attr,
2228 &device_attr_host_invalid_tx_word_count.attr,
2229 &device_attr_host_invalid_crc_count.attr,
2230 &device_attr_host_fcp_input_requests.attr,
2231 &device_attr_host_fcp_output_requests.attr,
2232 &device_attr_host_fcp_control_requests.attr,
2233 &device_attr_host_fcp_input_megabytes.attr,
2234 &device_attr_host_fcp_output_megabytes.attr,
2235 &device_attr_host_fcp_packet_alloc_failures.attr,
2236 &device_attr_host_fcp_packet_aborts.attr,
2237 &device_attr_host_fcp_frame_alloc_failures.attr,
2238 &device_attr_host_fc_no_free_exch.attr,
2239 &device_attr_host_fc_no_free_exch_xid.attr,
2240 &device_attr_host_fc_xid_not_found.attr,
2241 &device_attr_host_fc_xid_busy.attr,
2242 &device_attr_host_fc_seq_not_found.attr,
2243 &device_attr_host_fc_non_bls_resp.attr,
2244 &device_attr_host_cn_sig_warn.attr,
2245 &device_attr_host_cn_sig_alarm.attr,
2246 &device_attr_host_reset_statistics.attr,
2247 &device_attr_host_fpin_dn.attr,
2248 &device_attr_host_fpin_dn_unknown.attr,
2249 &device_attr_host_fpin_dn_timeout.attr,
2250 &device_attr_host_fpin_dn_unable_to_route.attr,
2251 &device_attr_host_fpin_dn_device_specific.attr,
2252 &device_attr_host_fpin_li.attr,
2253 &device_attr_host_fpin_li_failure_unknown.attr,
2254 &device_attr_host_fpin_li_link_failure_count.attr,
2255 &device_attr_host_fpin_li_loss_of_sync_count.attr,
2256 &device_attr_host_fpin_li_loss_of_signals_count.attr,
2257 &device_attr_host_fpin_li_prim_seq_err_count.attr,
2258 &device_attr_host_fpin_li_invalid_tx_word_count.attr,
2259 &device_attr_host_fpin_li_invalid_crc_count.attr,
2260 &device_attr_host_fpin_li_device_specific.attr,
2261 &device_attr_host_fpin_cn.attr,
2262 &device_attr_host_fpin_cn_clear.attr,
2263 &device_attr_host_fpin_cn_lost_credit.attr,
2264 &device_attr_host_fpin_cn_credit_stall.attr,
2265 &device_attr_host_fpin_cn_oversubscription.attr,
2266 &device_attr_host_fpin_cn_device_specific.attr,
2267 NULL
2268};
2269
2270static struct attribute_group fc_statistics_group = {
2271 .name = "statistics",
2272 .attrs = fc_statistics_attrs,
2273};
2274
2275
2276
2277
2278static int
2279fc_parse_wwn(const char *ns, u64 *nm)
2280{
2281 unsigned int i, j;
2282 u8 wwn[8];
2283
2284 memset(wwn, 0, sizeof(wwn));
2285
2286
2287 for (i=0, j=0; i < 16; i++) {
2288 int value;
2289
2290 value = hex_to_bin(*ns++);
2291 if (value >= 0)
2292 j = (j << 4) | value;
2293 else
2294 return -EINVAL;
2295 if (i % 2) {
2296 wwn[i/2] = j & 0xff;
2297 j = 0;
2298 }
2299 }
2300
2301 *nm = wwn_to_u64(wwn);
2302
2303 return 0;
2304}
2305
2306
2307
2308
2309
2310
2311
2312
2313static ssize_t
2314store_fc_host_vport_create(struct device *dev, struct device_attribute *attr,
2315 const char *buf, size_t count)
2316{
2317 struct Scsi_Host *shost = transport_class_to_shost(dev);
2318 struct fc_vport_identifiers vid;
2319 struct fc_vport *vport;
2320 unsigned int cnt=count;
2321 int stat;
2322
2323 memset(&vid, 0, sizeof(vid));
2324
2325
2326 if (buf[cnt-1] == '\n')
2327 cnt--;
2328
2329
2330 if ((cnt != (16+1+16)) || (buf[16] != ':'))
2331 return -EINVAL;
2332
2333 stat = fc_parse_wwn(&buf[0], &vid.port_name);
2334 if (stat)
2335 return stat;
2336
2337 stat = fc_parse_wwn(&buf[17], &vid.node_name);
2338 if (stat)
2339 return stat;
2340
2341 vid.roles = FC_PORT_ROLE_FCP_INITIATOR;
2342 vid.vport_type = FC_PORTTYPE_NPIV;
2343
2344 vid.disable = false;
2345
2346
2347 stat = fc_vport_setup(shost, 0, &shost->shost_gendev, &vid, &vport);
2348 return stat ? stat : count;
2349}
2350static FC_DEVICE_ATTR(host, vport_create, S_IWUSR, NULL,
2351 store_fc_host_vport_create);
2352
2353
2354
2355
2356
2357
2358
2359
2360static ssize_t
2361store_fc_host_vport_delete(struct device *dev, struct device_attribute *attr,
2362 const char *buf, size_t count)
2363{
2364 struct Scsi_Host *shost = transport_class_to_shost(dev);
2365 struct fc_host_attrs *fc_host = shost_to_fc_host(shost);
2366 struct fc_vport *vport;
2367 u64 wwpn, wwnn;
2368 unsigned long flags;
2369 unsigned int cnt=count;
2370 int stat, match;
2371
2372
2373 if (buf[cnt-1] == '\n')
2374 cnt--;
2375
2376
2377 if ((cnt != (16+1+16)) || (buf[16] != ':'))
2378 return -EINVAL;
2379
2380 stat = fc_parse_wwn(&buf[0], &wwpn);
2381 if (stat)
2382 return stat;
2383
2384 stat = fc_parse_wwn(&buf[17], &wwnn);
2385 if (stat)
2386 return stat;
2387
2388 spin_lock_irqsave(shost->host_lock, flags);
2389 match = 0;
2390
2391 list_for_each_entry(vport, &fc_host->vports, peers) {
2392 if ((vport->channel == 0) &&
2393 (vport->port_name == wwpn) && (vport->node_name == wwnn)) {
2394 if (vport->flags & (FC_VPORT_DEL | FC_VPORT_CREATING))
2395 break;
2396 vport->flags |= FC_VPORT_DELETING;
2397 match = 1;
2398 break;
2399 }
2400 }
2401 spin_unlock_irqrestore(shost->host_lock, flags);
2402
2403 if (!match)
2404 return -ENODEV;
2405
2406 stat = fc_vport_terminate(vport);
2407 return stat ? stat : count;
2408}
2409static FC_DEVICE_ATTR(host, vport_delete, S_IWUSR, NULL,
2410 store_fc_host_vport_delete);
2411
2412
2413static int fc_host_match(struct attribute_container *cont,
2414 struct device *dev)
2415{
2416 struct Scsi_Host *shost;
2417 struct fc_internal *i;
2418
2419 if (!scsi_is_host_device(dev))
2420 return 0;
2421
2422 shost = dev_to_shost(dev);
2423 if (!shost->transportt || shost->transportt->host_attrs.ac.class
2424 != &fc_host_class.class)
2425 return 0;
2426
2427 i = to_fc_internal(shost->transportt);
2428
2429 return &i->t.host_attrs.ac == cont;
2430}
2431
2432static int fc_target_match(struct attribute_container *cont,
2433 struct device *dev)
2434{
2435 struct Scsi_Host *shost;
2436 struct fc_internal *i;
2437
2438 if (!scsi_is_target_device(dev))
2439 return 0;
2440
2441 shost = dev_to_shost(dev->parent);
2442 if (!shost->transportt || shost->transportt->host_attrs.ac.class
2443 != &fc_host_class.class)
2444 return 0;
2445
2446 i = to_fc_internal(shost->transportt);
2447
2448 return &i->t.target_attrs.ac == cont;
2449}
2450
2451static void fc_rport_dev_release(struct device *dev)
2452{
2453 struct fc_rport *rport = dev_to_rport(dev);
2454 put_device(dev->parent);
2455 kfree(rport);
2456}
2457
2458int scsi_is_fc_rport(const struct device *dev)
2459{
2460 return dev->release == fc_rport_dev_release;
2461}
2462EXPORT_SYMBOL(scsi_is_fc_rport);
2463
2464static int fc_rport_match(struct attribute_container *cont,
2465 struct device *dev)
2466{
2467 struct Scsi_Host *shost;
2468 struct fc_internal *i;
2469
2470 if (!scsi_is_fc_rport(dev))
2471 return 0;
2472
2473 shost = dev_to_shost(dev->parent);
2474 if (!shost->transportt || shost->transportt->host_attrs.ac.class
2475 != &fc_host_class.class)
2476 return 0;
2477
2478 i = to_fc_internal(shost->transportt);
2479
2480 return &i->rport_attr_cont.ac == cont;
2481}
2482
2483
2484static void fc_vport_dev_release(struct device *dev)
2485{
2486 struct fc_vport *vport = dev_to_vport(dev);
2487 put_device(dev->parent);
2488 kfree(vport);
2489}
2490
2491static int scsi_is_fc_vport(const struct device *dev)
2492{
2493 return dev->release == fc_vport_dev_release;
2494}
2495
2496static int fc_vport_match(struct attribute_container *cont,
2497 struct device *dev)
2498{
2499 struct fc_vport *vport;
2500 struct Scsi_Host *shost;
2501 struct fc_internal *i;
2502
2503 if (!scsi_is_fc_vport(dev))
2504 return 0;
2505 vport = dev_to_vport(dev);
2506
2507 shost = vport_to_shost(vport);
2508 if (!shost->transportt || shost->transportt->host_attrs.ac.class
2509 != &fc_host_class.class)
2510 return 0;
2511
2512 i = to_fc_internal(shost->transportt);
2513 return &i->vport_attr_cont.ac == cont;
2514}
2515
2516
2517
2518
2519
2520
2521
2522
2523
2524
2525
2526
2527
2528
2529
2530
2531
2532
2533
2534
2535
2536
2537
2538
2539enum blk_eh_timer_return
2540fc_eh_timed_out(struct scsi_cmnd *scmd)
2541{
2542 struct fc_rport *rport = starget_to_rport(scsi_target(scmd->device));
2543
2544 if (rport->port_state == FC_PORTSTATE_BLOCKED)
2545 return BLK_EH_RESET_TIMER;
2546
2547 return BLK_EH_DONE;
2548}
2549EXPORT_SYMBOL(fc_eh_timed_out);
2550
2551
2552
2553
2554
2555
2556static void
2557fc_user_scan_tgt(struct Scsi_Host *shost, uint channel, uint id, u64 lun)
2558{
2559 struct fc_rport *rport;
2560 unsigned long flags;
2561
2562 spin_lock_irqsave(shost->host_lock, flags);
2563
2564 list_for_each_entry(rport, &fc_host_rports(shost), peers) {
2565 if (rport->scsi_target_id == -1)
2566 continue;
2567
2568 if ((rport->port_state != FC_PORTSTATE_ONLINE) &&
2569 (rport->port_state != FC_PORTSTATE_MARGINAL))
2570 continue;
2571
2572 if ((channel == rport->channel) &&
2573 (id == rport->scsi_target_id)) {
2574 spin_unlock_irqrestore(shost->host_lock, flags);
2575 scsi_scan_target(&rport->dev, channel, id, lun,
2576 SCSI_SCAN_MANUAL);
2577 return;
2578 }
2579 }
2580
2581 spin_unlock_irqrestore(shost->host_lock, flags);
2582}
2583
2584
2585
2586
2587
2588
2589
2590static int
2591fc_user_scan(struct Scsi_Host *shost, uint channel, uint id, u64 lun)
2592{
2593 uint chlo, chhi;
2594 uint tgtlo, tgthi;
2595
2596 if (((channel != SCAN_WILD_CARD) && (channel > shost->max_channel)) ||
2597 ((id != SCAN_WILD_CARD) && (id >= shost->max_id)) ||
2598 ((lun != SCAN_WILD_CARD) && (lun > shost->max_lun)))
2599 return -EINVAL;
2600
2601 if (channel == SCAN_WILD_CARD) {
2602 chlo = 0;
2603 chhi = shost->max_channel + 1;
2604 } else {
2605 chlo = channel;
2606 chhi = channel + 1;
2607 }
2608
2609 if (id == SCAN_WILD_CARD) {
2610 tgtlo = 0;
2611 tgthi = shost->max_id;
2612 } else {
2613 tgtlo = id;
2614 tgthi = id + 1;
2615 }
2616
2617 for ( ; chlo < chhi; chlo++)
2618 for ( ; tgtlo < tgthi; tgtlo++)
2619 fc_user_scan_tgt(shost, chlo, tgtlo, lun);
2620
2621 return 0;
2622}
2623
2624struct scsi_transport_template *
2625fc_attach_transport(struct fc_function_template *ft)
2626{
2627 int count;
2628 struct fc_internal *i = kzalloc(sizeof(struct fc_internal),
2629 GFP_KERNEL);
2630
2631 if (unlikely(!i))
2632 return NULL;
2633
2634 i->t.target_attrs.ac.attrs = &i->starget_attrs[0];
2635 i->t.target_attrs.ac.class = &fc_transport_class.class;
2636 i->t.target_attrs.ac.match = fc_target_match;
2637 i->t.target_size = sizeof(struct fc_starget_attrs);
2638 transport_container_register(&i->t.target_attrs);
2639
2640 i->t.host_attrs.ac.attrs = &i->host_attrs[0];
2641 i->t.host_attrs.ac.class = &fc_host_class.class;
2642 i->t.host_attrs.ac.match = fc_host_match;
2643 i->t.host_size = sizeof(struct fc_host_attrs);
2644 if (ft->get_fc_host_stats)
2645 i->t.host_attrs.statistics = &fc_statistics_group;
2646 transport_container_register(&i->t.host_attrs);
2647
2648 i->rport_attr_cont.ac.attrs = &i->rport_attrs[0];
2649 i->rport_attr_cont.ac.class = &fc_rport_class.class;
2650 i->rport_attr_cont.ac.match = fc_rport_match;
2651 i->rport_attr_cont.statistics = &fc_rport_statistics_group;
2652 transport_container_register(&i->rport_attr_cont);
2653
2654 i->vport_attr_cont.ac.attrs = &i->vport_attrs[0];
2655 i->vport_attr_cont.ac.class = &fc_vport_class.class;
2656 i->vport_attr_cont.ac.match = fc_vport_match;
2657 transport_container_register(&i->vport_attr_cont);
2658
2659 i->f = ft;
2660
2661
2662 i->t.create_work_queue = 1;
2663
2664 i->t.user_scan = fc_user_scan;
2665
2666
2667
2668
2669 count = 0;
2670 SETUP_STARGET_ATTRIBUTE_RD(node_name);
2671 SETUP_STARGET_ATTRIBUTE_RD(port_name);
2672 SETUP_STARGET_ATTRIBUTE_RD(port_id);
2673
2674 BUG_ON(count > FC_STARGET_NUM_ATTRS);
2675
2676 i->starget_attrs[count] = NULL;
2677
2678
2679
2680
2681
2682 count=0;
2683 SETUP_HOST_ATTRIBUTE_RD(node_name);
2684 SETUP_HOST_ATTRIBUTE_RD(port_name);
2685 SETUP_HOST_ATTRIBUTE_RD(permanent_port_name);
2686 SETUP_HOST_ATTRIBUTE_RD(supported_classes);
2687 SETUP_HOST_ATTRIBUTE_RD(supported_fc4s);
2688 SETUP_HOST_ATTRIBUTE_RD(supported_speeds);
2689 SETUP_HOST_ATTRIBUTE_RD(maxframe_size);
2690 if (ft->vport_create) {
2691 SETUP_HOST_ATTRIBUTE_RD_NS(max_npiv_vports);
2692 SETUP_HOST_ATTRIBUTE_RD_NS(npiv_vports_inuse);
2693 }
2694 SETUP_HOST_ATTRIBUTE_RD(serial_number);
2695 SETUP_HOST_ATTRIBUTE_RD(manufacturer);
2696 SETUP_HOST_ATTRIBUTE_RD(model);
2697 SETUP_HOST_ATTRIBUTE_RD(model_description);
2698 SETUP_HOST_ATTRIBUTE_RD(hardware_version);
2699 SETUP_HOST_ATTRIBUTE_RD(driver_version);
2700 SETUP_HOST_ATTRIBUTE_RD(firmware_version);
2701 SETUP_HOST_ATTRIBUTE_RD(optionrom_version);
2702
2703 SETUP_HOST_ATTRIBUTE_RD(port_id);
2704 SETUP_HOST_ATTRIBUTE_RD(port_type);
2705 SETUP_HOST_ATTRIBUTE_RD(port_state);
2706 SETUP_HOST_ATTRIBUTE_RD(active_fc4s);
2707 SETUP_HOST_ATTRIBUTE_RD(speed);
2708 SETUP_HOST_ATTRIBUTE_RD(fabric_name);
2709 SETUP_HOST_ATTRIBUTE_RD(symbolic_name);
2710 SETUP_HOST_ATTRIBUTE_RW(system_hostname);
2711
2712
2713 SETUP_PRIVATE_HOST_ATTRIBUTE_RW(dev_loss_tmo);
2714 SETUP_PRIVATE_HOST_ATTRIBUTE_RW(tgtid_bind_type);
2715 if (ft->issue_fc_host_lip)
2716 SETUP_PRIVATE_HOST_ATTRIBUTE_RW(issue_lip);
2717 if (ft->vport_create)
2718 SETUP_PRIVATE_HOST_ATTRIBUTE_RW(vport_create);
2719 if (ft->vport_delete)
2720 SETUP_PRIVATE_HOST_ATTRIBUTE_RW(vport_delete);
2721
2722 BUG_ON(count > FC_HOST_NUM_ATTRS);
2723
2724 i->host_attrs[count] = NULL;
2725
2726
2727
2728
2729 count=0;
2730 SETUP_RPORT_ATTRIBUTE_RD(maxframe_size);
2731 SETUP_RPORT_ATTRIBUTE_RD(supported_classes);
2732 SETUP_RPORT_ATTRIBUTE_RW(dev_loss_tmo);
2733 SETUP_PRIVATE_RPORT_ATTRIBUTE_RD(node_name);
2734 SETUP_PRIVATE_RPORT_ATTRIBUTE_RD(port_name);
2735 SETUP_PRIVATE_RPORT_ATTRIBUTE_RD(port_id);
2736 SETUP_PRIVATE_RPORT_ATTRIBUTE_RD(roles);
2737 SETUP_PRIVATE_RPORT_ATTRIBUTE_RW(port_state);
2738 SETUP_PRIVATE_RPORT_ATTRIBUTE_RD(scsi_target_id);
2739 SETUP_PRIVATE_RPORT_ATTRIBUTE_RW(fast_io_fail_tmo);
2740
2741 BUG_ON(count > FC_RPORT_NUM_ATTRS);
2742
2743 i->rport_attrs[count] = NULL;
2744
2745
2746
2747
2748 count=0;
2749 SETUP_PRIVATE_VPORT_ATTRIBUTE_RD(vport_state);
2750 SETUP_PRIVATE_VPORT_ATTRIBUTE_RD(vport_last_state);
2751 SETUP_PRIVATE_VPORT_ATTRIBUTE_RD(node_name);
2752 SETUP_PRIVATE_VPORT_ATTRIBUTE_RD(port_name);
2753 SETUP_PRIVATE_VPORT_ATTRIBUTE_RD(roles);
2754 SETUP_PRIVATE_VPORT_ATTRIBUTE_RD(vport_type);
2755 SETUP_VPORT_ATTRIBUTE_RW(symbolic_name);
2756 SETUP_VPORT_ATTRIBUTE_WR(vport_delete);
2757 SETUP_VPORT_ATTRIBUTE_WR(vport_disable);
2758
2759 BUG_ON(count > FC_VPORT_NUM_ATTRS);
2760
2761 i->vport_attrs[count] = NULL;
2762
2763 return &i->t;
2764}
2765EXPORT_SYMBOL(fc_attach_transport);
2766
2767void fc_release_transport(struct scsi_transport_template *t)
2768{
2769 struct fc_internal *i = to_fc_internal(t);
2770
2771 transport_container_unregister(&i->t.target_attrs);
2772 transport_container_unregister(&i->t.host_attrs);
2773 transport_container_unregister(&i->rport_attr_cont);
2774 transport_container_unregister(&i->vport_attr_cont);
2775
2776 kfree(i);
2777}
2778EXPORT_SYMBOL(fc_release_transport);
2779
2780
2781
2782
2783
2784
2785
2786
2787
2788
2789
2790static int
2791fc_queue_work(struct Scsi_Host *shost, struct work_struct *work)
2792{
2793 if (unlikely(!fc_host_work_q(shost))) {
2794 printk(KERN_ERR
2795 "ERROR: FC host '%s' attempted to queue work, "
2796 "when no workqueue created.\n", shost->hostt->name);
2797 dump_stack();
2798
2799 return -EINVAL;
2800 }
2801
2802 return queue_work(fc_host_work_q(shost), work);
2803}
2804
2805
2806
2807
2808
2809static void
2810fc_flush_work(struct Scsi_Host *shost)
2811{
2812 if (!fc_host_work_q(shost)) {
2813 printk(KERN_ERR
2814 "ERROR: FC host '%s' attempted to flush work, "
2815 "when no workqueue created.\n", shost->hostt->name);
2816 dump_stack();
2817 return;
2818 }
2819
2820 flush_workqueue(fc_host_work_q(shost));
2821}
2822
2823
2824
2825
2826
2827
2828
2829
2830
2831
2832static int
2833fc_queue_devloss_work(struct Scsi_Host *shost, struct delayed_work *work,
2834 unsigned long delay)
2835{
2836 if (unlikely(!fc_host_devloss_work_q(shost))) {
2837 printk(KERN_ERR
2838 "ERROR: FC host '%s' attempted to queue work, "
2839 "when no workqueue created.\n", shost->hostt->name);
2840 dump_stack();
2841
2842 return -EINVAL;
2843 }
2844
2845 return queue_delayed_work(fc_host_devloss_work_q(shost), work, delay);
2846}
2847
2848
2849
2850
2851
2852static void
2853fc_flush_devloss(struct Scsi_Host *shost)
2854{
2855 if (!fc_host_devloss_work_q(shost)) {
2856 printk(KERN_ERR
2857 "ERROR: FC host '%s' attempted to flush work, "
2858 "when no workqueue created.\n", shost->hostt->name);
2859 dump_stack();
2860 return;
2861 }
2862
2863 flush_workqueue(fc_host_devloss_work_q(shost));
2864}
2865
2866
2867
2868
2869
2870
2871
2872
2873
2874
2875
2876
2877
2878
2879
2880
2881
2882void
2883fc_remove_host(struct Scsi_Host *shost)
2884{
2885 struct fc_vport *vport = NULL, *next_vport = NULL;
2886 struct fc_rport *rport = NULL, *next_rport = NULL;
2887 struct workqueue_struct *work_q;
2888 struct fc_host_attrs *fc_host = shost_to_fc_host(shost);
2889 unsigned long flags;
2890
2891 spin_lock_irqsave(shost->host_lock, flags);
2892
2893
2894 list_for_each_entry_safe(vport, next_vport, &fc_host->vports, peers) {
2895 vport->flags |= FC_VPORT_DELETING;
2896 fc_queue_work(shost, &vport->vport_delete_work);
2897 }
2898
2899
2900 list_for_each_entry_safe(rport, next_rport,
2901 &fc_host->rports, peers) {
2902 list_del(&rport->peers);
2903 rport->port_state = FC_PORTSTATE_DELETED;
2904 fc_queue_work(shost, &rport->rport_delete_work);
2905 }
2906
2907 list_for_each_entry_safe(rport, next_rport,
2908 &fc_host->rport_bindings, peers) {
2909 list_del(&rport->peers);
2910 rport->port_state = FC_PORTSTATE_DELETED;
2911 fc_queue_work(shost, &rport->rport_delete_work);
2912 }
2913
2914 spin_unlock_irqrestore(shost->host_lock, flags);
2915
2916
2917 scsi_flush_work(shost);
2918
2919
2920 if (fc_host->work_q) {
2921 work_q = fc_host->work_q;
2922 fc_host->work_q = NULL;
2923 destroy_workqueue(work_q);
2924 }
2925
2926
2927 if (fc_host->devloss_work_q) {
2928 work_q = fc_host->devloss_work_q;
2929 fc_host->devloss_work_q = NULL;
2930 destroy_workqueue(work_q);
2931 }
2932}
2933EXPORT_SYMBOL(fc_remove_host);
2934
2935static void fc_terminate_rport_io(struct fc_rport *rport)
2936{
2937 struct Scsi_Host *shost = rport_to_shost(rport);
2938 struct fc_internal *i = to_fc_internal(shost->transportt);
2939
2940
2941 if (i->f->terminate_rport_io)
2942 i->f->terminate_rport_io(rport);
2943
2944
2945
2946
2947 scsi_target_unblock(&rport->dev, SDEV_TRANSPORT_OFFLINE);
2948}
2949
2950
2951
2952
2953
2954
2955
2956static void
2957fc_starget_delete(struct work_struct *work)
2958{
2959 struct fc_rport *rport =
2960 container_of(work, struct fc_rport, stgt_delete_work);
2961
2962 fc_terminate_rport_io(rport);
2963 scsi_remove_target(&rport->dev);
2964}
2965
2966
2967
2968
2969
2970
2971static void
2972fc_rport_final_delete(struct work_struct *work)
2973{
2974 struct fc_rport *rport =
2975 container_of(work, struct fc_rport, rport_delete_work);
2976 struct device *dev = &rport->dev;
2977 struct Scsi_Host *shost = rport_to_shost(rport);
2978 struct fc_internal *i = to_fc_internal(shost->transportt);
2979 unsigned long flags;
2980 int do_callback = 0;
2981
2982 fc_terminate_rport_io(rport);
2983
2984
2985
2986
2987
2988 if (rport->flags & FC_RPORT_SCAN_PENDING)
2989 scsi_flush_work(shost);
2990
2991
2992
2993
2994
2995
2996 spin_lock_irqsave(shost->host_lock, flags);
2997 if (rport->flags & FC_RPORT_DEVLOSS_PENDING) {
2998 spin_unlock_irqrestore(shost->host_lock, flags);
2999 if (!cancel_delayed_work(&rport->fail_io_work))
3000 fc_flush_devloss(shost);
3001 if (!cancel_delayed_work(&rport->dev_loss_work))
3002 fc_flush_devloss(shost);
3003 cancel_work_sync(&rport->scan_work);
3004 spin_lock_irqsave(shost->host_lock, flags);
3005 rport->flags &= ~FC_RPORT_DEVLOSS_PENDING;
3006 }
3007 spin_unlock_irqrestore(shost->host_lock, flags);
3008
3009
3010 if (rport->scsi_target_id != -1)
3011 fc_starget_delete(&rport->stgt_delete_work);
3012
3013
3014
3015
3016
3017
3018
3019
3020 spin_lock_irqsave(shost->host_lock, flags);
3021 if (!(rport->flags & FC_RPORT_DEVLOSS_CALLBK_DONE) &&
3022 (i->f->dev_loss_tmo_callbk)) {
3023 rport->flags |= FC_RPORT_DEVLOSS_CALLBK_DONE;
3024 do_callback = 1;
3025 }
3026 spin_unlock_irqrestore(shost->host_lock, flags);
3027
3028 if (do_callback)
3029 i->f->dev_loss_tmo_callbk(rport);
3030
3031 fc_bsg_remove(rport->rqst_q);
3032
3033 transport_remove_device(dev);
3034 device_del(dev);
3035 transport_destroy_device(dev);
3036 scsi_host_put(shost);
3037 put_device(dev);
3038}
3039
3040
3041
3042
3043
3044
3045
3046
3047
3048
3049
3050
3051
3052
3053
3054static struct fc_rport *
3055fc_remote_port_create(struct Scsi_Host *shost, int channel,
3056 struct fc_rport_identifiers *ids)
3057{
3058 struct fc_host_attrs *fc_host = shost_to_fc_host(shost);
3059 struct fc_internal *fci = to_fc_internal(shost->transportt);
3060 struct fc_rport *rport;
3061 struct device *dev;
3062 unsigned long flags;
3063 int error;
3064 size_t size;
3065
3066 size = (sizeof(struct fc_rport) + fci->f->dd_fcrport_size);
3067 rport = kzalloc(size, GFP_KERNEL);
3068 if (unlikely(!rport)) {
3069 printk(KERN_ERR "%s: allocation failure\n", __func__);
3070 return NULL;
3071 }
3072
3073 rport->maxframe_size = -1;
3074 rport->supported_classes = FC_COS_UNSPECIFIED;
3075 rport->dev_loss_tmo = fc_host->dev_loss_tmo;
3076 memcpy(&rport->node_name, &ids->node_name, sizeof(rport->node_name));
3077 memcpy(&rport->port_name, &ids->port_name, sizeof(rport->port_name));
3078 rport->port_id = ids->port_id;
3079 rport->roles = ids->roles;
3080 rport->port_state = FC_PORTSTATE_ONLINE;
3081 if (fci->f->dd_fcrport_size)
3082 rport->dd_data = &rport[1];
3083 rport->channel = channel;
3084 rport->fast_io_fail_tmo = -1;
3085
3086 INIT_DELAYED_WORK(&rport->dev_loss_work, fc_timeout_deleted_rport);
3087 INIT_DELAYED_WORK(&rport->fail_io_work, fc_timeout_fail_rport_io);
3088 INIT_WORK(&rport->scan_work, fc_scsi_scan_rport);
3089 INIT_WORK(&rport->stgt_delete_work, fc_starget_delete);
3090 INIT_WORK(&rport->rport_delete_work, fc_rport_final_delete);
3091
3092 spin_lock_irqsave(shost->host_lock, flags);
3093
3094 rport->number = fc_host->next_rport_number++;
3095 if ((rport->roles & FC_PORT_ROLE_FCP_TARGET) ||
3096 (rport->roles & FC_PORT_ROLE_FCP_DUMMY_INITIATOR))
3097 rport->scsi_target_id = fc_host->next_target_id++;
3098 else
3099 rport->scsi_target_id = -1;
3100 list_add_tail(&rport->peers, &fc_host->rports);
3101 scsi_host_get(shost);
3102
3103 spin_unlock_irqrestore(shost->host_lock, flags);
3104
3105 dev = &rport->dev;
3106 device_initialize(dev);
3107 dev->parent = get_device(&shost->shost_gendev);
3108 dev->release = fc_rport_dev_release;
3109 dev_set_name(dev, "rport-%d:%d-%d",
3110 shost->host_no, channel, rport->number);
3111 transport_setup_device(dev);
3112
3113 error = device_add(dev);
3114 if (error) {
3115 printk(KERN_ERR "FC Remote Port device_add failed\n");
3116 goto delete_rport;
3117 }
3118 transport_add_device(dev);
3119 transport_configure_device(dev);
3120
3121 fc_bsg_rportadd(shost, rport);
3122
3123
3124 if (rport->roles & FC_PORT_ROLE_FCP_TARGET) {
3125
3126 rport->flags |= FC_RPORT_SCAN_PENDING;
3127 scsi_queue_work(shost, &rport->scan_work);
3128 }
3129
3130 return rport;
3131
3132delete_rport:
3133 transport_destroy_device(dev);
3134 spin_lock_irqsave(shost->host_lock, flags);
3135 list_del(&rport->peers);
3136 scsi_host_put(shost);
3137 spin_unlock_irqrestore(shost->host_lock, flags);
3138 put_device(dev->parent);
3139 kfree(rport);
3140 return NULL;
3141}
3142
3143
3144
3145
3146
3147
3148
3149
3150
3151
3152
3153
3154
3155
3156
3157
3158
3159
3160
3161
3162
3163
3164
3165
3166
3167
3168
3169
3170
3171
3172
3173
3174
3175
3176
3177
3178
3179
3180
3181struct fc_rport *
3182fc_remote_port_add(struct Scsi_Host *shost, int channel,
3183 struct fc_rport_identifiers *ids)
3184{
3185 struct fc_internal *fci = to_fc_internal(shost->transportt);
3186 struct fc_host_attrs *fc_host = shost_to_fc_host(shost);
3187 struct fc_rport *rport;
3188 unsigned long flags;
3189 int match = 0;
3190
3191
3192 fc_flush_work(shost);
3193
3194
3195
3196
3197
3198
3199 spin_lock_irqsave(shost->host_lock, flags);
3200
3201 list_for_each_entry(rport, &fc_host->rports, peers) {
3202
3203 if ((rport->port_state == FC_PORTSTATE_BLOCKED ||
3204 rport->port_state == FC_PORTSTATE_NOTPRESENT) &&
3205 (rport->channel == channel)) {
3206
3207 switch (fc_host->tgtid_bind_type) {
3208 case FC_TGTID_BIND_BY_WWPN:
3209 case FC_TGTID_BIND_NONE:
3210 if (rport->port_name == ids->port_name)
3211 match = 1;
3212 break;
3213 case FC_TGTID_BIND_BY_WWNN:
3214 if (rport->node_name == ids->node_name)
3215 match = 1;
3216 break;
3217 case FC_TGTID_BIND_BY_ID:
3218 if (rport->port_id == ids->port_id)
3219 match = 1;
3220 break;
3221 }
3222
3223 if (match) {
3224
3225 memcpy(&rport->node_name, &ids->node_name,
3226 sizeof(rport->node_name));
3227 memcpy(&rport->port_name, &ids->port_name,
3228 sizeof(rport->port_name));
3229 rport->port_id = ids->port_id;
3230
3231 rport->port_state = FC_PORTSTATE_ONLINE;
3232 rport->roles = ids->roles;
3233
3234 spin_unlock_irqrestore(shost->host_lock, flags);
3235
3236 if (fci->f->dd_fcrport_size)
3237 memset(rport->dd_data, 0,
3238 fci->f->dd_fcrport_size);
3239
3240
3241
3242
3243
3244
3245
3246
3247
3248
3249
3250
3251
3252
3253
3254
3255
3256
3257 if ((rport->scsi_target_id != -1) &&
3258 (!(ids->roles & FC_PORT_ROLE_FCP_TARGET)))
3259 return rport;
3260
3261
3262
3263
3264
3265
3266 if (!cancel_delayed_work(&rport->fail_io_work))
3267 fc_flush_devloss(shost);
3268 if (!cancel_delayed_work(&rport->dev_loss_work))
3269 fc_flush_devloss(shost);
3270
3271 spin_lock_irqsave(shost->host_lock, flags);
3272
3273 rport->flags &= ~(FC_RPORT_FAST_FAIL_TIMEDOUT |
3274 FC_RPORT_DEVLOSS_PENDING |
3275 FC_RPORT_DEVLOSS_CALLBK_DONE);
3276
3277 spin_unlock_irqrestore(shost->host_lock, flags);
3278
3279
3280 if (rport->scsi_target_id != -1) {
3281 scsi_target_unblock(&rport->dev,
3282 SDEV_RUNNING);
3283 spin_lock_irqsave(shost->host_lock,
3284 flags);
3285 rport->flags |= FC_RPORT_SCAN_PENDING;
3286 scsi_queue_work(shost,
3287 &rport->scan_work);
3288 spin_unlock_irqrestore(shost->host_lock,
3289 flags);
3290 }
3291
3292 fc_bsg_goose_queue(rport);
3293
3294 return rport;
3295 }
3296 }
3297 }
3298
3299
3300
3301
3302
3303 if (fc_host->tgtid_bind_type != FC_TGTID_BIND_NONE) {
3304
3305
3306
3307 list_for_each_entry(rport, &fc_host->rport_bindings,
3308 peers) {
3309 if (rport->channel != channel)
3310 continue;
3311
3312 switch (fc_host->tgtid_bind_type) {
3313 case FC_TGTID_BIND_BY_WWPN:
3314 if (rport->port_name == ids->port_name)
3315 match = 1;
3316 break;
3317 case FC_TGTID_BIND_BY_WWNN:
3318 if (rport->node_name == ids->node_name)
3319 match = 1;
3320 break;
3321 case FC_TGTID_BIND_BY_ID:
3322 if (rport->port_id == ids->port_id)
3323 match = 1;
3324 break;
3325 case FC_TGTID_BIND_NONE:
3326 break;
3327 }
3328
3329 if (match) {
3330 list_move_tail(&rport->peers, &fc_host->rports);
3331 break;
3332 }
3333 }
3334
3335 if (match) {
3336 memcpy(&rport->node_name, &ids->node_name,
3337 sizeof(rport->node_name));
3338 memcpy(&rport->port_name, &ids->port_name,
3339 sizeof(rport->port_name));
3340 rport->port_id = ids->port_id;
3341 rport->port_state = FC_PORTSTATE_ONLINE;
3342 rport->flags &= ~FC_RPORT_FAST_FAIL_TIMEDOUT;
3343
3344 if (fci->f->dd_fcrport_size)
3345 memset(rport->dd_data, 0,
3346 fci->f->dd_fcrport_size);
3347 spin_unlock_irqrestore(shost->host_lock, flags);
3348
3349 fc_remote_port_rolechg(rport, ids->roles);
3350 return rport;
3351 }
3352 }
3353
3354 spin_unlock_irqrestore(shost->host_lock, flags);
3355
3356
3357 rport = fc_remote_port_create(shost, channel, ids);
3358
3359 return rport;
3360}
3361EXPORT_SYMBOL(fc_remote_port_add);
3362
3363
3364
3365
3366
3367
3368
3369
3370
3371
3372
3373
3374
3375
3376
3377
3378
3379
3380
3381
3382
3383
3384
3385
3386
3387
3388
3389
3390
3391
3392
3393
3394
3395
3396
3397
3398
3399
3400
3401
3402
3403
3404
3405
3406
3407
3408
3409
3410
3411
3412
3413
3414
3415
3416void
3417fc_remote_port_delete(struct fc_rport *rport)
3418{
3419 struct Scsi_Host *shost = rport_to_shost(rport);
3420 unsigned long timeout = rport->dev_loss_tmo;
3421 unsigned long flags;
3422
3423
3424
3425
3426
3427
3428
3429
3430
3431 spin_lock_irqsave(shost->host_lock, flags);
3432
3433 if ((rport->port_state != FC_PORTSTATE_ONLINE) &&
3434 (rport->port_state != FC_PORTSTATE_MARGINAL)) {
3435 spin_unlock_irqrestore(shost->host_lock, flags);
3436 return;
3437 }
3438
3439
3440
3441
3442
3443
3444
3445
3446
3447
3448
3449
3450
3451
3452 rport->port_state = FC_PORTSTATE_BLOCKED;
3453
3454 rport->flags |= FC_RPORT_DEVLOSS_PENDING;
3455
3456 spin_unlock_irqrestore(shost->host_lock, flags);
3457
3458 scsi_target_block(&rport->dev);
3459
3460
3461 if ((rport->fast_io_fail_tmo != -1) &&
3462 (rport->fast_io_fail_tmo < timeout))
3463 fc_queue_devloss_work(shost, &rport->fail_io_work,
3464 rport->fast_io_fail_tmo * HZ);
3465
3466
3467 fc_queue_devloss_work(shost, &rport->dev_loss_work, timeout * HZ);
3468}
3469EXPORT_SYMBOL(fc_remote_port_delete);
3470
3471
3472
3473
3474
3475
3476
3477
3478
3479
3480
3481
3482
3483
3484
3485
3486
3487
3488
3489
3490
3491void
3492fc_remote_port_rolechg(struct fc_rport *rport, u32 roles)
3493{
3494 struct Scsi_Host *shost = rport_to_shost(rport);
3495 struct fc_host_attrs *fc_host = shost_to_fc_host(shost);
3496 unsigned long flags;
3497 int create = 0;
3498
3499 spin_lock_irqsave(shost->host_lock, flags);
3500 if (roles & FC_PORT_ROLE_FCP_TARGET) {
3501 if (rport->scsi_target_id == -1) {
3502 rport->scsi_target_id = fc_host->next_target_id++;
3503 create = 1;
3504 } else if (!(rport->roles & FC_PORT_ROLE_FCP_TARGET))
3505 create = 1;
3506 }
3507
3508 rport->roles = roles;
3509
3510 spin_unlock_irqrestore(shost->host_lock, flags);
3511
3512 if (create) {
3513
3514
3515
3516
3517
3518
3519
3520
3521
3522
3523
3524
3525 if (!cancel_delayed_work(&rport->fail_io_work))
3526 fc_flush_devloss(shost);
3527 if (!cancel_delayed_work(&rport->dev_loss_work))
3528 fc_flush_devloss(shost);
3529
3530 spin_lock_irqsave(shost->host_lock, flags);
3531 rport->flags &= ~(FC_RPORT_FAST_FAIL_TIMEDOUT |
3532 FC_RPORT_DEVLOSS_PENDING |
3533 FC_RPORT_DEVLOSS_CALLBK_DONE);
3534 spin_unlock_irqrestore(shost->host_lock, flags);
3535
3536
3537 fc_flush_work(shost);
3538
3539 scsi_target_unblock(&rport->dev, SDEV_RUNNING);
3540
3541 spin_lock_irqsave(shost->host_lock, flags);
3542 rport->flags |= FC_RPORT_SCAN_PENDING;
3543 scsi_queue_work(shost, &rport->scan_work);
3544 spin_unlock_irqrestore(shost->host_lock, flags);
3545 }
3546}
3547EXPORT_SYMBOL(fc_remote_port_rolechg);
3548
3549
3550
3551
3552
3553
3554
3555
3556static void
3557fc_timeout_deleted_rport(struct work_struct *work)
3558{
3559 struct fc_rport *rport =
3560 container_of(work, struct fc_rport, dev_loss_work.work);
3561 struct Scsi_Host *shost = rport_to_shost(rport);
3562 struct fc_internal *i = to_fc_internal(shost->transportt);
3563 struct fc_host_attrs *fc_host = shost_to_fc_host(shost);
3564 unsigned long flags;
3565 int do_callback = 0;
3566
3567 spin_lock_irqsave(shost->host_lock, flags);
3568
3569 rport->flags &= ~FC_RPORT_DEVLOSS_PENDING;
3570
3571
3572
3573
3574
3575
3576 if (((rport->port_state == FC_PORTSTATE_ONLINE) ||
3577 (rport->port_state == FC_PORTSTATE_MARGINAL)) &&
3578 (rport->scsi_target_id != -1) &&
3579 !(rport->roles & FC_PORT_ROLE_FCP_TARGET)) {
3580 dev_printk(KERN_ERR, &rport->dev,
3581 "blocked FC remote port time out: no longer"
3582 " a FCP target, removing starget\n");
3583 spin_unlock_irqrestore(shost->host_lock, flags);
3584 scsi_target_unblock(&rport->dev, SDEV_TRANSPORT_OFFLINE);
3585 fc_queue_work(shost, &rport->stgt_delete_work);
3586 return;
3587 }
3588
3589
3590 if (rport->port_state != FC_PORTSTATE_BLOCKED) {
3591 spin_unlock_irqrestore(shost->host_lock, flags);
3592 dev_printk(KERN_ERR, &rport->dev,
3593 "blocked FC remote port time out: leaving"
3594 " rport%s alone\n",
3595 (rport->scsi_target_id != -1) ? " and starget" : "");
3596 return;
3597 }
3598
3599 if ((fc_host->tgtid_bind_type == FC_TGTID_BIND_NONE) ||
3600 (rport->scsi_target_id == -1)) {
3601 list_del(&rport->peers);
3602 rport->port_state = FC_PORTSTATE_DELETED;
3603 dev_printk(KERN_ERR, &rport->dev,
3604 "blocked FC remote port time out: removing"
3605 " rport%s\n",
3606 (rport->scsi_target_id != -1) ? " and starget" : "");
3607 fc_queue_work(shost, &rport->rport_delete_work);
3608 spin_unlock_irqrestore(shost->host_lock, flags);
3609 return;
3610 }
3611
3612 dev_printk(KERN_ERR, &rport->dev,
3613 "blocked FC remote port time out: removing target and "
3614 "saving binding\n");
3615
3616 list_move_tail(&rport->peers, &fc_host->rport_bindings);
3617
3618
3619
3620
3621
3622
3623
3624
3625
3626
3627 rport->maxframe_size = -1;
3628 rport->supported_classes = FC_COS_UNSPECIFIED;
3629 rport->roles = FC_PORT_ROLE_UNKNOWN;
3630 rport->port_state = FC_PORTSTATE_NOTPRESENT;
3631 rport->flags &= ~FC_RPORT_FAST_FAIL_TIMEDOUT;
3632
3633
3634
3635
3636
3637
3638 spin_unlock_irqrestore(shost->host_lock, flags);
3639 fc_terminate_rport_io(rport);
3640
3641 spin_lock_irqsave(shost->host_lock, flags);
3642
3643 if (rport->port_state == FC_PORTSTATE_NOTPRESENT) {
3644
3645
3646 switch (fc_host->tgtid_bind_type) {
3647 case FC_TGTID_BIND_BY_WWPN:
3648 rport->node_name = -1;
3649 rport->port_id = -1;
3650 break;
3651 case FC_TGTID_BIND_BY_WWNN:
3652 rport->port_name = -1;
3653 rport->port_id = -1;
3654 break;
3655 case FC_TGTID_BIND_BY_ID:
3656 rport->node_name = -1;
3657 rport->port_name = -1;
3658 break;
3659 case FC_TGTID_BIND_NONE:
3660 break;
3661 }
3662
3663
3664
3665
3666
3667
3668 rport->flags |= FC_RPORT_DEVLOSS_CALLBK_DONE;
3669 fc_queue_work(shost, &rport->stgt_delete_work);
3670
3671 do_callback = 1;
3672 }
3673
3674 spin_unlock_irqrestore(shost->host_lock, flags);
3675
3676
3677
3678
3679
3680
3681
3682 if (do_callback && i->f->dev_loss_tmo_callbk)
3683 i->f->dev_loss_tmo_callbk(rport);
3684}
3685
3686
3687
3688
3689
3690
3691
3692
3693
3694static void
3695fc_timeout_fail_rport_io(struct work_struct *work)
3696{
3697 struct fc_rport *rport =
3698 container_of(work, struct fc_rport, fail_io_work.work);
3699
3700 if (rport->port_state != FC_PORTSTATE_BLOCKED)
3701 return;
3702
3703 rport->flags |= FC_RPORT_FAST_FAIL_TIMEDOUT;
3704 fc_terminate_rport_io(rport);
3705}
3706
3707
3708
3709
3710
3711static void
3712fc_scsi_scan_rport(struct work_struct *work)
3713{
3714 struct fc_rport *rport =
3715 container_of(work, struct fc_rport, scan_work);
3716 struct Scsi_Host *shost = rport_to_shost(rport);
3717 struct fc_internal *i = to_fc_internal(shost->transportt);
3718 unsigned long flags;
3719
3720 if (((rport->port_state == FC_PORTSTATE_ONLINE) ||
3721 (rport->port_state == FC_PORTSTATE_MARGINAL)) &&
3722 (rport->roles & FC_PORT_ROLE_FCP_TARGET) &&
3723 !(i->f->disable_target_scan)) {
3724 scsi_scan_target(&rport->dev, rport->channel,
3725 rport->scsi_target_id, SCAN_WILD_CARD,
3726 SCSI_SCAN_RESCAN);
3727 }
3728
3729 spin_lock_irqsave(shost->host_lock, flags);
3730 rport->flags &= ~FC_RPORT_SCAN_PENDING;
3731 spin_unlock_irqrestore(shost->host_lock, flags);
3732}
3733
3734
3735
3736
3737
3738
3739
3740
3741
3742
3743
3744
3745
3746
3747
3748int fc_block_rport(struct fc_rport *rport)
3749{
3750 struct Scsi_Host *shost = rport_to_shost(rport);
3751 unsigned long flags;
3752
3753 spin_lock_irqsave(shost->host_lock, flags);
3754 while (rport->port_state == FC_PORTSTATE_BLOCKED &&
3755 !(rport->flags & FC_RPORT_FAST_FAIL_TIMEDOUT)) {
3756 spin_unlock_irqrestore(shost->host_lock, flags);
3757 msleep(1000);
3758 spin_lock_irqsave(shost->host_lock, flags);
3759 }
3760 spin_unlock_irqrestore(shost->host_lock, flags);
3761
3762 if (rport->flags & FC_RPORT_FAST_FAIL_TIMEDOUT)
3763 return FAST_IO_FAIL;
3764
3765 return 0;
3766}
3767EXPORT_SYMBOL(fc_block_rport);
3768
3769
3770
3771
3772
3773
3774
3775
3776
3777
3778
3779
3780
3781
3782
3783int fc_block_scsi_eh(struct scsi_cmnd *cmnd)
3784{
3785 struct fc_rport *rport = starget_to_rport(scsi_target(cmnd->device));
3786
3787 if (WARN_ON_ONCE(!rport))
3788 return FAST_IO_FAIL;
3789
3790 return fc_block_rport(rport);
3791}
3792EXPORT_SYMBOL(fc_block_scsi_eh);
3793
3794
3795
3796
3797
3798
3799
3800
3801
3802
3803bool fc_eh_should_retry_cmd(struct scsi_cmnd *scmd)
3804{
3805 struct fc_rport *rport = starget_to_rport(scsi_target(scmd->device));
3806
3807 if ((rport->port_state != FC_PORTSTATE_ONLINE) &&
3808 (scmd->request->cmd_flags & REQ_FAILFAST_TRANSPORT)) {
3809 set_host_byte(scmd, DID_TRANSPORT_MARGINAL);
3810 return false;
3811 }
3812 return true;
3813}
3814EXPORT_SYMBOL_GPL(fc_eh_should_retry_cmd);
3815
3816
3817
3818
3819
3820
3821
3822
3823
3824
3825
3826
3827
3828
3829
3830
3831static int
3832fc_vport_setup(struct Scsi_Host *shost, int channel, struct device *pdev,
3833 struct fc_vport_identifiers *ids, struct fc_vport **ret_vport)
3834{
3835 struct fc_host_attrs *fc_host = shost_to_fc_host(shost);
3836 struct fc_internal *fci = to_fc_internal(shost->transportt);
3837 struct fc_vport *vport;
3838 struct device *dev;
3839 unsigned long flags;
3840 size_t size;
3841 int error;
3842
3843 *ret_vport = NULL;
3844
3845 if ( ! fci->f->vport_create)
3846 return -ENOENT;
3847
3848 size = (sizeof(struct fc_vport) + fci->f->dd_fcvport_size);
3849 vport = kzalloc(size, GFP_KERNEL);
3850 if (unlikely(!vport)) {
3851 printk(KERN_ERR "%s: allocation failure\n", __func__);
3852 return -ENOMEM;
3853 }
3854
3855 vport->vport_state = FC_VPORT_UNKNOWN;
3856 vport->vport_last_state = FC_VPORT_UNKNOWN;
3857 vport->node_name = ids->node_name;
3858 vport->port_name = ids->port_name;
3859 vport->roles = ids->roles;
3860 vport->vport_type = ids->vport_type;
3861 if (fci->f->dd_fcvport_size)
3862 vport->dd_data = &vport[1];
3863 vport->shost = shost;
3864 vport->channel = channel;
3865 vport->flags = FC_VPORT_CREATING;
3866 INIT_WORK(&vport->vport_delete_work, fc_vport_sched_delete);
3867
3868 spin_lock_irqsave(shost->host_lock, flags);
3869
3870 if (fc_host->npiv_vports_inuse >= fc_host->max_npiv_vports) {
3871 spin_unlock_irqrestore(shost->host_lock, flags);
3872 kfree(vport);
3873 return -ENOSPC;
3874 }
3875 fc_host->npiv_vports_inuse++;
3876 vport->number = fc_host->next_vport_number++;
3877 list_add_tail(&vport->peers, &fc_host->vports);
3878 scsi_host_get(shost);
3879
3880 spin_unlock_irqrestore(shost->host_lock, flags);
3881
3882 dev = &vport->dev;
3883 device_initialize(dev);
3884 dev->parent = get_device(pdev);
3885 dev->release = fc_vport_dev_release;
3886 dev_set_name(dev, "vport-%d:%d-%d",
3887 shost->host_no, channel, vport->number);
3888 transport_setup_device(dev);
3889
3890 error = device_add(dev);
3891 if (error) {
3892 printk(KERN_ERR "FC Virtual Port device_add failed\n");
3893 goto delete_vport;
3894 }
3895 transport_add_device(dev);
3896 transport_configure_device(dev);
3897
3898 error = fci->f->vport_create(vport, ids->disable);
3899 if (error) {
3900 printk(KERN_ERR "FC Virtual Port LLDD Create failed\n");
3901 goto delete_vport_all;
3902 }
3903
3904
3905
3906
3907
3908 if (pdev != &shost->shost_gendev) {
3909 error = sysfs_create_link(&shost->shost_gendev.kobj,
3910 &dev->kobj, dev_name(dev));
3911 if (error)
3912 printk(KERN_ERR
3913 "%s: Cannot create vport symlinks for "
3914 "%s, err=%d\n",
3915 __func__, dev_name(dev), error);
3916 }
3917 spin_lock_irqsave(shost->host_lock, flags);
3918 vport->flags &= ~FC_VPORT_CREATING;
3919 spin_unlock_irqrestore(shost->host_lock, flags);
3920
3921 dev_printk(KERN_NOTICE, pdev,
3922 "%s created via shost%d channel %d\n", dev_name(dev),
3923 shost->host_no, channel);
3924
3925 *ret_vport = vport;
3926
3927 return 0;
3928
3929delete_vport_all:
3930 transport_remove_device(dev);
3931 device_del(dev);
3932delete_vport:
3933 transport_destroy_device(dev);
3934 spin_lock_irqsave(shost->host_lock, flags);
3935 list_del(&vport->peers);
3936 scsi_host_put(shost);
3937 fc_host->npiv_vports_inuse--;
3938 spin_unlock_irqrestore(shost->host_lock, flags);
3939 put_device(dev->parent);
3940 kfree(vport);
3941
3942 return error;
3943}
3944
3945
3946
3947
3948
3949
3950
3951
3952
3953
3954
3955struct fc_vport *
3956fc_vport_create(struct Scsi_Host *shost, int channel,
3957 struct fc_vport_identifiers *ids)
3958{
3959 int stat;
3960 struct fc_vport *vport;
3961
3962 stat = fc_vport_setup(shost, channel, &shost->shost_gendev,
3963 ids, &vport);
3964 return stat ? NULL : vport;
3965}
3966EXPORT_SYMBOL(fc_vport_create);
3967
3968
3969
3970
3971
3972
3973
3974
3975
3976
3977
3978int
3979fc_vport_terminate(struct fc_vport *vport)
3980{
3981 struct Scsi_Host *shost = vport_to_shost(vport);
3982 struct fc_host_attrs *fc_host = shost_to_fc_host(shost);
3983 struct fc_internal *i = to_fc_internal(shost->transportt);
3984 struct device *dev = &vport->dev;
3985 unsigned long flags;
3986 int stat;
3987
3988 if (i->f->vport_delete)
3989 stat = i->f->vport_delete(vport);
3990 else
3991 stat = -ENOENT;
3992
3993 spin_lock_irqsave(shost->host_lock, flags);
3994 vport->flags &= ~FC_VPORT_DELETING;
3995 if (!stat) {
3996 vport->flags |= FC_VPORT_DELETED;
3997 list_del(&vport->peers);
3998 fc_host->npiv_vports_inuse--;
3999 scsi_host_put(shost);
4000 }
4001 spin_unlock_irqrestore(shost->host_lock, flags);
4002
4003 if (stat)
4004 return stat;
4005
4006 if (dev->parent != &shost->shost_gendev)
4007 sysfs_remove_link(&shost->shost_gendev.kobj, dev_name(dev));
4008 transport_remove_device(dev);
4009 device_del(dev);
4010 transport_destroy_device(dev);
4011
4012
4013
4014
4015
4016
4017 put_device(dev);
4018
4019 return 0;
4020}
4021EXPORT_SYMBOL(fc_vport_terminate);
4022
4023
4024
4025
4026
4027static void
4028fc_vport_sched_delete(struct work_struct *work)
4029{
4030 struct fc_vport *vport =
4031 container_of(work, struct fc_vport, vport_delete_work);
4032 int stat;
4033
4034 stat = fc_vport_terminate(vport);
4035 if (stat)
4036 dev_printk(KERN_ERR, vport->dev.parent,
4037 "%s: %s could not be deleted created via "
4038 "shost%d channel %d - error %d\n", __func__,
4039 dev_name(&vport->dev), vport->shost->host_no,
4040 vport->channel, stat);
4041}
4042
4043
4044
4045
4046
4047
4048
4049
4050
4051
4052static enum blk_eh_timer_return
4053fc_bsg_job_timeout(struct request *req)
4054{
4055 struct bsg_job *job = blk_mq_rq_to_pdu(req);
4056 struct Scsi_Host *shost = fc_bsg_to_shost(job);
4057 struct fc_rport *rport = fc_bsg_to_rport(job);
4058 struct fc_internal *i = to_fc_internal(shost->transportt);
4059 int err = 0, inflight = 0;
4060
4061 if (rport && rport->port_state == FC_PORTSTATE_BLOCKED)
4062 return BLK_EH_RESET_TIMER;
4063
4064 inflight = bsg_job_get(job);
4065
4066 if (inflight && i->f->bsg_timeout) {
4067
4068 err = i->f->bsg_timeout(job);
4069 if (err == -EAGAIN) {
4070 bsg_job_put(job);
4071 return BLK_EH_RESET_TIMER;
4072 } else if (err)
4073 printk(KERN_ERR "ERROR: FC BSG request timeout - LLD "
4074 "abort failed with status %d\n", err);
4075 }
4076
4077
4078 if (inflight)
4079 blk_mq_end_request(req, BLK_STS_IOERR);
4080 return BLK_EH_DONE;
4081}
4082
4083
4084
4085
4086
4087
4088static int fc_bsg_host_dispatch(struct Scsi_Host *shost, struct bsg_job *job)
4089{
4090 struct fc_internal *i = to_fc_internal(shost->transportt);
4091 struct fc_bsg_request *bsg_request = job->request;
4092 struct fc_bsg_reply *bsg_reply = job->reply;
4093 int cmdlen = sizeof(uint32_t);
4094 int ret;
4095
4096
4097 if (job->request_len < cmdlen) {
4098 ret = -ENOMSG;
4099 goto fail_host_msg;
4100 }
4101
4102
4103 switch (bsg_request->msgcode) {
4104 case FC_BSG_HST_ADD_RPORT:
4105 cmdlen += sizeof(struct fc_bsg_host_add_rport);
4106 break;
4107
4108 case FC_BSG_HST_DEL_RPORT:
4109 cmdlen += sizeof(struct fc_bsg_host_del_rport);
4110 break;
4111
4112 case FC_BSG_HST_ELS_NOLOGIN:
4113 cmdlen += sizeof(struct fc_bsg_host_els);
4114
4115 if ((!job->request_payload.payload_len) ||
4116 (!job->reply_payload.payload_len)) {
4117 ret = -EINVAL;
4118 goto fail_host_msg;
4119 }
4120 break;
4121
4122 case FC_BSG_HST_CT:
4123 cmdlen += sizeof(struct fc_bsg_host_ct);
4124
4125 if ((!job->request_payload.payload_len) ||
4126 (!job->reply_payload.payload_len)) {
4127 ret = -EINVAL;
4128 goto fail_host_msg;
4129 }
4130 break;
4131
4132 case FC_BSG_HST_VENDOR:
4133 cmdlen += sizeof(struct fc_bsg_host_vendor);
4134 if ((shost->hostt->vendor_id == 0L) ||
4135 (bsg_request->rqst_data.h_vendor.vendor_id !=
4136 shost->hostt->vendor_id)) {
4137 ret = -ESRCH;
4138 goto fail_host_msg;
4139 }
4140 break;
4141
4142 default:
4143 ret = -EBADR;
4144 goto fail_host_msg;
4145 }
4146
4147 ret = i->f->bsg_request(job);
4148 if (!ret)
4149 return 0;
4150
4151fail_host_msg:
4152
4153 BUG_ON(job->reply_len < sizeof(uint32_t));
4154 bsg_reply->reply_payload_rcv_len = 0;
4155 bsg_reply->result = ret;
4156 job->reply_len = sizeof(uint32_t);
4157 bsg_job_done(job, bsg_reply->result,
4158 bsg_reply->reply_payload_rcv_len);
4159 return 0;
4160}
4161
4162
4163
4164
4165
4166
4167static void
4168fc_bsg_goose_queue(struct fc_rport *rport)
4169{
4170 struct request_queue *q = rport->rqst_q;
4171
4172 if (q)
4173 blk_mq_run_hw_queues(q, true);
4174}
4175
4176
4177
4178
4179
4180
4181static int fc_bsg_rport_dispatch(struct Scsi_Host *shost, struct bsg_job *job)
4182{
4183 struct fc_internal *i = to_fc_internal(shost->transportt);
4184 struct fc_bsg_request *bsg_request = job->request;
4185 struct fc_bsg_reply *bsg_reply = job->reply;
4186 int cmdlen = sizeof(uint32_t);
4187 int ret;
4188
4189
4190 if (job->request_len < cmdlen) {
4191 ret = -ENOMSG;
4192 goto fail_rport_msg;
4193 }
4194
4195
4196 switch (bsg_request->msgcode) {
4197 case FC_BSG_RPT_ELS:
4198 cmdlen += sizeof(struct fc_bsg_rport_els);
4199 goto check_bidi;
4200
4201 case FC_BSG_RPT_CT:
4202 cmdlen += sizeof(struct fc_bsg_rport_ct);
4203check_bidi:
4204
4205 if ((!job->request_payload.payload_len) ||
4206 (!job->reply_payload.payload_len)) {
4207 ret = -EINVAL;
4208 goto fail_rport_msg;
4209 }
4210 break;
4211 default:
4212 ret = -EBADR;
4213 goto fail_rport_msg;
4214 }
4215
4216 ret = i->f->bsg_request(job);
4217 if (!ret)
4218 return 0;
4219
4220fail_rport_msg:
4221
4222 BUG_ON(job->reply_len < sizeof(uint32_t));
4223 bsg_reply->reply_payload_rcv_len = 0;
4224 bsg_reply->result = ret;
4225 job->reply_len = sizeof(uint32_t);
4226 bsg_job_done(job, bsg_reply->result,
4227 bsg_reply->reply_payload_rcv_len);
4228 return 0;
4229}
4230
4231static int fc_bsg_dispatch(struct bsg_job *job)
4232{
4233 struct Scsi_Host *shost = fc_bsg_to_shost(job);
4234
4235 if (scsi_is_fc_rport(job->dev))
4236 return fc_bsg_rport_dispatch(shost, job);
4237 else
4238 return fc_bsg_host_dispatch(shost, job);
4239}
4240
4241static blk_status_t fc_bsg_rport_prep(struct fc_rport *rport)
4242{
4243 if (rport->port_state == FC_PORTSTATE_BLOCKED &&
4244 !(rport->flags & FC_RPORT_FAST_FAIL_TIMEDOUT))
4245 return BLK_STS_RESOURCE;
4246
4247 if ((rport->port_state != FC_PORTSTATE_ONLINE) &&
4248 (rport->port_state != FC_PORTSTATE_MARGINAL))
4249 return BLK_STS_IOERR;
4250
4251 return BLK_STS_OK;
4252}
4253
4254
4255static int fc_bsg_dispatch_prep(struct bsg_job *job)
4256{
4257 struct fc_rport *rport = fc_bsg_to_rport(job);
4258 blk_status_t ret;
4259
4260 ret = fc_bsg_rport_prep(rport);
4261 switch (ret) {
4262 case BLK_STS_OK:
4263 break;
4264 case BLK_STS_RESOURCE:
4265 return -EAGAIN;
4266 default:
4267 return -EIO;
4268 }
4269
4270 return fc_bsg_dispatch(job);
4271}
4272
4273
4274
4275
4276
4277
4278static int
4279fc_bsg_hostadd(struct Scsi_Host *shost, struct fc_host_attrs *fc_host)
4280{
4281 struct device *dev = &shost->shost_gendev;
4282 struct fc_internal *i = to_fc_internal(shost->transportt);
4283 struct request_queue *q;
4284 char bsg_name[20];
4285
4286 fc_host->rqst_q = NULL;
4287
4288 if (!i->f->bsg_request)
4289 return -ENOTSUPP;
4290
4291 snprintf(bsg_name, sizeof(bsg_name),
4292 "fc_host%d", shost->host_no);
4293
4294 q = bsg_setup_queue(dev, bsg_name, fc_bsg_dispatch, fc_bsg_job_timeout,
4295 i->f->dd_bsg_size);
4296 if (IS_ERR(q)) {
4297 dev_err(dev,
4298 "fc_host%d: bsg interface failed to initialize - setup queue\n",
4299 shost->host_no);
4300 return PTR_ERR(q);
4301 }
4302 __scsi_init_queue(shost, q);
4303 blk_queue_rq_timeout(q, FC_DEFAULT_BSG_TIMEOUT);
4304 fc_host->rqst_q = q;
4305 return 0;
4306}
4307
4308
4309
4310
4311
4312
4313static int
4314fc_bsg_rportadd(struct Scsi_Host *shost, struct fc_rport *rport)
4315{
4316 struct device *dev = &rport->dev;
4317 struct fc_internal *i = to_fc_internal(shost->transportt);
4318 struct request_queue *q;
4319
4320 rport->rqst_q = NULL;
4321
4322 if (!i->f->bsg_request)
4323 return -ENOTSUPP;
4324
4325 q = bsg_setup_queue(dev, dev_name(dev), fc_bsg_dispatch_prep,
4326 fc_bsg_job_timeout, i->f->dd_bsg_size);
4327 if (IS_ERR(q)) {
4328 dev_err(dev, "failed to setup bsg queue\n");
4329 return PTR_ERR(q);
4330 }
4331 __scsi_init_queue(shost, q);
4332 blk_queue_rq_timeout(q, BLK_DEFAULT_SG_TIMEOUT);
4333 rport->rqst_q = q;
4334 return 0;
4335}
4336
4337
4338
4339
4340
4341
4342
4343
4344
4345
4346
4347static void
4348fc_bsg_remove(struct request_queue *q)
4349{
4350 bsg_remove_queue(q);
4351}
4352
4353
4354
4355MODULE_AUTHOR("James Smart");
4356MODULE_DESCRIPTION("FC Transport Attributes");
4357MODULE_LICENSE("GPL");
4358
4359module_init(fc_transport_init);
4360module_exit(fc_transport_exit);
4361