/* Propagate PCI IRQ# */ static int vlv2_pci_enable_irq(struct pci_dev *pdev) { u8 ir_val, dev; void __iomem *ilb_mem; struct io_apic_irq_attr irq_attr; ilb_mem = ioremap_nocache(ILB_BASE, ILB_SIZE); if (ilb_mem == NULL) { pr_err("%s(): can't map ILB_BASE(0x%x)\n", __func__, ILB_BASE); return -EIO; } dev = PCI_DEV_NUM(pdev->devfn); ir_val = ioread8(ilb_mem + ILB_IR + PCI_DEV_NUM(pdev->devfn) * 2); iounmap(ilb_mem); /* map INTA# only */ pdev->irq = PIRQ2IRQ(IR_INTA(ir_val)); pci_write_config_byte(pdev, PCI_INTERRUPT_LINE, pdev->irq); irq_attr.ioapic = mp_find_ioapic(pdev->irq); irq_attr.ioapic_pin = pdev->irq; irq_attr.trigger = 1; /* level */ irq_attr.polarity = 1; /* active low */ io_apic_set_pci_routing(&pdev->dev, pdev->irq, &irq_attr); return 0; }
static inline int byt_program_ioapic(int irq, int trigger, int polarity) { struct io_apic_irq_attr irq_attr; int ioapic; ioapic = mp_find_ioapic(irq); if (ioapic < 0) return -EINVAL; irq_attr.ioapic = ioapic; irq_attr.ioapic_pin = irq; irq_attr.trigger = trigger; irq_attr.polarity = polarity; return io_apic_set_pci_routing(NULL, irq, &irq_attr); }
static int handle_mrfl_dev_ioapic(int irq) { int ret = 0; int ioapic; struct io_apic_irq_attr irq_attr; ioapic = mp_find_ioapic(irq); if (ioapic >= 0) { irq_attr.ioapic = ioapic; irq_attr.ioapic_pin = irq; irq_attr.trigger = 1; irq_attr.polarity = 0; /* Active high */ io_apic_set_pci_routing(NULL, irq, &irq_attr); } else { pr_warn("can not find interrupt %d in ioapic\n", irq); ret = -EINVAL; } return ret; }