8ace2a32b98b423a4725ff4e0767333fdff249b2
[linux-flexiantxendom0-3.2.10.git] / arch / mips / sibyte / sb1250 / irq.c
1 /*
2  * Copyright (C) 2000, 2001 Broadcom Corporation
3  *
4  * This program is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU General Public License
6  * as published by the Free Software Foundation; either version 2
7  * of the License, or (at your option) any later version.
8  *
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12  * GNU General Public License for more details.
13  *
14  * You should have received a copy of the GNU General Public License
15  * along with this program; if not, write to the Free Software
16  * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
17  */
18 #include <linux/config.h>
19 #include <linux/kernel.h>
20 #include <linux/init.h>
21 #include <linux/linkage.h>
22 #include <linux/interrupt.h>
23 #include <linux/spinlock.h>
24 #include <linux/mm.h>
25 #include <linux/slab.h>
26
27 #include <asm/errno.h>
28 #include <asm/signal.h>
29 #include <asm/system.h>
30 #include <asm/ptrace.h>
31
32 #include <asm/sibyte/sb1250_regs.h>
33 #include <asm/sibyte/sb1250_int.h>
34 #include <asm/sibyte/sb1250_uart.h>
35 #include <asm/sibyte/sb1250_scd.h>
36 #include <asm/sibyte/sb1250.h>
37 #include <asm/sibyte/64bit.h>
38
39 /*
40  * These are the routines that handle all the low level interrupt stuff.
41  * Actions handled here are: initialization of the interrupt map, requesting of
42  * interrupt lines by handlers, dispatching if interrupts to handlers, probing
43  * for interrupt lines
44  */
45
46
47 #define shutdown_sb1250_irq     disable_sb1250_irq
48 static void end_sb1250_irq(unsigned int irq);
49 static void enable_sb1250_irq(unsigned int irq);
50 static void disable_sb1250_irq(unsigned int irq);
51 static unsigned int startup_sb1250_irq(unsigned int irq);
52 static void ack_sb1250_irq(unsigned int irq);
53 #ifdef CONFIG_SMP
54 static void sb1250_set_affinity(unsigned int irq, unsigned long mask);
55 #endif
56
57 #ifdef CONFIG_SIBYTE_HAS_LDT
58 extern unsigned long ldt_eoi_space;
59 #endif
60
61 #ifdef CONFIG_KGDB
62 extern void breakpoint(void);
63 extern void set_debug_traps(void);
64
65 /* kgdb is on when configured.  Pass "nokgdb" kernel arg to turn it off */
66 static int kgdb_flag = 1;
67 static int __init nokgdb(char *str)
68 {
69         kgdb_flag = 0;
70 }
71 __setup("nokgdb", nokgdb);
72 #endif
73
74 static struct hw_interrupt_type sb1250_irq_type = {
75         "SB1250-IMR",
76         startup_sb1250_irq,
77         shutdown_sb1250_irq,
78         enable_sb1250_irq,
79         disable_sb1250_irq,
80         ack_sb1250_irq,
81         end_sb1250_irq,
82 #ifdef CONFIG_SMP
83         sb1250_set_affinity
84 #else
85         NULL
86 #endif
87 };
88
89 /* Store the CPU id (not the logical number) */
90 int sb1250_irq_owner[SB1250_NR_IRQS];
91
92 spinlock_t sb1250_imr_lock = SPIN_LOCK_UNLOCKED;
93
94 void sb1250_mask_irq(int cpu, int irq)
95 {
96         unsigned long flags;
97         u64 cur_ints;
98
99         spin_lock_irqsave(&sb1250_imr_lock, flags);
100         cur_ints = __in64(KSEG1 + A_IMR_MAPPER(cpu) + R_IMR_INTERRUPT_MASK);
101         cur_ints |= (((u64) 1) << irq);
102         __out64(cur_ints, KSEG1 + A_IMR_MAPPER(cpu) + R_IMR_INTERRUPT_MASK);
103         spin_unlock_irqrestore(&sb1250_imr_lock, flags);
104 }
105
106 void sb1250_unmask_irq(int cpu, int irq)
107 {
108         unsigned long flags;
109         u64 cur_ints;
110
111         spin_lock_irqsave(&sb1250_imr_lock, flags);
112         cur_ints = __in64(KSEG1 + A_IMR_MAPPER(cpu) + R_IMR_INTERRUPT_MASK);
113         cur_ints &= ~(((u64) 1) << irq);
114         __out64(cur_ints, KSEG1 + A_IMR_MAPPER(cpu) + R_IMR_INTERRUPT_MASK);
115         spin_unlock_irqrestore(&sb1250_imr_lock, flags);
116 }
117
118 #ifdef CONFIG_SMP
119 static void sb1250_set_affinity(unsigned int irq, unsigned long mask)
120 {
121         int i = 0, old_cpu, cpu, int_on;
122         u64 cur_ints;
123         irq_desc_t *desc = irq_desc + irq;
124         unsigned int flags;
125
126         while (mask) {
127                 if (mask & 1) {
128                         mask >>= 1;
129                         break;
130                 }
131                 mask >>= 1;
132                 i++;
133         }
134
135         if (mask) {
136                 printk("attempted to set irq affinity for irq %d to multiple CPUs\n", irq);
137                 return;
138         }
139
140         /* Convert logical CPU to physical CPU */
141         cpu = cpu_logical_map(i);
142
143         /* Protect against other affinity changers and IMR manipulation */
144         spin_lock_irqsave(&desc->lock, flags);
145         spin_lock(&sb1250_imr_lock);
146
147         /* Swizzle each CPU's IMR (but leave the IP selection alone) */
148         old_cpu = sb1250_irq_owner[irq];
149         cur_ints = __in64(KSEG1 + A_IMR_MAPPER(old_cpu) + R_IMR_INTERRUPT_MASK);
150         int_on = !(cur_ints & (((u64) 1) << irq));
151         if (int_on) {
152                 /* If it was on, mask it */
153                 cur_ints |= (((u64) 1) << irq);
154                 __out64(cur_ints, KSEG1 + A_IMR_MAPPER(old_cpu) + R_IMR_INTERRUPT_MASK);
155         }
156         sb1250_irq_owner[irq] = cpu;
157         if (int_on) {
158                 /* unmask for the new CPU */
159                 cur_ints = __in64(KSEG1 + A_IMR_MAPPER(cpu) + R_IMR_INTERRUPT_MASK);
160                 cur_ints &= ~(((u64) 1) << irq);
161                 __out64(cur_ints, KSEG1 + A_IMR_MAPPER(cpu) + R_IMR_INTERRUPT_MASK);
162         }
163         spin_unlock(&sb1250_imr_lock);
164         spin_unlock_irqrestore(&desc->lock, flags);
165 }
166 #endif
167
168
169 /* Defined in arch/mips/sibyte/sb1250/irq_handler.S */
170 extern void sb1250_irq_handler(void);
171
172 /*****************************************************************************/
173
174 static unsigned int startup_sb1250_irq(unsigned int irq)
175 {
176         sb1250_unmask_irq(sb1250_irq_owner[irq], irq);
177
178         return 0;               /* never anything pending */
179 }
180
181
182 static void disable_sb1250_irq(unsigned int irq)
183 {
184         sb1250_mask_irq(sb1250_irq_owner[irq], irq);
185 }
186
187 static void enable_sb1250_irq(unsigned int irq)
188 {
189         sb1250_unmask_irq(sb1250_irq_owner[irq], irq);
190 }
191
192
193 static void ack_sb1250_irq(unsigned int irq)
194 {
195 #ifdef CONFIG_SIBYTE_HAS_LDT
196         u64 pending;
197
198         /*
199          * If the interrupt was an HT interrupt, now is the time to
200          * clear it.  NOTE: we assume the HT bridge was set up to
201          * deliver the interrupts to all CPUs (which makes affinity
202          * changing easier for us)
203          */
204         pending = in64(KSEG1 + A_IMR_REGISTER(sb1250_irq_owner[irq],
205                                               R_IMR_LDT_INTERRUPT));
206         pending &= ((u64)1 << (irq));
207         if (pending) {
208                 int i;
209                 for (i=0; i<smp_num_cpus; i++) {
210                         /*
211                          * Clear for all CPUs so an affinity switch
212                          * doesn't find an old status
213                          */
214                         out64(pending, 
215                               KSEG1+A_IMR_REGISTER(cpu_logical_map(i),
216                                                    R_IMR_LDT_INTERRUPT_CLR));
217                 }
218
219                 /*
220                  * Generate EOI.  For Pass 1 parts, EOI is a nop.  For
221                  * Pass 2, the LDT world may be edge-triggered, but
222                  * this EOI shouldn't hurt.  If they are
223                  * level-sensitive, the EOI is required.
224                  */
225                 *(uint32_t *)(ldt_eoi_space+(irq<<16)+(7<<2)) = 0;
226         }
227 #endif
228         sb1250_mask_irq(sb1250_irq_owner[irq], irq);
229 }
230
231
232 static void end_sb1250_irq(unsigned int irq)
233 {
234         if (!(irq_desc[irq].status & (IRQ_DISABLED | IRQ_INPROGRESS))) {
235                 sb1250_unmask_irq(sb1250_irq_owner[irq], irq);
236         }
237 }
238
239
240 void __init init_sb1250_irqs(void)
241 {
242         int i;
243
244         for (i = 0; i < NR_IRQS; i++) {
245                 irq_desc[i].status = IRQ_DISABLED;
246                 irq_desc[i].action = 0;
247                 irq_desc[i].depth = 1;
248                 if (i < SB1250_NR_IRQS) {
249                         irq_desc[i].handler = &sb1250_irq_type;
250                         sb1250_irq_owner[i] = 0;
251                 } else {
252                         irq_desc[i].handler = &no_irq_type;
253                 }
254         }
255 }
256
257
258 static irqreturn_t  sb1250_dummy_handler(int irq, void *dev_id,
259         struct pt_regs *regs)
260 {
261         return IRQ_NONE;
262 }
263
264 static struct irqaction sb1250_dummy_action = {
265         .handler = sb1250_dummy_handler,
266         .flags   = 0,
267         .mask    = 0,
268         .name    = "sb1250-private",
269         .next    = NULL,
270         .dev_id  = 0
271 };
272
273 int sb1250_steal_irq(int irq)
274 {
275         irq_desc_t *desc = irq_desc + irq;
276         unsigned long flags;
277         int retval = 0;
278
279         if (irq >= SB1250_NR_IRQS)
280                 return -EINVAL;
281
282         spin_lock_irqsave(&desc->lock,flags);
283         /* Don't allow sharing at all for these */
284         if (desc->action != NULL)
285                 retval = -EBUSY;
286         else {
287                 desc->action = &sb1250_dummy_action;
288                 desc->depth = 0;
289         }
290         spin_unlock_irqrestore(&desc->lock,flags);
291         return 0;
292 }
293
294 /*
295  *  init_IRQ is called early in the boot sequence from init/main.c.  It
296  *  is responsible for setting up the interrupt mapper and installing the
297  *  handler that will be responsible for dispatching interrupts to the
298  *  "right" place.
299  */
300 /*
301  * For now, map all interrupts to IP[2].  We could save
302  * some cycles by parceling out system interrupts to different
303  * IP lines, but keep it simple for bringup.  We'll also direct
304  * all interrupts to a single CPU; we should probably route
305  * PCI and LDT to one cpu and everything else to the other
306  * to balance the load a bit.
307  *
308  * On the second cpu, everything is set to IP5, which is
309  * ignored, EXCEPT the mailbox interrupt.  That one is
310  * set to IP[2] so it is handled.  This is needed so we
311  * can do cross-cpu function calls, as requred by SMP
312  */
313
314 #define IMR_IP2_VAL     K_INT_MAP_I0
315 #define IMR_IP3_VAL     K_INT_MAP_I1
316 #define IMR_IP4_VAL     K_INT_MAP_I2
317 #define IMR_IP5_VAL     K_INT_MAP_I3
318 #define IMR_IP6_VAL     K_INT_MAP_I4
319
320 void __init init_IRQ(void)
321 {
322
323         unsigned int i;
324         u64 tmp;
325         unsigned int imask = STATUSF_IP4 | STATUSF_IP3 | STATUSF_IP2 |
326                 STATUSF_IP1 | STATUSF_IP0;
327
328         /* Default everything to IP2 */
329         for (i = 0; i < SB1250_NR_IRQS; i++) {  /* was I0 */
330                 out64(IMR_IP2_VAL,
331                       KSEG1 + A_IMR_REGISTER(0,
332                                              R_IMR_INTERRUPT_MAP_BASE) +
333                       (i << 3));
334                 out64(IMR_IP2_VAL,
335                       KSEG1 + A_IMR_REGISTER(1,
336                                              R_IMR_INTERRUPT_MAP_BASE) +
337                       (i << 3));
338         }
339
340         init_sb1250_irqs();
341
342         /*
343          * Map the high 16 bits of the mailbox registers to IP[3], for
344          * inter-cpu messages
345          */
346         /* Was I1 */
347         out64(IMR_IP3_VAL, KSEG1 + A_IMR_REGISTER(0, R_IMR_INTERRUPT_MAP_BASE) +
348                            (K_INT_MBOX_0 << 3));
349         out64(IMR_IP3_VAL, KSEG1 + A_IMR_REGISTER(1, R_IMR_INTERRUPT_MAP_BASE) +
350                            (K_INT_MBOX_0 << 3));
351
352         /* Clear the mailboxes.  The firmware may leave them dirty */
353         out64(0xffffffffffffffff,
354               KSEG1 + A_IMR_REGISTER(0, R_IMR_MAILBOX_CLR_CPU));
355         out64(0xffffffffffffffff,
356               KSEG1 + A_IMR_REGISTER(1, R_IMR_MAILBOX_CLR_CPU));
357
358         /* Mask everything except the mailbox registers for both cpus */
359         tmp = ~((u64) 0) ^ (((u64) 1) << K_INT_MBOX_0);
360         out64(tmp, KSEG1 + A_IMR_REGISTER(0, R_IMR_INTERRUPT_MASK));
361         out64(tmp, KSEG1 + A_IMR_REGISTER(1, R_IMR_INTERRUPT_MASK));
362
363         sb1250_steal_irq(K_INT_MBOX_0);
364
365         /*
366          * Note that the timer interrupts are also mapped, but this is
367          * done in sb1250_time_init()
368          */
369
370 #ifdef CONFIG_BCM1250_PROF
371         imask |= STATUSF_IP7;
372 #endif
373 #ifdef CONFIG_KGDB
374         imask |= STATUSF_IP6;
375 #endif
376         /* Enable necessary IPs, disable the rest */
377         change_c0_status(ST0_IM, imask);
378         set_except_vector(0, sb1250_irq_handler);
379
380 #ifdef CONFIG_KGDB
381         if (kgdb_flag) {
382                 /* Setup uart 1 settings, mapper */
383                 out64(M_DUART_IMR_BRK, KSEG1 + A_DUART + R_DUART_IMR_B);
384
385                 out64(IMR_IP6_VAL,
386                         KSEG1 + A_IMR_REGISTER(0, R_IMR_INTERRUPT_MAP_BASE) + (K_INT_UART_1<<3));
387                 tmp = in64(KSEG1 + A_IMR_REGISTER(0, R_IMR_INTERRUPT_MASK));
388                 tmp &= ~(1<<K_INT_UART_1);
389                 out64(tmp, KSEG1 + A_IMR_REGISTER(0, R_IMR_INTERRUPT_MASK));
390
391                 set_debug_traps();
392                 breakpoint();
393         }
394 #endif
395 }
396
397 #ifdef CONFIG_KGDB
398
399 #include <linux/delay.h>
400
401 extern void set_async_breakpoint(unsigned int epc);
402
403 #define duart_out(reg, val)     out64(val, KSEG1 + A_DUART_CHANREG(1,reg))
404 #define duart_in(reg)           in64(KSEG1 + A_DUART_CHANREG(1,reg))
405
406 void sb1250_kgdb_interrupt(struct pt_regs *regs)
407 {
408         /*
409          * Clear break-change status (allow some time for the remote
410          * host to stop the break, since we would see another
411          * interrupt on the end-of-break too)
412          */
413         mdelay(500);
414         duart_out(R_DUART_CMD, V_DUART_MISC_CMD_RESET_BREAK_INT |
415                                 M_DUART_RX_EN | M_DUART_TX_EN);
416         if (!user_mode(regs))
417                 set_async_breakpoint(regs->cp0_epc);
418 }
419 #endif  /* CONFIG_KGDB */