diff options
author | Jing Huang <huangj@brocade.com> | 2010-03-19 14:05:39 -0400 |
---|---|---|
committer | James Bottomley <James.Bottomley@suse.de> | 2010-04-11 10:24:16 -0400 |
commit | b504293fe9dc42917a919044f2b672fb361329d0 (patch) | |
tree | 13a7a576560155c6c8b49976e286060b5c904aba /drivers/scsi/bfa/bfad_im.c | |
parent | 12fb8c1574d7d0c262d2f4c667047889c4f27ebe (diff) |
[SCSI] bfa: add fc transport class based vport create/delete
Use duplicate fc transport template for physical and vitual port. Add
vport create/delete/disalbe functions in the transport template of physical
port. Changes to make the vport create/delete function to work under this
framework.
Signed-off-by: Jing Huang <huangj@brocade.com>
Signed-off-by: James Bottomley <James.Bottomley@suse.de>
Diffstat (limited to 'drivers/scsi/bfa/bfad_im.c')
-rw-r--r-- | drivers/scsi/bfa/bfad_im.c | 53 |
1 files changed, 27 insertions, 26 deletions
diff --git a/drivers/scsi/bfa/bfad_im.c b/drivers/scsi/bfa/bfad_im.c index e2c70de2dba5..f263891b8cc6 100644 --- a/drivers/scsi/bfa/bfad_im.c +++ b/drivers/scsi/bfa/bfad_im.c | |||
@@ -30,6 +30,7 @@ BFA_TRC_FILE(LDRV, IM); | |||
30 | 30 | ||
31 | DEFINE_IDR(bfad_im_port_index); | 31 | DEFINE_IDR(bfad_im_port_index); |
32 | struct scsi_transport_template *bfad_im_scsi_transport_template; | 32 | struct scsi_transport_template *bfad_im_scsi_transport_template; |
33 | struct scsi_transport_template *bfad_im_scsi_vport_transport_template; | ||
33 | static void bfad_im_itnim_work_handler(struct work_struct *work); | 34 | static void bfad_im_itnim_work_handler(struct work_struct *work); |
34 | static int bfad_im_queuecommand(struct scsi_cmnd *cmnd, | 35 | static int bfad_im_queuecommand(struct scsi_cmnd *cmnd, |
35 | void (*done)(struct scsi_cmnd *)); | 36 | void (*done)(struct scsi_cmnd *)); |
@@ -512,7 +513,8 @@ void bfa_fcb_itnim_tov(struct bfad_itnim_s *itnim) | |||
512 | * Allocate a Scsi_Host for a port. | 513 | * Allocate a Scsi_Host for a port. |
513 | */ | 514 | */ |
514 | int | 515 | int |
515 | bfad_im_scsi_host_alloc(struct bfad_s *bfad, struct bfad_im_port_s *im_port) | 516 | bfad_im_scsi_host_alloc(struct bfad_s *bfad, struct bfad_im_port_s *im_port, |
517 | struct device *dev) | ||
516 | { | 518 | { |
517 | int error = 1; | 519 | int error = 1; |
518 | 520 | ||
@@ -541,12 +543,15 @@ bfad_im_scsi_host_alloc(struct bfad_s *bfad, struct bfad_im_port_s *im_port) | |||
541 | im_port->shost->max_lun = MAX_FCP_LUN; | 543 | im_port->shost->max_lun = MAX_FCP_LUN; |
542 | im_port->shost->max_cmd_len = 16; | 544 | im_port->shost->max_cmd_len = 16; |
543 | im_port->shost->can_queue = bfad->cfg_data.ioc_queue_depth; | 545 | im_port->shost->can_queue = bfad->cfg_data.ioc_queue_depth; |
544 | im_port->shost->transportt = bfad_im_scsi_transport_template; | 546 | if (im_port->port->pvb_type == BFAD_PORT_PHYS_BASE) |
547 | im_port->shost->transportt = bfad_im_scsi_transport_template; | ||
548 | else | ||
549 | im_port->shost->transportt = | ||
550 | bfad_im_scsi_vport_transport_template; | ||
545 | 551 | ||
546 | error = bfad_os_scsi_add_host(im_port->shost, im_port, bfad); | 552 | error = scsi_add_host(im_port->shost, dev); |
547 | if (error) { | 553 | if (error) { |
548 | printk(KERN_WARNING "bfad_os_scsi_add_host failure %d\n", | 554 | printk(KERN_WARNING "scsi_add_host failure %d\n", error); |
549 | error); | ||
550 | goto out_fc_rel; | 555 | goto out_fc_rel; |
551 | } | 556 | } |
552 | 557 | ||
@@ -588,9 +593,11 @@ bfad_im_port_delete_handler(struct work_struct *work) | |||
588 | struct bfad_im_port_s *im_port = | 593 | struct bfad_im_port_s *im_port = |
589 | container_of(work, struct bfad_im_port_s, port_delete_work); | 594 | container_of(work, struct bfad_im_port_s, port_delete_work); |
590 | 595 | ||
591 | bfad_im_scsi_host_free(im_port->bfad, im_port); | 596 | if (im_port->port->pvb_type != BFAD_PORT_PHYS_BASE) { |
592 | bfad_im_port_clean(im_port); | 597 | im_port->flags |= BFAD_PORT_DELETE; |
593 | kfree(im_port); | 598 | fc_vport_terminate(im_port->fc_vport); |
599 | } | ||
600 | |||
594 | } | 601 | } |
595 | 602 | ||
596 | bfa_status_t | 603 | bfa_status_t |
@@ -689,23 +696,6 @@ bfad_im_probe_undo(struct bfad_s *bfad) | |||
689 | } | 696 | } |
690 | } | 697 | } |
691 | 698 | ||
692 | |||
693 | |||
694 | |||
695 | int | ||
696 | bfad_os_scsi_add_host(struct Scsi_Host *shost, struct bfad_im_port_s *im_port, | ||
697 | struct bfad_s *bfad) | ||
698 | { | ||
699 | struct device *dev; | ||
700 | |||
701 | if (im_port->port->pvb_type == BFAD_PORT_PHYS_BASE) | ||
702 | dev = &bfad->pcidev->dev; | ||
703 | else | ||
704 | dev = &bfad->pport.im_port->shost->shost_gendev; | ||
705 | |||
706 | return scsi_add_host(shost, dev); | ||
707 | } | ||
708 | |||
709 | struct Scsi_Host * | 699 | struct Scsi_Host * |
710 | bfad_os_scsi_host_alloc(struct bfad_im_port_s *im_port, struct bfad_s *bfad) | 700 | bfad_os_scsi_host_alloc(struct bfad_im_port_s *im_port, struct bfad_s *bfad) |
711 | { | 701 | { |
@@ -724,7 +714,8 @@ bfad_os_scsi_host_alloc(struct bfad_im_port_s *im_port, struct bfad_s *bfad) | |||
724 | void | 714 | void |
725 | bfad_os_scsi_host_free(struct bfad_s *bfad, struct bfad_im_port_s *im_port) | 715 | bfad_os_scsi_host_free(struct bfad_s *bfad, struct bfad_im_port_s *im_port) |
726 | { | 716 | { |
727 | flush_workqueue(bfad->im->drv_workq); | 717 | if (!(im_port->flags & BFAD_PORT_DELETE)) |
718 | flush_workqueue(bfad->im->drv_workq); | ||
728 | bfad_im_scsi_host_free(im_port->bfad, im_port); | 719 | bfad_im_scsi_host_free(im_port->bfad, im_port); |
729 | bfad_im_port_clean(im_port); | 720 | bfad_im_port_clean(im_port); |
730 | kfree(im_port); | 721 | kfree(im_port); |
@@ -829,6 +820,13 @@ bfad_im_module_init(void) | |||
829 | if (!bfad_im_scsi_transport_template) | 820 | if (!bfad_im_scsi_transport_template) |
830 | return BFA_STATUS_ENOMEM; | 821 | return BFA_STATUS_ENOMEM; |
831 | 822 | ||
823 | bfad_im_scsi_vport_transport_template = | ||
824 | fc_attach_transport(&bfad_im_vport_fc_function_template); | ||
825 | if (!bfad_im_scsi_vport_transport_template) { | ||
826 | fc_release_transport(bfad_im_scsi_transport_template); | ||
827 | return BFA_STATUS_ENOMEM; | ||
828 | } | ||
829 | |||
832 | return BFA_STATUS_OK; | 830 | return BFA_STATUS_OK; |
833 | } | 831 | } |
834 | 832 | ||
@@ -837,6 +835,8 @@ bfad_im_module_exit(void) | |||
837 | { | 835 | { |
838 | if (bfad_im_scsi_transport_template) | 836 | if (bfad_im_scsi_transport_template) |
839 | fc_release_transport(bfad_im_scsi_transport_template); | 837 | fc_release_transport(bfad_im_scsi_transport_template); |
838 | if (bfad_im_scsi_vport_transport_template) | ||
839 | fc_release_transport(bfad_im_scsi_vport_transport_template); | ||
840 | } | 840 | } |
841 | 841 | ||
842 | void | 842 | void |
@@ -937,6 +937,7 @@ bfad_os_fc_host_init(struct bfad_im_port_s *im_port) | |||
937 | bfa_os_htonll((bfa_fcs_port_get_nwwn(port->fcs_port))); | 937 | bfa_os_htonll((bfa_fcs_port_get_nwwn(port->fcs_port))); |
938 | fc_host_port_name(host) = | 938 | fc_host_port_name(host) = |
939 | bfa_os_htonll((bfa_fcs_port_get_pwwn(port->fcs_port))); | 939 | bfa_os_htonll((bfa_fcs_port_get_pwwn(port->fcs_port))); |
940 | fc_host_max_npiv_vports(host) = bfa_lps_get_max_vport(&bfad->bfa); | ||
940 | 941 | ||
941 | fc_host_supported_classes(host) = FC_COS_CLASS3; | 942 | fc_host_supported_classes(host) = FC_COS_CLASS3; |
942 | 943 | ||