blob: b830914e32d306263616894fb7cf324f51fb73e0 [file] [log] [blame]
Adrian Bunk88278ca2008-05-19 16:53:02 -07001/*
Sam Ravnborge54f8542011-01-28 22:08:21 +00002 * SS1000/SC2000 interrupt handling.
Linus Torvalds1da177e2005-04-16 15:20:36 -07003 *
4 * Copyright (C) 1997,1998 Jakub Jelinek (jj@sunsite.mff.cuni.cz)
5 * Heavily based on arch/sparc/kernel/irq.c.
6 */
7
Linus Torvalds1da177e2005-04-16 15:20:36 -07008#include <linux/kernel_stat.h>
Linus Torvalds1da177e2005-04-16 15:20:36 -07009#include <linux/seq_file.h>
10
Linus Torvalds1da177e2005-04-16 15:20:36 -070011#include <asm/timer.h>
Linus Torvalds1da177e2005-04-16 15:20:36 -070012#include <asm/traps.h>
13#include <asm/irq.h>
14#include <asm/io.h>
Linus Torvalds1da177e2005-04-16 15:20:36 -070015#include <asm/sbi.h>
16#include <asm/cacheflush.h>
Daniel Hellstrom5fcafb72011-04-21 04:20:23 +000017#include <asm/setup.h>
Linus Torvalds1da177e2005-04-16 15:20:36 -070018
Sam Ravnborg81265fd2008-12-08 01:08:24 -080019#include "kernel.h"
Al Viro32231a62007-07-21 19:18:57 -070020#include "irq.h"
21
Sam Ravnborge54f8542011-01-28 22:08:21 +000022/* Sun4d interrupts fall roughly into two categories. SBUS and
23 * cpu local. CPU local interrupts cover the timer interrupts
24 * and whatnot, and we encode those as normal PILs between
25 * 0 and 15.
Sam Ravnborg6baa9b22011-04-18 11:25:44 +000026 * SBUS interrupts are encodes as a combination of board, level and slot.
Sam Ravnborge54f8542011-01-28 22:08:21 +000027 */
28
Sam Ravnborg6baa9b22011-04-18 11:25:44 +000029struct sun4d_handler_data {
30 unsigned int cpuid; /* target cpu */
31 unsigned int real_irq; /* interrupt level */
32};
33
34
35static unsigned int sun4d_encode_irq(int board, int lvl, int slot)
36{
37 return (board + 1) << 5 | (lvl << 2) | slot;
38}
39
David S. Millerf5f10852008-09-13 22:04:55 -070040struct sun4d_timer_regs {
41 u32 l10_timer_limit;
42 u32 l10_cur_countx;
43 u32 l10_limit_noclear;
44 u32 ctrl;
45 u32 l10_cur_count;
46};
47
48static struct sun4d_timer_regs __iomem *sun4d_timers;
49
Sam Ravnborg6baa9b22011-04-18 11:25:44 +000050#define SUN4D_TIMER_IRQ 10
Sam Ravnborgdb1cdd12011-04-18 11:25:42 +000051
52/* Specify which cpu handle interrupts from which board.
53 * Index is board - value is cpu.
54 */
55static unsigned char board_to_cpu[32];
Linus Torvalds1da177e2005-04-16 15:20:36 -070056
Linus Torvalds1da177e2005-04-16 15:20:36 -070057static int pil_to_sbus[] = {
Sam Ravnborge54f8542011-01-28 22:08:21 +000058 0,
59 0,
60 1,
61 2,
62 0,
63 3,
64 0,
65 4,
66 0,
67 5,
68 0,
69 6,
70 0,
71 7,
72 0,
73 0,
Linus Torvalds1da177e2005-04-16 15:20:36 -070074};
75
David S. Millerf8376e92008-09-13 22:05:25 -070076/* Exported for sun4d_smp.c */
Linus Torvalds1da177e2005-04-16 15:20:36 -070077DEFINE_SPINLOCK(sun4d_imsk_lock);
Linus Torvalds1da177e2005-04-16 15:20:36 -070078
Sam Ravnborg6baa9b22011-04-18 11:25:44 +000079/* SBUS interrupts are encoded integers including the board number
80 * (plus one), the SBUS level, and the SBUS slot number. Sun4D
81 * IRQ dispatch is done by:
82 *
83 * 1) Reading the BW local interrupt table in order to get the bus
84 * interrupt mask.
85 *
86 * This table is indexed by SBUS interrupt level which can be
87 * derived from the PIL we got interrupted on.
88 *
89 * 2) For each bus showing interrupt pending from #1, read the
90 * SBI interrupt state register. This will indicate which slots
91 * have interrupts pending for that SBUS interrupt level.
92 *
93 * 3) Call the genreric IRQ support.
94 */
95static void sun4d_sbus_handler_irq(int sbusl)
Linus Torvalds1da177e2005-04-16 15:20:36 -070096{
Sam Ravnborg6baa9b22011-04-18 11:25:44 +000097 unsigned int bus_mask;
98 unsigned int sbino, slot;
99 unsigned int sbil;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700100
Sam Ravnborg6baa9b22011-04-18 11:25:44 +0000101 bus_mask = bw_get_intr_mask(sbusl) & 0x3ffff;
102 bw_clear_intr_mask(sbusl, bus_mask);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700103
Sam Ravnborg6baa9b22011-04-18 11:25:44 +0000104 sbil = (sbusl << 2);
105 /* Loop for each pending SBI */
106 for (sbino = 0; bus_mask; sbino++) {
107 unsigned int idx, mask;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700108
Sam Ravnborg6baa9b22011-04-18 11:25:44 +0000109 bus_mask >>= 1;
110 if (!(bus_mask & 1))
111 continue;
112 /* XXX This seems to ACK the irq twice. acquire_sbi()
113 * XXX uses swap, therefore this writes 0xf << sbil,
114 * XXX then later release_sbi() will write the individual
115 * XXX bits which were set again.
Linus Torvalds1da177e2005-04-16 15:20:36 -0700116 */
Sam Ravnborg6baa9b22011-04-18 11:25:44 +0000117 mask = acquire_sbi(SBI2DEVID(sbino), 0xf << sbil);
118 mask &= (0xf << sbil);
119
120 /* Loop for each pending SBI slot */
121 idx = 0;
122 slot = (1 << sbil);
123 while (mask != 0) {
124 unsigned int pil;
125 struct irq_bucket *p;
126
127 idx++;
128 slot <<= 1;
129 if (!(mask & slot))
130 continue;
131
132 mask &= ~slot;
133 pil = sun4d_encode_irq(sbino, sbil, idx);
134
135 p = irq_map[pil];
136 while (p) {
137 struct irq_bucket *next;
138
139 next = p->next;
140 generic_handle_irq(p->irq);
141 p = next;
142 }
143 release_sbi(SBI2DEVID(sbino), slot);
144 }
Linus Torvalds1da177e2005-04-16 15:20:36 -0700145 }
Linus Torvalds1da177e2005-04-16 15:20:36 -0700146}
147
Sam Ravnborge54f8542011-01-28 22:08:21 +0000148void sun4d_handler_irq(int pil, struct pt_regs *regs)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700149{
Al Viro0d844382006-10-08 14:30:44 +0100150 struct pt_regs *old_regs;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700151 /* SBUS IRQ level (1 - 7) */
Sam Ravnborgd4d1ec42011-01-22 11:32:15 +0000152 int sbusl = pil_to_sbus[pil];
Sam Ravnborge54f8542011-01-28 22:08:21 +0000153
Linus Torvalds1da177e2005-04-16 15:20:36 -0700154 /* FIXME: Is this necessary?? */
155 cc_get_ipen();
Sam Ravnborge54f8542011-01-28 22:08:21 +0000156
Sam Ravnborgd4d1ec42011-01-22 11:32:15 +0000157 cc_set_iclr(1 << pil);
Sam Ravnborge54f8542011-01-28 22:08:21 +0000158
Al Viro0d844382006-10-08 14:30:44 +0100159 old_regs = set_irq_regs(regs);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700160 irq_enter();
Sam Ravnborg6baa9b22011-04-18 11:25:44 +0000161 if (sbusl == 0) {
162 /* cpu interrupt */
163 struct irq_bucket *p;
164
165 p = irq_map[pil];
166 while (p) {
167 struct irq_bucket *next;
168
169 next = p->next;
170 generic_handle_irq(p->irq);
171 p = next;
172 }
Linus Torvalds1da177e2005-04-16 15:20:36 -0700173 } else {
Sam Ravnborg6baa9b22011-04-18 11:25:44 +0000174 /* SBUS interrupt */
175 sun4d_sbus_handler_irq(sbusl);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700176 }
177 irq_exit();
Al Viro0d844382006-10-08 14:30:44 +0100178 set_irq_regs(old_regs);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700179}
180
Sam Ravnborg6baa9b22011-04-18 11:25:44 +0000181
182static void sun4d_mask_irq(struct irq_data *data)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700183{
Sam Ravnborg6baa9b22011-04-18 11:25:44 +0000184 struct sun4d_handler_data *handler_data = data->handler_data;
185 unsigned int real_irq;
186#ifdef CONFIG_SMP
187 int cpuid = handler_data->cpuid;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700188 unsigned long flags;
Sam Ravnborg6baa9b22011-04-18 11:25:44 +0000189#endif
190 real_irq = handler_data->real_irq;
191#ifdef CONFIG_SMP
Linus Torvalds1da177e2005-04-16 15:20:36 -0700192 spin_lock_irqsave(&sun4d_imsk_lock, flags);
Sam Ravnborg6baa9b22011-04-18 11:25:44 +0000193 cc_set_imsk_other(cpuid, cc_get_imsk_other(cpuid) | (1 << real_irq));
Linus Torvalds1da177e2005-04-16 15:20:36 -0700194 spin_unlock_irqrestore(&sun4d_imsk_lock, flags);
Sam Ravnborg6baa9b22011-04-18 11:25:44 +0000195#else
196 cc_set_imsk(cc_get_imsk() | (1 << real_irq));
197#endif
Linus Torvalds1da177e2005-04-16 15:20:36 -0700198}
199
Sam Ravnborg6baa9b22011-04-18 11:25:44 +0000200static void sun4d_unmask_irq(struct irq_data *data)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700201{
Sam Ravnborg6baa9b22011-04-18 11:25:44 +0000202 struct sun4d_handler_data *handler_data = data->handler_data;
203 unsigned int real_irq;
204#ifdef CONFIG_SMP
205 int cpuid = handler_data->cpuid;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700206 unsigned long flags;
Sam Ravnborg6baa9b22011-04-18 11:25:44 +0000207#endif
208 real_irq = handler_data->real_irq;
Sam Ravnborge54f8542011-01-28 22:08:21 +0000209
Sam Ravnborg6baa9b22011-04-18 11:25:44 +0000210#ifdef CONFIG_SMP
Linus Torvalds1da177e2005-04-16 15:20:36 -0700211 spin_lock_irqsave(&sun4d_imsk_lock, flags);
Sam Ravnborg6baa9b22011-04-18 11:25:44 +0000212 cc_set_imsk_other(cpuid, cc_get_imsk_other(cpuid) | ~(1 << real_irq));
Linus Torvalds1da177e2005-04-16 15:20:36 -0700213 spin_unlock_irqrestore(&sun4d_imsk_lock, flags);
Sam Ravnborg6baa9b22011-04-18 11:25:44 +0000214#else
215 cc_set_imsk(cc_get_imsk() | ~(1 << real_irq));
216#endif
Linus Torvalds1da177e2005-04-16 15:20:36 -0700217}
218
Sam Ravnborg6baa9b22011-04-18 11:25:44 +0000219static unsigned int sun4d_startup_irq(struct irq_data *data)
220{
221 irq_link(data->irq);
222 sun4d_unmask_irq(data);
223 return 0;
224}
225
226static void sun4d_shutdown_irq(struct irq_data *data)
227{
228 sun4d_mask_irq(data);
229 irq_unlink(data->irq);
230}
231
232struct irq_chip sun4d_irq = {
233 .name = "sun4d",
234 .irq_startup = sun4d_startup_irq,
235 .irq_shutdown = sun4d_shutdown_irq,
236 .irq_unmask = sun4d_unmask_irq,
237 .irq_mask = sun4d_mask_irq,
238};
239
Linus Torvalds1da177e2005-04-16 15:20:36 -0700240#ifdef CONFIG_SMP
241static void sun4d_set_cpu_int(int cpu, int level)
242{
243 sun4d_send_ipi(cpu, level);
244}
245
246static void sun4d_clear_ipi(int cpu, int level)
247{
248}
249
250static void sun4d_set_udt(int cpu)
251{
252}
253
254/* Setup IRQ distribution scheme. */
255void __init sun4d_distribute_irqs(void)
256{
David S. Miller71d37212008-08-27 02:50:57 -0700257 struct device_node *dp;
258
Linus Torvalds1da177e2005-04-16 15:20:36 -0700259 int cpuid = cpu_logical_map(1);
260
261 if (cpuid == -1)
262 cpuid = cpu_logical_map(0);
David S. Miller71d37212008-08-27 02:50:57 -0700263 for_each_node_by_name(dp, "sbi") {
264 int devid = of_getintprop_default(dp, "device-id", 0);
265 int board = of_getintprop_default(dp, "board#", 0);
Sam Ravnborgdb1cdd12011-04-18 11:25:42 +0000266 board_to_cpu[board] = cpuid;
David S. Miller71d37212008-08-27 02:50:57 -0700267 set_sbi_tid(devid, cpuid << 3);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700268 }
Sam Ravnborge54f8542011-01-28 22:08:21 +0000269 printk(KERN_ERR "All sbus IRQs directed to CPU%d\n", cpuid);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700270}
271#endif
Sam Ravnborge54f8542011-01-28 22:08:21 +0000272
Linus Torvalds1da177e2005-04-16 15:20:36 -0700273static void sun4d_clear_clock_irq(void)
274{
David S. Millerf5f10852008-09-13 22:04:55 -0700275 sbus_readl(&sun4d_timers->l10_timer_limit);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700276}
277
Linus Torvalds1da177e2005-04-16 15:20:36 -0700278static void sun4d_load_profile_irq(int cpu, unsigned int limit)
279{
280 bw_set_prof_limit(cpu, limit);
281}
282
David S. Millerf5f10852008-09-13 22:04:55 -0700283static void __init sun4d_load_profile_irqs(void)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700284{
David S. Millerf5f10852008-09-13 22:04:55 -0700285 int cpu = 0, mid;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700286
Linus Torvalds1da177e2005-04-16 15:20:36 -0700287 while (!cpu_find_by_instance(cpu, NULL, &mid)) {
288 sun4d_load_profile_irq(mid >> 3, 0);
289 cpu++;
290 }
David S. Millerf5f10852008-09-13 22:04:55 -0700291}
292
Sam Ravnborg1d059952011-02-25 23:01:19 -0800293unsigned int sun4d_build_device_irq(struct platform_device *op,
294 unsigned int real_irq)
295{
Sam Ravnborg1d059952011-02-25 23:01:19 -0800296 struct device_node *dp = op->dev.of_node;
297 struct device_node *io_unit, *sbi = dp->parent;
298 const struct linux_prom_registers *regs;
Sam Ravnborg6baa9b22011-04-18 11:25:44 +0000299 struct sun4d_handler_data *handler_data;
300 unsigned int pil;
301 unsigned int irq;
Sam Ravnborg1d059952011-02-25 23:01:19 -0800302 int board, slot;
303 int sbusl;
304
Sam Ravnborg6baa9b22011-04-18 11:25:44 +0000305 irq = 0;
Sam Ravnborg1d059952011-02-25 23:01:19 -0800306 while (sbi) {
307 if (!strcmp(sbi->name, "sbi"))
308 break;
309
310 sbi = sbi->parent;
311 }
312 if (!sbi)
313 goto err_out;
314
315 regs = of_get_property(dp, "reg", NULL);
316 if (!regs)
317 goto err_out;
318
319 slot = regs->which_io;
320
321 /*
322 * If SBI's parent is not io-unit or the io-unit lacks
323 * a "board#" property, something is very wrong.
324 */
325 if (!sbi->parent || strcmp(sbi->parent->name, "io-unit")) {
326 printk("%s: Error, parent is not io-unit.\n", sbi->full_name);
327 goto err_out;
328 }
329 io_unit = sbi->parent;
330 board = of_getintprop_default(io_unit, "board#", -1);
331 if (board == -1) {
332 printk("%s: Error, lacks board# property.\n", io_unit->full_name);
333 goto err_out;
334 }
335
336 sbusl = pil_to_sbus[real_irq];
337 if (sbusl)
Sam Ravnborg6baa9b22011-04-18 11:25:44 +0000338 pil = sun4d_encode_irq(board, sbusl, slot);
339 else
340 pil = real_irq;
341
342 irq = irq_alloc(real_irq, pil);
343 if (irq == 0)
344 goto err_out;
345
346 handler_data = irq_get_handler_data(irq);
347 if (unlikely(handler_data))
348 goto err_out;
349
350 handler_data = kzalloc(sizeof(struct sun4d_handler_data), GFP_ATOMIC);
351 if (unlikely(!handler_data)) {
352 prom_printf("IRQ: kzalloc(sun4d_handler_data) failed.\n");
353 prom_halt();
354 }
355 handler_data->cpuid = board_to_cpu[board];
356 handler_data->real_irq = real_irq;
357 irq_set_chip_and_handler_name(irq, &sun4d_irq,
358 handle_level_irq, "level");
359 irq_set_handler_data(irq, handler_data);
Sam Ravnborg1d059952011-02-25 23:01:19 -0800360
361err_out:
362 return real_irq;
363}
364
David S. Millerf5f10852008-09-13 22:04:55 -0700365static void __init sun4d_fixup_trap_table(void)
366{
Linus Torvalds1da177e2005-04-16 15:20:36 -0700367#ifdef CONFIG_SMP
David S. Millerf5f10852008-09-13 22:04:55 -0700368 unsigned long flags;
David S. Millerf5f10852008-09-13 22:04:55 -0700369 struct tt_entry *trap_table = &sparc_ttable[SP_TRAP_IRQ1 + (14 - 1)];
Linus Torvalds1da177e2005-04-16 15:20:36 -0700370
David S. Millerf5f10852008-09-13 22:04:55 -0700371 /* Adjust so that we jump directly to smp4d_ticker */
372 lvl14_save[2] += smp4d_ticker - real_irq_entry;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700373
David S. Millerf5f10852008-09-13 22:04:55 -0700374 /* For SMP we use the level 14 ticker, however the bootup code
375 * has copied the firmware's level 14 vector into the boot cpu's
376 * trap table, we must fix this now or we get squashed.
377 */
378 local_irq_save(flags);
379 patchme_maybe_smp_msg[0] = 0x01000000; /* NOP out the branch */
380 trap_table->inst_one = lvl14_save[0];
381 trap_table->inst_two = lvl14_save[1];
382 trap_table->inst_three = lvl14_save[2];
383 trap_table->inst_four = lvl14_save[3];
384 local_flush_cache_all();
385 local_irq_restore(flags);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700386#endif
387}
388
David S. Millerf5f10852008-09-13 22:04:55 -0700389static void __init sun4d_init_timers(irq_handler_t counter_fn)
390{
391 struct device_node *dp;
392 struct resource res;
Sam Ravnborg6baa9b22011-04-18 11:25:44 +0000393 unsigned int irq;
David S. Millerf5f10852008-09-13 22:04:55 -0700394 const u32 *reg;
395 int err;
396
397 dp = of_find_node_by_name(NULL, "cpu-unit");
398 if (!dp) {
399 prom_printf("sun4d_init_timers: Unable to find cpu-unit\n");
400 prom_halt();
401 }
402
403 /* Which cpu-unit we use is arbitrary, we can view the bootbus timer
404 * registers via any cpu's mapping. The first 'reg' property is the
405 * bootbus.
406 */
407 reg = of_get_property(dp, "reg", NULL);
Nicolas Palixc2e27c32008-12-03 21:10:57 -0800408 of_node_put(dp);
David S. Millerf5f10852008-09-13 22:04:55 -0700409 if (!reg) {
410 prom_printf("sun4d_init_timers: No reg property\n");
411 prom_halt();
412 }
413
414 res.start = reg[1];
415 res.end = reg[2] - 1;
416 res.flags = reg[0] & 0xff;
417 sun4d_timers = of_ioremap(&res, BW_TIMER_LIMIT,
418 sizeof(struct sun4d_timer_regs), "user timer");
419 if (!sun4d_timers) {
420 prom_printf("sun4d_init_timers: Can't map timer regs\n");
421 prom_halt();
422 }
423
424 sbus_writel((((1000000/HZ) + 1) << 10), &sun4d_timers->l10_timer_limit);
425
426 master_l10_counter = &sun4d_timers->l10_cur_count;
David S. Millerf5f10852008-09-13 22:04:55 -0700427
Sam Ravnborg6baa9b22011-04-18 11:25:44 +0000428 irq = sun4d_build_device_irq(NULL, SUN4D_TIMER_IRQ);
429 err = request_irq(irq, counter_fn, IRQF_TIMER, "timer", NULL);
David S. Millerf5f10852008-09-13 22:04:55 -0700430 if (err) {
Sam Ravnborge54f8542011-01-28 22:08:21 +0000431 prom_printf("sun4d_init_timers: request_irq() failed with %d\n",
432 err);
David S. Millerf5f10852008-09-13 22:04:55 -0700433 prom_halt();
434 }
435 sun4d_load_profile_irqs();
436 sun4d_fixup_trap_table();
437}
438
Linus Torvalds1da177e2005-04-16 15:20:36 -0700439void __init sun4d_init_sbi_irq(void)
440{
David S. Miller71d37212008-08-27 02:50:57 -0700441 struct device_node *dp;
Daniel Hellstrom5fcafb72011-04-21 04:20:23 +0000442 int target_cpu;
David S. Millerf8376e92008-09-13 22:05:25 -0700443
David S. Millerf8376e92008-09-13 22:05:25 -0700444 target_cpu = boot_cpu_id;
David S. Miller71d37212008-08-27 02:50:57 -0700445 for_each_node_by_name(dp, "sbi") {
446 int devid = of_getintprop_default(dp, "device-id", 0);
447 int board = of_getintprop_default(dp, "board#", 0);
448 unsigned int mask;
449
David S. Millerf8376e92008-09-13 22:05:25 -0700450 set_sbi_tid(devid, target_cpu << 3);
Sam Ravnborgdb1cdd12011-04-18 11:25:42 +0000451 board_to_cpu[board] = target_cpu;
David S. Millerf8376e92008-09-13 22:05:25 -0700452
Linus Torvalds1da177e2005-04-16 15:20:36 -0700453 /* Get rid of pending irqs from PROM */
David S. Miller71d37212008-08-27 02:50:57 -0700454 mask = acquire_sbi(devid, 0xffffffff);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700455 if (mask) {
Sam Ravnborge54f8542011-01-28 22:08:21 +0000456 printk(KERN_ERR "Clearing pending IRQs %08x on SBI %d\n",
457 mask, board);
David S. Miller71d37212008-08-27 02:50:57 -0700458 release_sbi(devid, mask);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700459 }
460 }
461}
462
Linus Torvalds1da177e2005-04-16 15:20:36 -0700463void __init sun4d_init_IRQ(void)
464{
465 local_irq_disable();
466
Linus Torvalds1da177e2005-04-16 15:20:36 -0700467 BTFIXUPSET_CALL(clear_clock_irq, sun4d_clear_clock_irq, BTFIXUPCALL_NORM);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700468 BTFIXUPSET_CALL(load_profile_irq, sun4d_load_profile_irq, BTFIXUPCALL_NORM);
Sam Ravnborgbbdc2662011-02-25 23:00:19 -0800469
Sam Ravnborg6baa9b22011-04-18 11:25:44 +0000470 sparc_irq_config.init_timers = sun4d_init_timers;
Sam Ravnborg1d059952011-02-25 23:01:19 -0800471 sparc_irq_config.build_device_irq = sun4d_build_device_irq;
Sam Ravnborgbbdc2662011-02-25 23:00:19 -0800472
Linus Torvalds1da177e2005-04-16 15:20:36 -0700473#ifdef CONFIG_SMP
474 BTFIXUPSET_CALL(set_cpu_int, sun4d_set_cpu_int, BTFIXUPCALL_NORM);
475 BTFIXUPSET_CALL(clear_cpu_int, sun4d_clear_ipi, BTFIXUPCALL_NOP);
476 BTFIXUPSET_CALL(set_irq_udt, sun4d_set_udt, BTFIXUPCALL_NOP);
477#endif
478 /* Cannot enable interrupts until OBP ticker is disabled. */
479}