aboutsummaryrefslogtreecommitdiffstats
path: root/arch/tile/kernel/irq.c
diff options
context:
space:
mode:
Diffstat (limited to 'arch/tile/kernel/irq.c')
-rw-r--r--arch/tile/kernel/irq.c91
1 files changed, 26 insertions, 65 deletions
diff --git a/arch/tile/kernel/irq.c b/arch/tile/kernel/irq.c
index 596c60086930..aa0134db2dd6 100644
--- a/arch/tile/kernel/irq.c
+++ b/arch/tile/kernel/irq.c
@@ -26,7 +26,7 @@
26#define IS_HW_CLEARED 1 26#define IS_HW_CLEARED 1
27 27
28/* 28/*
29 * The set of interrupts we enable for raw_local_irq_enable(). 29 * The set of interrupts we enable for arch_local_irq_enable().
30 * This is initialized to have just a single interrupt that the kernel 30 * This is initialized to have just a single interrupt that the kernel
31 * doesn't actually use as a sentinel. During kernel init, 31 * doesn't actually use as a sentinel. During kernel init,
32 * interrupts are added as the kernel gets prepared to support them. 32 * interrupts are added as the kernel gets prepared to support them.
@@ -61,9 +61,9 @@ static DEFINE_SPINLOCK(available_irqs_lock);
61 61
62#if CHIP_HAS_IPI() 62#if CHIP_HAS_IPI()
63/* Use SPRs to manipulate device interrupts. */ 63/* Use SPRs to manipulate device interrupts. */
64#define mask_irqs(irq_mask) __insn_mtspr(SPR_IPI_MASK_SET_1, irq_mask) 64#define mask_irqs(irq_mask) __insn_mtspr(SPR_IPI_MASK_SET_K, irq_mask)
65#define unmask_irqs(irq_mask) __insn_mtspr(SPR_IPI_MASK_RESET_1, irq_mask) 65#define unmask_irqs(irq_mask) __insn_mtspr(SPR_IPI_MASK_RESET_K, irq_mask)
66#define clear_irqs(irq_mask) __insn_mtspr(SPR_IPI_EVENT_RESET_1, irq_mask) 66#define clear_irqs(irq_mask) __insn_mtspr(SPR_IPI_EVENT_RESET_K, irq_mask)
67#else 67#else
68/* Use HV to manipulate device interrupts. */ 68/* Use HV to manipulate device interrupts. */
69#define mask_irqs(irq_mask) hv_disable_intr(irq_mask) 69#define mask_irqs(irq_mask) hv_disable_intr(irq_mask)
@@ -89,16 +89,16 @@ void tile_dev_intr(struct pt_regs *regs, int intnum)
89 * masked by a previous interrupt. Then, mask out the ones 89 * masked by a previous interrupt. Then, mask out the ones
90 * we're going to handle. 90 * we're going to handle.
91 */ 91 */
92 unsigned long masked = __insn_mfspr(SPR_IPI_MASK_1); 92 unsigned long masked = __insn_mfspr(SPR_IPI_MASK_K);
93 original_irqs = __insn_mfspr(SPR_IPI_EVENT_1) & ~masked; 93 original_irqs = __insn_mfspr(SPR_IPI_EVENT_K) & ~masked;
94 __insn_mtspr(SPR_IPI_MASK_SET_1, original_irqs); 94 __insn_mtspr(SPR_IPI_MASK_SET_K, original_irqs);
95#else 95#else
96 /* 96 /*
97 * Hypervisor performs the equivalent of the Gx code above and 97 * Hypervisor performs the equivalent of the Gx code above and
98 * then puts the pending interrupt mask into a system save reg 98 * then puts the pending interrupt mask into a system save reg
99 * for us to find. 99 * for us to find.
100 */ 100 */
101 original_irqs = __insn_mfspr(SPR_SYSTEM_SAVE_1_3); 101 original_irqs = __insn_mfspr(SPR_SYSTEM_SAVE_K_3);
102#endif 102#endif
103 remaining_irqs = original_irqs; 103 remaining_irqs = original_irqs;
104 104
@@ -176,43 +176,43 @@ void disable_percpu_irq(unsigned int irq)
176EXPORT_SYMBOL(disable_percpu_irq); 176EXPORT_SYMBOL(disable_percpu_irq);
177 177
178/* Mask an interrupt. */ 178/* Mask an interrupt. */
179static void tile_irq_chip_mask(unsigned int irq) 179static void tile_irq_chip_mask(struct irq_data *d)
180{ 180{
181 mask_irqs(1UL << irq); 181 mask_irqs(1UL << d->irq);
182} 182}
183 183
184/* Unmask an interrupt. */ 184/* Unmask an interrupt. */
185static void tile_irq_chip_unmask(unsigned int irq) 185static void tile_irq_chip_unmask(struct irq_data *d)
186{ 186{
187 unmask_irqs(1UL << irq); 187 unmask_irqs(1UL << d->irq);
188} 188}
189 189
190/* 190/*
191 * Clear an interrupt before processing it so that any new assertions 191 * Clear an interrupt before processing it so that any new assertions
192 * will trigger another irq. 192 * will trigger another irq.
193 */ 193 */
194static void tile_irq_chip_ack(unsigned int irq) 194static void tile_irq_chip_ack(struct irq_data *d)
195{ 195{
196 if ((unsigned long)get_irq_chip_data(irq) != IS_HW_CLEARED) 196 if ((unsigned long)irq_data_get_irq_chip_data(d) != IS_HW_CLEARED)
197 clear_irqs(1UL << irq); 197 clear_irqs(1UL << d->irq);
198} 198}
199 199
200/* 200/*
201 * For per-cpu interrupts, we need to avoid unmasking any interrupts 201 * For per-cpu interrupts, we need to avoid unmasking any interrupts
202 * that we disabled via disable_percpu_irq(). 202 * that we disabled via disable_percpu_irq().
203 */ 203 */
204static void tile_irq_chip_eoi(unsigned int irq) 204static void tile_irq_chip_eoi(struct irq_data *d)
205{ 205{
206 if (!(__get_cpu_var(irq_disable_mask) & (1UL << irq))) 206 if (!(__get_cpu_var(irq_disable_mask) & (1UL << d->irq)))
207 unmask_irqs(1UL << irq); 207 unmask_irqs(1UL << d->irq);
208} 208}
209 209
210static struct irq_chip tile_irq_chip = { 210static struct irq_chip tile_irq_chip = {
211 .typename = "tile_irq_chip", 211 .name = "tile_irq_chip",
212 .ack = tile_irq_chip_ack, 212 .irq_ack = tile_irq_chip_ack,
213 .eoi = tile_irq_chip_eoi, 213 .irq_eoi = tile_irq_chip_eoi,
214 .mask = tile_irq_chip_mask, 214 .irq_mask = tile_irq_chip_mask,
215 .unmask = tile_irq_chip_unmask, 215 .irq_unmask = tile_irq_chip_unmask,
216}; 216};
217 217
218void __init init_IRQ(void) 218void __init init_IRQ(void)
@@ -225,7 +225,7 @@ void __cpuinit setup_irq_regs(void)
225 /* Enable interrupt delivery. */ 225 /* Enable interrupt delivery. */
226 unmask_irqs(~0UL); 226 unmask_irqs(~0UL);
227#if CHIP_HAS_IPI() 227#if CHIP_HAS_IPI()
228 raw_local_irq_unmask(INT_IPI_1); 228 arch_local_irq_unmask(INT_IPI_K);
229#endif 229#endif
230} 230}
231 231
@@ -241,14 +241,14 @@ void tile_irq_activate(unsigned int irq, int tile_irq_type)
241 irq_flow_handler_t handle = handle_level_irq; 241 irq_flow_handler_t handle = handle_level_irq;
242 if (tile_irq_type == TILE_IRQ_PERCPU) 242 if (tile_irq_type == TILE_IRQ_PERCPU)
243 handle = handle_percpu_irq; 243 handle = handle_percpu_irq;
244 set_irq_chip_and_handler(irq, &tile_irq_chip, handle); 244 irq_set_chip_and_handler(irq, &tile_irq_chip, handle);
245 245
246 /* 246 /*
247 * Flag interrupts that are hardware-cleared so that ack() 247 * Flag interrupts that are hardware-cleared so that ack()
248 * won't clear them. 248 * won't clear them.
249 */ 249 */
250 if (tile_irq_type == TILE_IRQ_HW_CLEAR) 250 if (tile_irq_type == TILE_IRQ_HW_CLEAR)
251 set_irq_chip_data(irq, (void *)IS_HW_CLEARED); 251 irq_set_chip_data(irq, (void *)IS_HW_CLEARED);
252} 252}
253EXPORT_SYMBOL(tile_irq_activate); 253EXPORT_SYMBOL(tile_irq_activate);
254 254
@@ -262,45 +262,6 @@ void ack_bad_irq(unsigned int irq)
262 * Generic, controller-independent functions: 262 * Generic, controller-independent functions:
263 */ 263 */
264 264
265int show_interrupts(struct seq_file *p, void *v)
266{
267 int i = *(loff_t *) v, j;
268 struct irqaction *action;
269 unsigned long flags;
270
271 if (i == 0) {
272 seq_printf(p, " ");
273 for (j = 0; j < NR_CPUS; j++)
274 if (cpu_online(j))
275 seq_printf(p, "CPU%-8d", j);
276 seq_putc(p, '\n');
277 }
278
279 if (i < NR_IRQS) {
280 raw_spin_lock_irqsave(&irq_desc[i].lock, flags);
281 action = irq_desc[i].action;
282 if (!action)
283 goto skip;
284 seq_printf(p, "%3d: ", i);
285#ifndef CONFIG_SMP
286 seq_printf(p, "%10u ", kstat_irqs(i));
287#else
288 for_each_online_cpu(j)
289 seq_printf(p, "%10u ", kstat_irqs_cpu(i, j));
290#endif
291 seq_printf(p, " %14s", irq_desc[i].chip->typename);
292 seq_printf(p, " %s", action->name);
293
294 for (action = action->next; action; action = action->next)
295 seq_printf(p, ", %s", action->name);
296
297 seq_putc(p, '\n');
298skip:
299 raw_spin_unlock_irqrestore(&irq_desc[i].lock, flags);
300 }
301 return 0;
302}
303
304#if CHIP_HAS_IPI() 265#if CHIP_HAS_IPI()
305int create_irq(void) 266int create_irq(void)
306{ 267{