igb_uio: refactor IRQ enable/disable into own functions

Interrupt setup code in igb_uio has to deal with multiple
types of interrupts and kernel versions. This patch moves
the setup and teardown code into own functions, to make
it more readable.

Signed-off-by: Markus Theil <markus.theil@tu-ilmenau.de>
Tested-by: Markus Theil <markus.theil@tu-ilmenau.de>
Acked-by: Ferruh Yigit <ferruh.yigit@intel.com>
This commit is contained in:
Markus Theil 2017-09-05 14:04:01 +02:00 committed by Ferruh Yigit
parent 535e850aed
commit 0256ec056f

View File

@ -308,6 +308,66 @@ igbuio_pci_release_iomem(struct uio_info *info)
}
}
static int
igbuio_pci_enable_interrupts(struct rte_uio_pci_dev *udev)
{
int err = 0;
#ifdef HAVE_PCI_ENABLE_MSIX
struct msix_entry msix_entry;
#endif
switch (igbuio_intr_mode_preferred) {
case RTE_INTR_MODE_MSIX:
/* Only 1 msi-x vector needed */
#ifdef HAVE_PCI_ENABLE_MSIX
msix_entry.entry = 0;
if (pci_enable_msix(udev->pdev, &msix_entry, 1) == 0) {
dev_dbg(&udev->pdev->dev, "using MSI-X");
udev->info.irq_flags = IRQF_NO_THREAD;
udev->info.irq = msix_entry.vector;
udev->mode = RTE_INTR_MODE_MSIX;
break;
}
#else
if (pci_alloc_irq_vectors(udev->pdev, 1, 1, PCI_IRQ_MSIX) == 1) {
dev_dbg(&udev->pdev->dev, "using MSI-X");
udev->info.irq = pci_irq_vector(udev->pdev, 0);
udev->mode = RTE_INTR_MODE_MSIX;
break;
}
#endif
/* fall back to INTX */
case RTE_INTR_MODE_LEGACY:
if (pci_intx_mask_supported(udev->pdev)) {
dev_dbg(&udev->pdev->dev, "using INTX");
udev->info.irq_flags = IRQF_SHARED | IRQF_NO_THREAD;
udev->info.irq = udev->pdev->irq;
udev->mode = RTE_INTR_MODE_LEGACY;
break;
}
dev_notice(&udev->pdev->dev, "PCI INTX mask not supported\n");
/* fall back to no IRQ */
case RTE_INTR_MODE_NONE:
udev->mode = RTE_INTR_MODE_NONE;
udev->info.irq = 0;
break;
default:
dev_err(&udev->pdev->dev, "invalid IRQ mode %u",
igbuio_intr_mode_preferred);
err = -EINVAL;
}
return err;
}
static void
igbuio_pci_disable_interrupts(struct rte_uio_pci_dev *udev)
{
if (udev->mode == RTE_INTR_MODE_MSIX)
pci_disable_msix(udev->pdev);
}
static int
igbuio_setup_bars(struct pci_dev *dev, struct uio_info *info)
{
@ -356,9 +416,6 @@ static int
igbuio_pci_probe(struct pci_dev *dev, const struct pci_device_id *id)
{
struct rte_uio_pci_dev *udev;
#ifdef HAVE_PCI_ENABLE_MSIX
struct msix_entry msix_entry;
#endif
dma_addr_t map_dma_addr;
void *map_addr;
int err;
@ -413,48 +470,9 @@ igbuio_pci_probe(struct pci_dev *dev, const struct pci_device_id *id)
udev->info.priv = udev;
udev->pdev = dev;
switch (igbuio_intr_mode_preferred) {
case RTE_INTR_MODE_MSIX:
/* Only 1 msi-x vector needed */
#ifdef HAVE_PCI_ENABLE_MSIX
msix_entry.entry = 0;
if (pci_enable_msix(dev, &msix_entry, 1) == 0) {
dev_dbg(&dev->dev, "using MSI-X");
udev->info.irq_flags = IRQF_NO_THREAD;
udev->info.irq = msix_entry.vector;
udev->mode = RTE_INTR_MODE_MSIX;
break;
}
#else
if (pci_alloc_irq_vectors(dev, 1, 1, PCI_IRQ_MSIX) == 1) {
dev_dbg(&dev->dev, "using MSI-X");
udev->info.irq = pci_irq_vector(dev, 0);
udev->mode = RTE_INTR_MODE_MSIX;
break;
}
#endif
/* fall back to INTX */
case RTE_INTR_MODE_LEGACY:
if (pci_intx_mask_supported(dev)) {
dev_dbg(&dev->dev, "using INTX");
udev->info.irq_flags = IRQF_SHARED | IRQF_NO_THREAD;
udev->info.irq = dev->irq;
udev->mode = RTE_INTR_MODE_LEGACY;
break;
}
dev_notice(&dev->dev, "PCI INTX mask not supported\n");
/* fall back to no IRQ */
case RTE_INTR_MODE_NONE:
udev->mode = RTE_INTR_MODE_NONE;
udev->info.irq = 0;
break;
default:
dev_err(&dev->dev, "invalid IRQ mode %u",
igbuio_intr_mode_preferred);
err = -EINVAL;
err = igbuio_pci_enable_interrupts(udev);
if (err != 0)
goto fail_release_iomem;
}
err = sysfs_create_group(&dev->dev.kobj, &dev_attr_grp);
if (err != 0)
@ -497,8 +515,7 @@ igbuio_pci_probe(struct pci_dev *dev, const struct pci_device_id *id)
sysfs_remove_group(&dev->dev.kobj, &dev_attr_grp);
fail_release_iomem:
igbuio_pci_release_iomem(&udev->info);
if (udev->mode == RTE_INTR_MODE_MSIX)
pci_disable_msix(udev->pdev);
igbuio_pci_disable_interrupts(udev);
pci_disable_device(dev);
fail_free:
kfree(udev);
@ -514,8 +531,7 @@ igbuio_pci_remove(struct pci_dev *dev)
sysfs_remove_group(&dev->dev.kobj, &dev_attr_grp);
uio_unregister_device(&udev->info);
igbuio_pci_release_iomem(&udev->info);
if (udev->mode == RTE_INTR_MODE_MSIX)
pci_disable_msix(dev);
igbuio_pci_disable_interrupts(udev);
pci_disable_device(dev);
pci_set_drvdata(dev, NULL);
kfree(udev);