irqchip: i8259: Allow platforms to override poll function
authorPaul Burton <paul.burton@imgtec.com>
Mon, 19 Sep 2016 21:21:19 +0000 (22:21 +0100)
committerRalf Baechle <ralf@linux-mips.org>
Thu, 6 Oct 2016 15:31:00 +0000 (17:31 +0200)
The default i8259 polling function (i8259_irq) is nicely generic but is
fairly costly. Platforms often provide an alternative means of polling
for an i8259 interrupt, and when using the i8259 without device tree
have typically just chained its parent interrupt to their own handler
function. In order to allow for platform-specific polling functions to
be used in cases where the driver is probed via device tree, provide an
i8259_set_poll function that accepts a pointer to an alternative poll
function that will override the default.

Signed-off-by: Paul Burton <paul.burton@imgtec.com>
Acked-by: Thomas Gleixner <tglx@linutronix.de>
Cc: Jason Cooper <jason@lakedaemon.net>
Cc: Marc Zyngier <marc.zyngier@arm.com>
Cc: linux-mips@linux-mips.org
Cc: linux-kernel@vger.kernel.org
Patchwork: https://patchwork.linux-mips.org/patch/14270/
Signed-off-by: Ralf Baechle <ralf@linux-mips.org>
arch/mips/include/asm/i8259.h
drivers/irqchip/irq-i8259.c

index a7fbcd6ed13c4fb41d19609102ea5813feba17c2..b27fcc4ae4741d768b4358d6bd4925e2e2d1fdf8 100644 (file)
@@ -43,6 +43,17 @@ extern void make_8259A_irq(unsigned int irq);
 extern void init_i8259_irqs(void);
 extern int i8259_of_init(struct device_node *node, struct device_node *parent);
 
+/**
+ * i8159_set_poll() - Override the i8259 polling function
+ * @poll: pointer to platform-specific polling function
+ *
+ * Call this to override the generic i8259 polling function, which directly
+ * accesses i8259 registers, with a platform specific one which may be faster
+ * in cases where hardware provides a more optimal means of polling for an
+ * interrupt.
+ */
+extern void i8259_set_poll(int (*poll)(void));
+
 /*
  * Do the traditional i8259 interrupt polling thing.  This is for the few
  * cases where no better interrupt acknowledge method is available and we
index 85897fdc15273f36921428de146a03f279c84de0..1f4a3442342bbd3830c536d18bacb2fecb3c5be2 100644 (file)
@@ -38,6 +38,7 @@ static void disable_8259A_irq(struct irq_data *d);
 static void enable_8259A_irq(struct irq_data *d);
 static void mask_and_ack_8259A(struct irq_data *d);
 static void init_8259A(int auto_eoi);
+static int (*i8259_poll)(void) = i8259_irq;
 
 static struct irq_chip i8259A_chip = {
        .name                   = "XT-PIC",
@@ -51,6 +52,11 @@ static struct irq_chip i8259A_chip = {
  * 8259A PIC functions to handle ISA devices:
  */
 
+void i8259_set_poll(int (*poll)(void))
+{
+       i8259_poll = poll;
+}
+
 /*
  * This contains the irq mask for both 8259A irq controllers,
  */
@@ -355,7 +361,7 @@ void __init init_i8259_irqs(void)
 static void i8259_irq_dispatch(struct irq_desc *desc)
 {
        struct irq_domain *domain = irq_desc_get_handler_data(desc);
-       int hwirq = i8259_irq();
+       int hwirq = i8259_poll();
        unsigned int irq;
 
        if (hwirq < 0)