1 /* Copyright (C) 2013 Jonas Jensen <jonas.jensen@gmail.com>
2 * This program is free software; you can redistribute it and/or modify it
3 * under the terms of the GNU General Public License as published by the
4 * Free Software Foundation; either version 2 of the License,
5 * or (at your option) any later version. */
7 #include <linux/init.h>
9 #include <linux/ioport.h>
10 #include <linux/stddef.h>
11 #include <linux/list.h>
12 #include <linux/sched.h>
14 #include <asm/mach/irq.h>
15 #include <mach/hardware.h>
17 static void moxart_ack_irq(unsigned int irq
)
20 __raw_writel(1 << irq
,
21 IRQ_CLEAR(IO_ADDRESS(MOXART_INTERRUPT_BASE
)));
24 __raw_writel(1 << irq
,
25 FIQ_CLEAR(IO_ADDRESS(MOXART_INTERRUPT_BASE
)));
29 static void moxart_mask_irq(unsigned int irq
)
33 mask
= __raw_readl(IRQ_MASK(IO_ADDRESS(MOXART_INTERRUPT_BASE
)));
35 __raw_writel(mask
, IRQ_MASK(IO_ADDRESS(MOXART_INTERRUPT_BASE
)));
39 mask
= __raw_readl(FIQ_MASK(IO_ADDRESS(MOXART_INTERRUPT_BASE
)));
41 __raw_writel(mask
, FIQ_MASK(IO_ADDRESS(MOXART_INTERRUPT_BASE
)));
45 static void moxart_unmask_irq(unsigned int irq
)
49 mask
= __raw_readl(IRQ_MASK(IO_ADDRESS(MOXART_INTERRUPT_BASE
)));
51 __raw_writel(mask
, IRQ_MASK(IO_ADDRESS(MOXART_INTERRUPT_BASE
)));
55 mask
= __raw_readl(FIQ_MASK(IO_ADDRESS(MOXART_INTERRUPT_BASE
)));
57 __raw_writel(mask
, FIQ_MASK(IO_ADDRESS(MOXART_INTERRUPT_BASE
)));
61 void moxart_generic_set_generic(unsigned int base
, unsigned int irq
,
65 mask
= __raw_readl(base
);
66 (low
) ? (mask
|= (1 << irq
)) : (mask
&= ~(1 << irq
));
67 __raw_writel(mask
, base
);
70 /*void __init moxart_int_set_irq(unsigned int irq, int mode, int level)*/
71 void moxart_int_set_irq(unsigned int irq
, int mode
, int level
)
74 moxart_generic_set_generic(
75 IRQ_TMODE(IO_ADDRESS(MOXART_INTERRUPT_BASE
)),
77 moxart_generic_set_generic(
78 IRQ_TLEVEL(IO_ADDRESS(MOXART_INTERRUPT_BASE
)),
83 moxart_generic_set_generic(
84 FIQ_TMODE(IO_ADDRESS(MOXART_INTERRUPT_BASE
)),
86 moxart_generic_set_generic(
87 FIQ_TLEVEL(IO_ADDRESS(MOXART_INTERRUPT_BASE
)),
92 static struct irq_chip moxart_irq_chip
= {
94 .ack
= moxart_ack_irq
,
95 .mask
= moxart_mask_irq
,
96 .unmask
= moxart_unmask_irq
,
99 static struct resource irq_resource
= {
100 .name
= "irq_handler",
101 .start
= IO_ADDRESS(MOXART_INTERRUPT_BASE
),
102 .end
= IO_ADDRESS(FIQ_STATUS(MOXART_INTERRUPT_BASE
)) + 4,
105 void __init
moxart_init_irq(void)
107 unsigned int mode
= 0, level
= 0, irq
;
111 request_resource(&iomem_resource
, &irq_resource
);
113 for (irq
= 0; irq
< NR_IRQS
; irq
++) {
114 set_irq_chip(irq
, &moxart_irq_chip
);
115 if (irq
== IRQ_TIMER1
|| irq
== IRQ_TIMER2
||
117 set_irq_handler(irq
, handle_edge_irq
);
121 set_irq_handler(irq
, handle_level_irq
);
123 set_irq_flags(irq
, IRQF_VALID
| IRQF_PROBE
);
125 /* pr_info("IRQ chip/handler/flags assign finished\r\n"); */
127 __raw_writel(0, IRQ_MASK(IO_ADDRESS(MOXART_INTERRUPT_BASE
)));
128 __raw_writel(0, FIQ_MASK(IO_ADDRESS(MOXART_INTERRUPT_BASE
)));
130 __raw_writel(0xffffffff, IRQ_CLEAR(IO_ADDRESS(MOXART_INTERRUPT_BASE
)));
131 __raw_writel(0xffffffff, FIQ_CLEAR(IO_ADDRESS(MOXART_INTERRUPT_BASE
)));
132 /* pr_info("IRQ init finished\n"); */
134 __raw_writel(mode
, IRQ_TMODE(IO_ADDRESS(MOXART_INTERRUPT_BASE
)));
135 __raw_writel(level
, IRQ_TLEVEL(IO_ADDRESS(MOXART_INTERRUPT_BASE
)));
136 __raw_writel(0, FIQ_TMODE(IO_ADDRESS(MOXART_INTERRUPT_BASE
)));
137 __raw_writel(0, FIQ_TLEVEL(IO_ADDRESS(MOXART_INTERRUPT_BASE
)));
138 /* pr_info("IRQ mode/level setup finished\n"); */
140 pr_info("MOXART CPU IRQ: init_irq finished\n");