input/vmmouse: Update the backdoor call with support for new instructions
[sfrench/cifs-2.6.git] / arch / arm / mach-ks8695 / irq.c
1 // SPDX-License-Identifier: GPL-2.0-or-later
2 /*
3  * arch/arm/mach-ks8695/irq.c
4  *
5  * Copyright (C) 2006 Ben Dooks <ben@simtec.co.uk>
6  * Copyright (C) 2006 Simtec Electronics
7  */
8
9 #include <linux/init.h>
10 #include <linux/module.h>
11 #include <linux/interrupt.h>
12 #include <linux/ioport.h>
13 #include <linux/device.h>
14 #include <linux/io.h>
15
16 #include <mach/hardware.h>
17 #include <asm/irq.h>
18
19 #include <asm/mach/irq.h>
20
21 #include <mach/regs-irq.h>
22 #include <mach/regs-gpio.h>
23
24 static void ks8695_irq_mask(struct irq_data *d)
25 {
26         unsigned long inten;
27
28         inten = __raw_readl(KS8695_IRQ_VA + KS8695_INTEN);
29         inten &= ~(1 << d->irq);
30
31         __raw_writel(inten, KS8695_IRQ_VA + KS8695_INTEN);
32 }
33
34 static void ks8695_irq_unmask(struct irq_data *d)
35 {
36         unsigned long inten;
37
38         inten = __raw_readl(KS8695_IRQ_VA + KS8695_INTEN);
39         inten |= (1 << d->irq);
40
41         __raw_writel(inten, KS8695_IRQ_VA + KS8695_INTEN);
42 }
43
44 static void ks8695_irq_ack(struct irq_data *d)
45 {
46         __raw_writel((1 << d->irq), KS8695_IRQ_VA + KS8695_INTST);
47 }
48
49
50 static struct irq_chip ks8695_irq_level_chip;
51 static struct irq_chip ks8695_irq_edge_chip;
52
53
54 static int ks8695_irq_set_type(struct irq_data *d, unsigned int type)
55 {
56         unsigned long ctrl, mode;
57         unsigned short level_triggered = 0;
58
59         ctrl = __raw_readl(KS8695_GPIO_VA + KS8695_IOPC);
60
61         switch (type) {
62                 case IRQ_TYPE_LEVEL_HIGH:
63                         mode = IOPC_TM_HIGH;
64                         level_triggered = 1;
65                         break;
66                 case IRQ_TYPE_LEVEL_LOW:
67                         mode = IOPC_TM_LOW;
68                         level_triggered = 1;
69                         break;
70                 case IRQ_TYPE_EDGE_RISING:
71                         mode = IOPC_TM_RISING;
72                         break;
73                 case IRQ_TYPE_EDGE_FALLING:
74                         mode = IOPC_TM_FALLING;
75                         break;
76                 case IRQ_TYPE_EDGE_BOTH:
77                         mode = IOPC_TM_EDGE;
78                         break;
79                 default:
80                         return -EINVAL;
81         }
82
83         switch (d->irq) {
84                 case KS8695_IRQ_EXTERN0:
85                         ctrl &= ~IOPC_IOEINT0TM;
86                         ctrl |= IOPC_IOEINT0_MODE(mode);
87                         break;
88                 case KS8695_IRQ_EXTERN1:
89                         ctrl &= ~IOPC_IOEINT1TM;
90                         ctrl |= IOPC_IOEINT1_MODE(mode);
91                         break;
92                 case KS8695_IRQ_EXTERN2:
93                         ctrl &= ~IOPC_IOEINT2TM;
94                         ctrl |= IOPC_IOEINT2_MODE(mode);
95                         break;
96                 case KS8695_IRQ_EXTERN3:
97                         ctrl &= ~IOPC_IOEINT3TM;
98                         ctrl |= IOPC_IOEINT3_MODE(mode);
99                         break;
100                 default:
101                         return -EINVAL;
102         }
103
104         if (level_triggered) {
105                 irq_set_chip_and_handler(d->irq, &ks8695_irq_level_chip,
106                                          handle_level_irq);
107         }
108         else {
109                 irq_set_chip_and_handler(d->irq, &ks8695_irq_edge_chip,
110                                          handle_edge_irq);
111         }
112
113         __raw_writel(ctrl, KS8695_GPIO_VA + KS8695_IOPC);
114         return 0;
115 }
116
117 static struct irq_chip ks8695_irq_level_chip = {
118         .irq_ack        = ks8695_irq_mask,
119         .irq_mask       = ks8695_irq_mask,
120         .irq_unmask     = ks8695_irq_unmask,
121         .irq_set_type   = ks8695_irq_set_type,
122 };
123
124 static struct irq_chip ks8695_irq_edge_chip = {
125         .irq_ack        = ks8695_irq_ack,
126         .irq_mask       = ks8695_irq_mask,
127         .irq_unmask     = ks8695_irq_unmask,
128         .irq_set_type   = ks8695_irq_set_type,
129 };
130
131 void __init ks8695_init_irq(void)
132 {
133         unsigned int irq;
134
135         /* Disable all interrupts initially */
136         __raw_writel(0, KS8695_IRQ_VA + KS8695_INTMC);
137         __raw_writel(0, KS8695_IRQ_VA + KS8695_INTEN);
138
139         for (irq = 0; irq < NR_IRQS; irq++) {
140                 switch (irq) {
141                         /* Level-triggered interrupts */
142                         case KS8695_IRQ_BUS_ERROR:
143                         case KS8695_IRQ_UART_MODEM_STATUS:
144                         case KS8695_IRQ_UART_LINE_STATUS:
145                         case KS8695_IRQ_UART_RX:
146                         case KS8695_IRQ_COMM_TX:
147                         case KS8695_IRQ_COMM_RX:
148                                 irq_set_chip_and_handler(irq,
149                                                          &ks8695_irq_level_chip,
150                                                          handle_level_irq);
151                                 break;
152
153                         /* Edge-triggered interrupts */
154                         default:
155                                 /* clear pending bit */
156                                 ks8695_irq_ack(irq_get_irq_data(irq));
157                                 irq_set_chip_and_handler(irq,
158                                                          &ks8695_irq_edge_chip,
159                                                          handle_edge_irq);
160                 }
161
162                 irq_clear_status_flags(irq, IRQ_NOREQUEST);
163         }
164 }