aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/scsi/fnic/fnic_main.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/scsi/fnic/fnic_main.c')
-rw-r--r--drivers/scsi/fnic/fnic_main.c109
1 files changed, 63 insertions, 46 deletions
diff --git a/drivers/scsi/fnic/fnic_main.c b/drivers/scsi/fnic/fnic_main.c
index 71c7bbe26d05..97b212570bcc 100644
--- a/drivers/scsi/fnic/fnic_main.c
+++ b/drivers/scsi/fnic/fnic_main.c
@@ -18,6 +18,7 @@
18#include <linux/module.h> 18#include <linux/module.h>
19#include <linux/mempool.h> 19#include <linux/mempool.h>
20#include <linux/string.h> 20#include <linux/string.h>
21#include <linux/slab.h>
21#include <linux/errno.h> 22#include <linux/errno.h>
22#include <linux/init.h> 23#include <linux/init.h>
23#include <linux/pci.h> 24#include <linux/pci.h>
@@ -25,6 +26,8 @@
25#include <linux/interrupt.h> 26#include <linux/interrupt.h>
26#include <linux/spinlock.h> 27#include <linux/spinlock.h>
27#include <linux/workqueue.h> 28#include <linux/workqueue.h>
29#include <linux/if_ether.h>
30#include <scsi/fc/fc_fip.h>
28#include <scsi/scsi_host.h> 31#include <scsi/scsi_host.h>
29#include <scsi/scsi_transport.h> 32#include <scsi/scsi_transport.h>
30#include <scsi/scsi_transport_fc.h> 33#include <scsi/scsi_transport_fc.h>
@@ -68,6 +71,7 @@ MODULE_PARM_DESC(fnic_log_level, "bit mask of fnic logging levels");
68 71
69static struct libfc_function_template fnic_transport_template = { 72static struct libfc_function_template fnic_transport_template = {
70 .frame_send = fnic_send, 73 .frame_send = fnic_send,
74 .lport_set_port_id = fnic_set_port_id,
71 .fcp_abort_io = fnic_empty_scsi_cleanup, 75 .fcp_abort_io = fnic_empty_scsi_cleanup,
72 .fcp_cleanup = fnic_empty_scsi_cleanup, 76 .fcp_cleanup = fnic_empty_scsi_cleanup,
73 .exch_mgr_reset = fnic_exch_mgr_reset 77 .exch_mgr_reset = fnic_exch_mgr_reset
@@ -140,6 +144,7 @@ static struct fc_function_template fnic_fc_functions = {
140 .get_fc_host_stats = fnic_get_stats, 144 .get_fc_host_stats = fnic_get_stats,
141 .dd_fcrport_size = sizeof(struct fc_rport_libfc_priv), 145 .dd_fcrport_size = sizeof(struct fc_rport_libfc_priv),
142 .terminate_rport_io = fnic_terminate_rport_io, 146 .terminate_rport_io = fnic_terminate_rport_io,
147 .bsg_request = fc_lport_bsg_request,
143}; 148};
144 149
145static void fnic_get_host_speed(struct Scsi_Host *shost) 150static void fnic_get_host_speed(struct Scsi_Host *shost)
@@ -324,9 +329,6 @@ static int fnic_cleanup(struct fnic *fnic)
324{ 329{
325 unsigned int i; 330 unsigned int i;
326 int err; 331 int err;
327 unsigned long flags;
328 struct fc_frame *flogi = NULL;
329 struct fc_frame *flogi_resp = NULL;
330 332
331 vnic_dev_disable(fnic->vdev); 333 vnic_dev_disable(fnic->vdev);
332 for (i = 0; i < fnic->intr_count; i++) 334 for (i = 0; i < fnic->intr_count; i++)
@@ -367,24 +369,6 @@ static int fnic_cleanup(struct fnic *fnic)
367 for (i = 0; i < fnic->intr_count; i++) 369 for (i = 0; i < fnic->intr_count; i++)
368 vnic_intr_clean(&fnic->intr[i]); 370 vnic_intr_clean(&fnic->intr[i]);
369 371
370 /*
371 * Remove cached flogi and flogi resp frames if any
372 * These frames are not in any queue, and therefore queue
373 * cleanup does not clean them. So clean them explicitly
374 */
375 spin_lock_irqsave(&fnic->fnic_lock, flags);
376 flogi = fnic->flogi;
377 fnic->flogi = NULL;
378 flogi_resp = fnic->flogi_resp;
379 fnic->flogi_resp = NULL;
380 spin_unlock_irqrestore(&fnic->fnic_lock, flags);
381
382 if (flogi)
383 dev_kfree_skb(fp_skb(flogi));
384
385 if (flogi_resp)
386 dev_kfree_skb(fp_skb(flogi_resp));
387
388 mempool_destroy(fnic->io_req_pool); 372 mempool_destroy(fnic->io_req_pool);
389 for (i = 0; i < FNIC_SGL_NUM_CACHES; i++) 373 for (i = 0; i < FNIC_SGL_NUM_CACHES; i++)
390 mempool_destroy(fnic->io_sgl_pool[i]); 374 mempool_destroy(fnic->io_sgl_pool[i]);
@@ -409,6 +393,17 @@ static void *fnic_alloc_slab_dma(gfp_t gfp_mask, void *pool_data)
409 return kmem_cache_alloc(mem, gfp_mask | GFP_ATOMIC | GFP_DMA); 393 return kmem_cache_alloc(mem, gfp_mask | GFP_ATOMIC | GFP_DMA);
410} 394}
411 395
396/**
397 * fnic_get_mac() - get assigned data MAC address for FIP code.
398 * @lport: local port.
399 */
400static u8 *fnic_get_mac(struct fc_lport *lport)
401{
402 struct fnic *fnic = lport_priv(lport);
403
404 return fnic->data_src_addr;
405}
406
412static int __devinit fnic_probe(struct pci_dev *pdev, 407static int __devinit fnic_probe(struct pci_dev *pdev,
413 const struct pci_device_id *ent) 408 const struct pci_device_id *ent)
414{ 409{
@@ -424,17 +419,16 @@ static int __devinit fnic_probe(struct pci_dev *pdev,
424 * Allocate SCSI Host and set up association between host, 419 * Allocate SCSI Host and set up association between host,
425 * local port, and fnic 420 * local port, and fnic
426 */ 421 */
427 host = scsi_host_alloc(&fnic_host_template, 422 lp = libfc_host_alloc(&fnic_host_template, sizeof(struct fnic));
428 sizeof(struct fc_lport) + sizeof(struct fnic)); 423 if (!lp) {
429 if (!host) { 424 printk(KERN_ERR PFX "Unable to alloc libfc local port\n");
430 printk(KERN_ERR PFX "Unable to alloc SCSI host\n");
431 err = -ENOMEM; 425 err = -ENOMEM;
432 goto err_out; 426 goto err_out;
433 } 427 }
434 lp = shost_priv(host); 428 host = lp->host;
435 lp->host = host;
436 fnic = lport_priv(lp); 429 fnic = lport_priv(lp);
437 fnic->lport = lp; 430 fnic->lport = lp;
431 fnic->ctlr.lp = lp;
438 432
439 snprintf(fnic->name, sizeof(fnic->name) - 1, "%s%d", DRV_NAME, 433 snprintf(fnic->name, sizeof(fnic->name) - 1, "%s%d", DRV_NAME,
440 host->host_no); 434 host->host_no);
@@ -543,12 +537,14 @@ static int __devinit fnic_probe(struct pci_dev *pdev,
543 goto err_out_dev_close; 537 goto err_out_dev_close;
544 } 538 }
545 539
546 err = vnic_dev_mac_addr(fnic->vdev, fnic->mac_addr); 540 err = vnic_dev_mac_addr(fnic->vdev, fnic->ctlr.ctl_src_addr);
547 if (err) { 541 if (err) {
548 shost_printk(KERN_ERR, fnic->lport->host, 542 shost_printk(KERN_ERR, fnic->lport->host,
549 "vNIC get MAC addr failed \n"); 543 "vNIC get MAC addr failed \n");
550 goto err_out_dev_close; 544 goto err_out_dev_close;
551 } 545 }
546 /* set data_src for point-to-point mode and to keep it non-zero */
547 memcpy(fnic->data_src_addr, fnic->ctlr.ctl_src_addr, ETH_ALEN);
552 548
553 /* Get vNIC configuration */ 549 /* Get vNIC configuration */
554 err = fnic_get_vnic_config(fnic); 550 err = fnic_get_vnic_config(fnic);
@@ -560,6 +556,7 @@ static int __devinit fnic_probe(struct pci_dev *pdev,
560 } 556 }
561 host->max_lun = fnic->config.luns_per_tgt; 557 host->max_lun = fnic->config.luns_per_tgt;
562 host->max_id = FNIC_MAX_FCP_TARGET; 558 host->max_id = FNIC_MAX_FCP_TARGET;
559 host->max_cmd_len = FNIC_MAX_CMD_LEN;
563 560
564 fnic_get_res_counts(fnic); 561 fnic_get_res_counts(fnic);
565 562
@@ -571,19 +568,12 @@ static int __devinit fnic_probe(struct pci_dev *pdev,
571 goto err_out_dev_close; 568 goto err_out_dev_close;
572 } 569 }
573 570
574 err = fnic_request_intr(fnic);
575 if (err) {
576 shost_printk(KERN_ERR, fnic->lport->host,
577 "Unable to request irq.\n");
578 goto err_out_clear_intr;
579 }
580
581 err = fnic_alloc_vnic_resources(fnic); 571 err = fnic_alloc_vnic_resources(fnic);
582 if (err) { 572 if (err) {
583 shost_printk(KERN_ERR, fnic->lport->host, 573 shost_printk(KERN_ERR, fnic->lport->host,
584 "Failed to alloc vNIC resources, " 574 "Failed to alloc vNIC resources, "
585 "aborting.\n"); 575 "aborting.\n");
586 goto err_out_free_intr; 576 goto err_out_clear_intr;
587 } 577 }
588 578
589 579
@@ -623,9 +613,23 @@ static int __devinit fnic_probe(struct pci_dev *pdev,
623 fnic->vlan_hw_insert = 1; 613 fnic->vlan_hw_insert = 1;
624 fnic->vlan_id = 0; 614 fnic->vlan_id = 0;
625 615
626 fnic->flogi_oxid = FC_XID_UNKNOWN; 616 /* Initialize the FIP fcoe_ctrl struct */
627 fnic->flogi = NULL; 617 fnic->ctlr.send = fnic_eth_send;
628 fnic->flogi_resp = NULL; 618 fnic->ctlr.update_mac = fnic_update_mac;
619 fnic->ctlr.get_src_addr = fnic_get_mac;
620 fcoe_ctlr_init(&fnic->ctlr);
621 if (fnic->config.flags & VFCF_FIP_CAPABLE) {
622 shost_printk(KERN_INFO, fnic->lport->host,
623 "firmware supports FIP\n");
624 /* enable directed and multicast */
625 vnic_dev_packet_filter(fnic->vdev, 1, 1, 0, 0, 0);
626 vnic_dev_add_addr(fnic->vdev, FIP_ALL_ENODE_MACS);
627 vnic_dev_add_addr(fnic->vdev, fnic->ctlr.ctl_src_addr);
628 } else {
629 shost_printk(KERN_INFO, fnic->lport->host,
630 "firmware uses non-FIP mode\n");
631 fnic->ctlr.mode = FIP_ST_NON_FIP;
632 }
629 fnic->state = FNIC_IN_FC_MODE; 633 fnic->state = FNIC_IN_FC_MODE;
630 634
631 /* Enable hardware stripping of vlan header on ingress */ 635 /* Enable hardware stripping of vlan header on ingress */
@@ -697,6 +701,8 @@ static int __devinit fnic_probe(struct pci_dev *pdev,
697 goto err_out_remove_scsi_host; 701 goto err_out_remove_scsi_host;
698 } 702 }
699 703
704 fc_lport_init_stats(lp);
705
700 fc_lport_config(lp); 706 fc_lport_config(lp);
701 707
702 if (fc_set_mfs(lp, fnic->config.maxdatafieldsize + 708 if (fc_set_mfs(lp, fnic->config.maxdatafieldsize +
@@ -716,6 +722,7 @@ static int __devinit fnic_probe(struct pci_dev *pdev,
716 INIT_WORK(&fnic->link_work, fnic_handle_link); 722 INIT_WORK(&fnic->link_work, fnic_handle_link);
717 INIT_WORK(&fnic->frame_work, fnic_handle_frame); 723 INIT_WORK(&fnic->frame_work, fnic_handle_frame);
718 skb_queue_head_init(&fnic->frame_queue); 724 skb_queue_head_init(&fnic->frame_queue);
725 skb_queue_head_init(&fnic->tx_queue);
719 726
720 /* Enable all queues */ 727 /* Enable all queues */
721 for (i = 0; i < fnic->raw_wq_count; i++) 728 for (i = 0; i < fnic->raw_wq_count; i++)
@@ -728,6 +735,14 @@ static int __devinit fnic_probe(struct pci_dev *pdev,
728 fc_fabric_login(lp); 735 fc_fabric_login(lp);
729 736
730 vnic_dev_enable(fnic->vdev); 737 vnic_dev_enable(fnic->vdev);
738
739 err = fnic_request_intr(fnic);
740 if (err) {
741 shost_printk(KERN_ERR, fnic->lport->host,
742 "Unable to request irq.\n");
743 goto err_out_free_exch_mgr;
744 }
745
731 for (i = 0; i < fnic->intr_count; i++) 746 for (i = 0; i < fnic->intr_count; i++)
732 vnic_intr_unmask(&fnic->intr[i]); 747 vnic_intr_unmask(&fnic->intr[i]);
733 748
@@ -738,8 +753,8 @@ static int __devinit fnic_probe(struct pci_dev *pdev,
738err_out_free_exch_mgr: 753err_out_free_exch_mgr:
739 fc_exch_mgr_free(lp); 754 fc_exch_mgr_free(lp);
740err_out_remove_scsi_host: 755err_out_remove_scsi_host:
741 fc_remove_host(fnic->lport->host); 756 fc_remove_host(lp->host);
742 scsi_remove_host(fnic->lport->host); 757 scsi_remove_host(lp->host);
743err_out_free_rq_buf: 758err_out_free_rq_buf:
744 for (i = 0; i < fnic->rq_count; i++) 759 for (i = 0; i < fnic->rq_count; i++)
745 vnic_rq_clean(&fnic->rq[i], fnic_free_rq_buf); 760 vnic_rq_clean(&fnic->rq[i], fnic_free_rq_buf);
@@ -752,8 +767,6 @@ err_out_free_ioreq_pool:
752 mempool_destroy(fnic->io_req_pool); 767 mempool_destroy(fnic->io_req_pool);
753err_out_free_resources: 768err_out_free_resources:
754 fnic_free_vnic_resources(fnic); 769 fnic_free_vnic_resources(fnic);
755err_out_free_intr:
756 fnic_free_intr(fnic);
757err_out_clear_intr: 770err_out_clear_intr:
758 fnic_clear_intr_mode(fnic); 771 fnic_clear_intr_mode(fnic);
759err_out_dev_close: 772err_out_dev_close:
@@ -775,6 +788,7 @@ err_out:
775static void __devexit fnic_remove(struct pci_dev *pdev) 788static void __devexit fnic_remove(struct pci_dev *pdev)
776{ 789{
777 struct fnic *fnic = pci_get_drvdata(pdev); 790 struct fnic *fnic = pci_get_drvdata(pdev);
791 struct fc_lport *lp = fnic->lport;
778 unsigned long flags; 792 unsigned long flags;
779 793
780 /* 794 /*
@@ -796,6 +810,7 @@ static void __devexit fnic_remove(struct pci_dev *pdev)
796 */ 810 */
797 flush_workqueue(fnic_event_queue); 811 flush_workqueue(fnic_event_queue);
798 skb_queue_purge(&fnic->frame_queue); 812 skb_queue_purge(&fnic->frame_queue);
813 skb_queue_purge(&fnic->tx_queue);
799 814
800 /* 815 /*
801 * Log off the fabric. This stops all remote ports, dns port, 816 * Log off the fabric. This stops all remote ports, dns port,
@@ -808,7 +823,8 @@ static void __devexit fnic_remove(struct pci_dev *pdev)
808 fnic->in_remove = 1; 823 fnic->in_remove = 1;
809 spin_unlock_irqrestore(&fnic->fnic_lock, flags); 824 spin_unlock_irqrestore(&fnic->fnic_lock, flags);
810 825
811 fc_lport_destroy(fnic->lport); 826 fcoe_ctlr_destroy(&fnic->ctlr);
827 fc_lport_destroy(lp);
812 828
813 /* 829 /*
814 * This stops the fnic device, masks all interrupts. Completed 830 * This stops the fnic device, masks all interrupts. Completed
@@ -818,6 +834,7 @@ static void __devexit fnic_remove(struct pci_dev *pdev)
818 fnic_cleanup(fnic); 834 fnic_cleanup(fnic);
819 835
820 BUG_ON(!skb_queue_empty(&fnic->frame_queue)); 836 BUG_ON(!skb_queue_empty(&fnic->frame_queue));
837 BUG_ON(!skb_queue_empty(&fnic->tx_queue));
821 838
822 spin_lock_irqsave(&fnic_list_lock, flags); 839 spin_lock_irqsave(&fnic_list_lock, flags);
823 list_del(&fnic->list); 840 list_del(&fnic->list);
@@ -827,8 +844,8 @@ static void __devexit fnic_remove(struct pci_dev *pdev)
827 scsi_remove_host(fnic->lport->host); 844 scsi_remove_host(fnic->lport->host);
828 fc_exch_mgr_free(fnic->lport); 845 fc_exch_mgr_free(fnic->lport);
829 vnic_dev_notify_unset(fnic->vdev); 846 vnic_dev_notify_unset(fnic->vdev);
830 fnic_free_vnic_resources(fnic);
831 fnic_free_intr(fnic); 847 fnic_free_intr(fnic);
848 fnic_free_vnic_resources(fnic);
832 fnic_clear_intr_mode(fnic); 849 fnic_clear_intr_mode(fnic);
833 vnic_dev_close(fnic->vdev); 850 vnic_dev_close(fnic->vdev);
834 vnic_dev_unregister(fnic->vdev); 851 vnic_dev_unregister(fnic->vdev);
@@ -836,7 +853,7 @@ static void __devexit fnic_remove(struct pci_dev *pdev)
836 pci_release_regions(pdev); 853 pci_release_regions(pdev);
837 pci_disable_device(pdev); 854 pci_disable_device(pdev);
838 pci_set_drvdata(pdev, NULL); 855 pci_set_drvdata(pdev, NULL);
839 scsi_host_put(fnic->lport->host); 856 scsi_host_put(lp->host);
840} 857}
841 858
842static struct pci_driver fnic_driver = { 859static struct pci_driver fnic_driver = {