diff options
author | Christoph Hellwig <hch@lst.de> | 2016-09-11 09:31:23 -0400 |
---|---|---|
committer | Martin K. Petersen <martin.petersen@oracle.com> | 2016-11-08 17:29:46 -0500 |
commit | 68130c99480919c2088df530fc25b5e314ad806a (patch) | |
tree | 4ccad352ff0d508e00c4c69db281b30727bb65a4 /drivers | |
parent | e3a00f68e426df24a5fb98956a1bd1b23943aa1e (diff) |
scsi: arcmsr: Use pci_alloc_irq_vectors
Switch the arcmsr driver to use pci_alloc_irq_vectors. We need to two
calls to pci_alloc_irq_vectors as arcmsr only supports multiple MSI-X
vectors, but not multiple MSI vectors.
Otherwise this cleans up a lot of cruft and allows to use a common
request_irq loop for irq types, which happens to only iterate over a
single line in the non MSI-X case.
Signed-off-by: Christoph Hellwig <hch@lst.de>
Acked-by: Ching Huang <ching2048@areca.com.tw>
Signed-off-by: Martin K. Petersen <martin.petersen@oracle.com>
Diffstat (limited to 'drivers')
-rw-r--r-- | drivers/scsi/arcmsr/arcmsr.h | 5 | ||||
-rw-r--r-- | drivers/scsi/arcmsr/arcmsr_hba.c | 82 |
2 files changed, 33 insertions, 54 deletions
diff --git a/drivers/scsi/arcmsr/arcmsr.h b/drivers/scsi/arcmsr/arcmsr.h index cf99f8cf4cdd..a254b32eba39 100644 --- a/drivers/scsi/arcmsr/arcmsr.h +++ b/drivers/scsi/arcmsr/arcmsr.h | |||
@@ -629,7 +629,6 @@ struct AdapterControlBlock | |||
629 | struct pci_dev * pdev; | 629 | struct pci_dev * pdev; |
630 | struct Scsi_Host * host; | 630 | struct Scsi_Host * host; |
631 | unsigned long vir2phy_offset; | 631 | unsigned long vir2phy_offset; |
632 | struct msix_entry entries[ARCMST_NUM_MSIX_VECTORS]; | ||
633 | /* Offset is used in making arc cdb physical to virtual calculations */ | 632 | /* Offset is used in making arc cdb physical to virtual calculations */ |
634 | uint32_t outbound_int_enable; | 633 | uint32_t outbound_int_enable; |
635 | uint32_t cdb_phyaddr_hi32; | 634 | uint32_t cdb_phyaddr_hi32; |
@@ -671,8 +670,6 @@ struct AdapterControlBlock | |||
671 | /* iop init */ | 670 | /* iop init */ |
672 | #define ACB_F_ABORT 0x0200 | 671 | #define ACB_F_ABORT 0x0200 |
673 | #define ACB_F_FIRMWARE_TRAP 0x0400 | 672 | #define ACB_F_FIRMWARE_TRAP 0x0400 |
674 | #define ACB_F_MSI_ENABLED 0x1000 | ||
675 | #define ACB_F_MSIX_ENABLED 0x2000 | ||
676 | struct CommandControlBlock * pccb_pool[ARCMSR_MAX_FREECCB_NUM]; | 673 | struct CommandControlBlock * pccb_pool[ARCMSR_MAX_FREECCB_NUM]; |
677 | /* used for memory free */ | 674 | /* used for memory free */ |
678 | struct list_head ccb_free_list; | 675 | struct list_head ccb_free_list; |
@@ -725,7 +722,7 @@ struct AdapterControlBlock | |||
725 | atomic_t rq_map_token; | 722 | atomic_t rq_map_token; |
726 | atomic_t ante_token_value; | 723 | atomic_t ante_token_value; |
727 | uint32_t maxOutstanding; | 724 | uint32_t maxOutstanding; |
728 | int msix_vector_count; | 725 | int vector_count; |
729 | };/* HW_DEVICE_EXTENSION */ | 726 | };/* HW_DEVICE_EXTENSION */ |
730 | /* | 727 | /* |
731 | ******************************************************************************* | 728 | ******************************************************************************* |
diff --git a/drivers/scsi/arcmsr/arcmsr_hba.c b/drivers/scsi/arcmsr/arcmsr_hba.c index f0cfb0451757..9e45749d55ed 100644 --- a/drivers/scsi/arcmsr/arcmsr_hba.c +++ b/drivers/scsi/arcmsr/arcmsr_hba.c | |||
@@ -720,51 +720,39 @@ static void arcmsr_message_isr_bh_fn(struct work_struct *work) | |||
720 | static int | 720 | static int |
721 | arcmsr_request_irq(struct pci_dev *pdev, struct AdapterControlBlock *acb) | 721 | arcmsr_request_irq(struct pci_dev *pdev, struct AdapterControlBlock *acb) |
722 | { | 722 | { |
723 | int i, j, r; | 723 | unsigned long flags; |
724 | struct msix_entry entries[ARCMST_NUM_MSIX_VECTORS]; | 724 | int nvec, i; |
725 | 725 | ||
726 | for (i = 0; i < ARCMST_NUM_MSIX_VECTORS; i++) | 726 | nvec = pci_alloc_irq_vectors(pdev, 1, ARCMST_NUM_MSIX_VECTORS, |
727 | entries[i].entry = i; | 727 | PCI_IRQ_MSIX); |
728 | r = pci_enable_msix_range(pdev, entries, 1, ARCMST_NUM_MSIX_VECTORS); | 728 | if (nvec > 0) { |
729 | if (r < 0) | 729 | pr_info("arcmsr%d: msi-x enabled\n", acb->host->host_no); |
730 | goto msi_int; | 730 | flags = 0; |
731 | acb->msix_vector_count = r; | 731 | } else { |
732 | for (i = 0; i < r; i++) { | 732 | nvec = pci_alloc_irq_vectors(pdev, 1, 1, |
733 | if (request_irq(entries[i].vector, | 733 | PCI_IRQ_MSI | PCI_IRQ_LEGACY); |
734 | arcmsr_do_interrupt, 0, "arcmsr", acb)) { | 734 | if (nvec < 1) |
735 | return FAILED; | ||
736 | |||
737 | flags = IRQF_SHARED; | ||
738 | } | ||
739 | |||
740 | acb->vector_count = nvec; | ||
741 | for (i = 0; i < nvec; i++) { | ||
742 | if (request_irq(pci_irq_vector(pdev, i), arcmsr_do_interrupt, | ||
743 | flags, "arcmsr", acb)) { | ||
735 | pr_warn("arcmsr%d: request_irq =%d failed!\n", | 744 | pr_warn("arcmsr%d: request_irq =%d failed!\n", |
736 | acb->host->host_no, entries[i].vector); | 745 | acb->host->host_no, pci_irq_vector(pdev, i)); |
737 | for (j = 0 ; j < i ; j++) | 746 | goto out_free_irq; |
738 | free_irq(entries[j].vector, acb); | ||
739 | pci_disable_msix(pdev); | ||
740 | goto msi_int; | ||
741 | } | 747 | } |
742 | acb->entries[i] = entries[i]; | ||
743 | } | ||
744 | acb->acb_flags |= ACB_F_MSIX_ENABLED; | ||
745 | pr_info("arcmsr%d: msi-x enabled\n", acb->host->host_no); | ||
746 | return SUCCESS; | ||
747 | msi_int: | ||
748 | if (pci_enable_msi_exact(pdev, 1) < 0) | ||
749 | goto legacy_int; | ||
750 | if (request_irq(pdev->irq, arcmsr_do_interrupt, | ||
751 | IRQF_SHARED, "arcmsr", acb)) { | ||
752 | pr_warn("arcmsr%d: request_irq =%d failed!\n", | ||
753 | acb->host->host_no, pdev->irq); | ||
754 | pci_disable_msi(pdev); | ||
755 | goto legacy_int; | ||
756 | } | ||
757 | acb->acb_flags |= ACB_F_MSI_ENABLED; | ||
758 | pr_info("arcmsr%d: msi enabled\n", acb->host->host_no); | ||
759 | return SUCCESS; | ||
760 | legacy_int: | ||
761 | if (request_irq(pdev->irq, arcmsr_do_interrupt, | ||
762 | IRQF_SHARED, "arcmsr", acb)) { | ||
763 | pr_warn("arcmsr%d: request_irq = %d failed!\n", | ||
764 | acb->host->host_no, pdev->irq); | ||
765 | return FAILED; | ||
766 | } | 748 | } |
749 | |||
767 | return SUCCESS; | 750 | return SUCCESS; |
751 | out_free_irq: | ||
752 | while (--i >= 0) | ||
753 | free_irq(pci_irq_vector(pdev, i), acb); | ||
754 | pci_free_irq_vectors(pdev); | ||
755 | return FAILED; | ||
768 | } | 756 | } |
769 | 757 | ||
770 | static int arcmsr_probe(struct pci_dev *pdev, const struct pci_device_id *id) | 758 | static int arcmsr_probe(struct pci_dev *pdev, const struct pci_device_id *id) |
@@ -886,15 +874,9 @@ static void arcmsr_free_irq(struct pci_dev *pdev, | |||
886 | { | 874 | { |
887 | int i; | 875 | int i; |
888 | 876 | ||
889 | if (acb->acb_flags & ACB_F_MSI_ENABLED) { | 877 | for (i = 0; i < acb->vector_count; i++) |
890 | free_irq(pdev->irq, acb); | 878 | free_irq(pci_irq_vector(pdev, i), acb); |
891 | pci_disable_msi(pdev); | 879 | pci_free_irq_vectors(pdev); |
892 | } else if (acb->acb_flags & ACB_F_MSIX_ENABLED) { | ||
893 | for (i = 0; i < acb->msix_vector_count; i++) | ||
894 | free_irq(acb->entries[i].vector, acb); | ||
895 | pci_disable_msix(pdev); | ||
896 | } else | ||
897 | free_irq(pdev->irq, acb); | ||
898 | } | 880 | } |
899 | 881 | ||
900 | static int arcmsr_suspend(struct pci_dev *pdev, pm_message_t state) | 882 | static int arcmsr_suspend(struct pci_dev *pdev, pm_message_t state) |