From: "Chew, Kean Ho" <kean.ho.c...@intel.com>

BayTrail GPIO NORTH, SOUTH and SUS clusters use IRQ48,
49 and 50 respectively. On non-ACPI system, we need
to setup IOAPIC RTE for device that use interrupt
beyond IRQ23.

Signed-off-by: Chew, Kean Ho <kean.ho.c...@intel.com>
Signed-off-by: Chew, Chiau Ee <chiau.ee.c...@intel.com>
Signed-off-by: Sreeju Selvaraj <sreeju.armughanx.selva...@intel.com>
---
 drivers/pinctrl/pinctrl-baytrail.c | 37 +++++++++++++++++++++++++++++++++++++
 1 file changed, 37 insertions(+)

diff --git a/drivers/pinctrl/pinctrl-baytrail.c 
b/drivers/pinctrl/pinctrl-baytrail.c
index 7a313f1..954418f 100644
--- a/drivers/pinctrl/pinctrl-baytrail.c
+++ b/drivers/pinctrl/pinctrl-baytrail.c
@@ -448,6 +448,36 @@ static const struct irq_domain_ops byt_gpio_irq_ops = {
        .map = byt_gpio_irq_map,
 };
 
+#ifdef CONFIG_PINCTRL_BAYTRAIL_DEVICE
+static int byt_gpio_irq_enable(unsigned hwirq, struct platform_device *pdev)
+{
+       struct io_apic_irq_attr irq_attr;
+       struct device *dev = &pdev->dev;
+       /*
+        *  Since PCI BIOS is not able to provide IRQ mapping to
+        *  IRQ24 and onward, we need register to ioapic directly
+        *  and hardcode pci->irq= hwirq
+        */
+       irq_attr.ioapic = mp_find_ioapic(hwirq);
+       if (irq_attr.ioapic < 0) {
+               dev_err(&pdev->dev,
+                       "Unable to locate IOAPIC for IRQ=%d\n", hwirq);
+               return irq_attr.ioapic;
+       }
+       irq_attr.ioapic_pin = hwirq;
+       irq_attr.trigger = 1;   /* level */
+       irq_attr.polarity = 1;  /* active low */
+       io_apic_set_pci_routing(dev, hwirq, &irq_attr);
+       return 0;
+
+}
+#else
+static int byt_gpio_irq_enable(unsigned hwirq, struct platform_device *pdev)
+{
+       return 0;
+}
+#endif
+
 static int byt_gpio_probe(struct platform_device *pdev)
 {
        struct byt_gpio *vg;
@@ -523,6 +553,11 @@ static int byt_gpio_probe(struct platform_device *pdev)
        if (irq_rc && irq_rc->start) {
                hwirq = irq_rc->start;
                gc->to_irq = byt_gpio_to_irq;
+               ret = byt_gpio_irq_enable(hwirq, pdev);
+               if (ret) {
+                       dev_err(&pdev->dev, "failed to add GPIO to APIC\n");
+                       return ret;
+               }
 
                vg->domain = irq_domain_add_linear(NULL, gc->ngpio,
                                                   &byt_gpio_irq_ops, vg);
@@ -534,8 +569,10 @@ static int byt_gpio_probe(struct platform_device *pdev)
                irq_set_handler_data(hwirq, vg);
                irq_set_chained_handler(hwirq, byt_gpio_irq_handler);
 
+#ifndef CONFIG_PINCTRL_BAYTRAIL_DEVICE
                /* Register interrupt handlers for gpio signaled acpi events */
                acpi_gpiochip_request_interrupts(gc);
+#endif
        }
 
        pm_runtime_enable(dev);
-- 
1.9.1

-- 
_______________________________________________
linux-yocto mailing list
linux-yocto@yoctoproject.org
https://lists.yoctoproject.org/listinfo/linux-yocto

Reply via email to