diff options
Diffstat (limited to 'arch/mips/sibyte/sb1250/irq.c')
-rw-r--r-- | arch/mips/sibyte/sb1250/irq.c | 121 |
1 files changed, 58 insertions, 63 deletions
diff --git a/arch/mips/sibyte/sb1250/irq.c b/arch/mips/sibyte/sb1250/irq.c index 2725b263cced..589537bfcc3d 100644 --- a/arch/mips/sibyte/sb1250/irq.c +++ b/arch/mips/sibyte/sb1250/irq.c | |||
@@ -53,7 +53,7 @@ static void disable_sb1250_irq(unsigned int irq); | |||
53 | static unsigned int startup_sb1250_irq(unsigned int irq); | 53 | static unsigned int startup_sb1250_irq(unsigned int irq); |
54 | static void ack_sb1250_irq(unsigned int irq); | 54 | static void ack_sb1250_irq(unsigned int irq); |
55 | #ifdef CONFIG_SMP | 55 | #ifdef CONFIG_SMP |
56 | static void sb1250_set_affinity(unsigned int irq, unsigned long mask); | 56 | static void sb1250_set_affinity(unsigned int irq, cpumask_t mask); |
57 | #endif | 57 | #endif |
58 | 58 | ||
59 | #ifdef CONFIG_SIBYTE_HAS_LDT | 59 | #ifdef CONFIG_SIBYTE_HAS_LDT |
@@ -71,17 +71,15 @@ extern char sb1250_duart_present[]; | |||
71 | #endif | 71 | #endif |
72 | 72 | ||
73 | static struct hw_interrupt_type sb1250_irq_type = { | 73 | static struct hw_interrupt_type sb1250_irq_type = { |
74 | "SB1250-IMR", | 74 | .typename = "SB1250-IMR", |
75 | startup_sb1250_irq, | 75 | .startup = startup_sb1250_irq, |
76 | shutdown_sb1250_irq, | 76 | .shutdown = shutdown_sb1250_irq, |
77 | enable_sb1250_irq, | 77 | .enable = enable_sb1250_irq, |
78 | disable_sb1250_irq, | 78 | .disable = disable_sb1250_irq, |
79 | ack_sb1250_irq, | 79 | .ack = ack_sb1250_irq, |
80 | end_sb1250_irq, | 80 | .end = end_sb1250_irq, |
81 | #ifdef CONFIG_SMP | 81 | #ifdef CONFIG_SMP |
82 | sb1250_set_affinity | 82 | .set_affinity = sb1250_set_affinity |
83 | #else | ||
84 | NULL | ||
85 | #endif | 83 | #endif |
86 | }; | 84 | }; |
87 | 85 | ||
@@ -96,11 +94,11 @@ void sb1250_mask_irq(int cpu, int irq) | |||
96 | u64 cur_ints; | 94 | u64 cur_ints; |
97 | 95 | ||
98 | spin_lock_irqsave(&sb1250_imr_lock, flags); | 96 | spin_lock_irqsave(&sb1250_imr_lock, flags); |
99 | cur_ints = __bus_readq(IOADDR(A_IMR_MAPPER(cpu) + | 97 | cur_ints = ____raw_readq(IOADDR(A_IMR_MAPPER(cpu) + |
100 | R_IMR_INTERRUPT_MASK)); | 98 | R_IMR_INTERRUPT_MASK)); |
101 | cur_ints |= (((u64) 1) << irq); | 99 | cur_ints |= (((u64) 1) << irq); |
102 | __bus_writeq(cur_ints, IOADDR(A_IMR_MAPPER(cpu) + | 100 | ____raw_writeq(cur_ints, IOADDR(A_IMR_MAPPER(cpu) + |
103 | R_IMR_INTERRUPT_MASK)); | 101 | R_IMR_INTERRUPT_MASK)); |
104 | spin_unlock_irqrestore(&sb1250_imr_lock, flags); | 102 | spin_unlock_irqrestore(&sb1250_imr_lock, flags); |
105 | } | 103 | } |
106 | 104 | ||
@@ -110,32 +108,25 @@ void sb1250_unmask_irq(int cpu, int irq) | |||
110 | u64 cur_ints; | 108 | u64 cur_ints; |
111 | 109 | ||
112 | spin_lock_irqsave(&sb1250_imr_lock, flags); | 110 | spin_lock_irqsave(&sb1250_imr_lock, flags); |
113 | cur_ints = __bus_readq(IOADDR(A_IMR_MAPPER(cpu) + | 111 | cur_ints = ____raw_readq(IOADDR(A_IMR_MAPPER(cpu) + |
114 | R_IMR_INTERRUPT_MASK)); | 112 | R_IMR_INTERRUPT_MASK)); |
115 | cur_ints &= ~(((u64) 1) << irq); | 113 | cur_ints &= ~(((u64) 1) << irq); |
116 | __bus_writeq(cur_ints, IOADDR(A_IMR_MAPPER(cpu) + | 114 | ____raw_writeq(cur_ints, IOADDR(A_IMR_MAPPER(cpu) + |
117 | R_IMR_INTERRUPT_MASK)); | 115 | R_IMR_INTERRUPT_MASK)); |
118 | spin_unlock_irqrestore(&sb1250_imr_lock, flags); | 116 | spin_unlock_irqrestore(&sb1250_imr_lock, flags); |
119 | } | 117 | } |
120 | 118 | ||
121 | #ifdef CONFIG_SMP | 119 | #ifdef CONFIG_SMP |
122 | static void sb1250_set_affinity(unsigned int irq, unsigned long mask) | 120 | static void sb1250_set_affinity(unsigned int irq, cpumask_t mask) |
123 | { | 121 | { |
124 | int i = 0, old_cpu, cpu, int_on; | 122 | int i = 0, old_cpu, cpu, int_on; |
125 | u64 cur_ints; | 123 | u64 cur_ints; |
126 | irq_desc_t *desc = irq_desc + irq; | 124 | irq_desc_t *desc = irq_desc + irq; |
127 | unsigned long flags; | 125 | unsigned long flags; |
128 | 126 | ||
129 | while (mask) { | 127 | i = first_cpu(mask); |
130 | if (mask & 1) { | ||
131 | mask >>= 1; | ||
132 | break; | ||
133 | } | ||
134 | mask >>= 1; | ||
135 | i++; | ||
136 | } | ||
137 | 128 | ||
138 | if (mask) { | 129 | if (cpus_weight(mask) > 1) { |
139 | printk("attempted to set irq affinity for irq %d to multiple CPUs\n", irq); | 130 | printk("attempted to set irq affinity for irq %d to multiple CPUs\n", irq); |
140 | return; | 131 | return; |
141 | } | 132 | } |
@@ -149,23 +140,23 @@ static void sb1250_set_affinity(unsigned int irq, unsigned long mask) | |||
149 | 140 | ||
150 | /* Swizzle each CPU's IMR (but leave the IP selection alone) */ | 141 | /* Swizzle each CPU's IMR (but leave the IP selection alone) */ |
151 | old_cpu = sb1250_irq_owner[irq]; | 142 | old_cpu = sb1250_irq_owner[irq]; |
152 | cur_ints = __bus_readq(IOADDR(A_IMR_MAPPER(old_cpu) + | 143 | cur_ints = ____raw_readq(IOADDR(A_IMR_MAPPER(old_cpu) + |
153 | R_IMR_INTERRUPT_MASK)); | 144 | R_IMR_INTERRUPT_MASK)); |
154 | int_on = !(cur_ints & (((u64) 1) << irq)); | 145 | int_on = !(cur_ints & (((u64) 1) << irq)); |
155 | if (int_on) { | 146 | if (int_on) { |
156 | /* If it was on, mask it */ | 147 | /* If it was on, mask it */ |
157 | cur_ints |= (((u64) 1) << irq); | 148 | cur_ints |= (((u64) 1) << irq); |
158 | __bus_writeq(cur_ints, IOADDR(A_IMR_MAPPER(old_cpu) + | 149 | ____raw_writeq(cur_ints, IOADDR(A_IMR_MAPPER(old_cpu) + |
159 | R_IMR_INTERRUPT_MASK)); | 150 | R_IMR_INTERRUPT_MASK)); |
160 | } | 151 | } |
161 | sb1250_irq_owner[irq] = cpu; | 152 | sb1250_irq_owner[irq] = cpu; |
162 | if (int_on) { | 153 | if (int_on) { |
163 | /* unmask for the new CPU */ | 154 | /* unmask for the new CPU */ |
164 | cur_ints = __bus_readq(IOADDR(A_IMR_MAPPER(cpu) + | 155 | cur_ints = ____raw_readq(IOADDR(A_IMR_MAPPER(cpu) + |
165 | R_IMR_INTERRUPT_MASK)); | 156 | R_IMR_INTERRUPT_MASK)); |
166 | cur_ints &= ~(((u64) 1) << irq); | 157 | cur_ints &= ~(((u64) 1) << irq); |
167 | __bus_writeq(cur_ints, IOADDR(A_IMR_MAPPER(cpu) + | 158 | ____raw_writeq(cur_ints, IOADDR(A_IMR_MAPPER(cpu) + |
168 | R_IMR_INTERRUPT_MASK)); | 159 | R_IMR_INTERRUPT_MASK)); |
169 | } | 160 | } |
170 | spin_unlock(&sb1250_imr_lock); | 161 | spin_unlock(&sb1250_imr_lock); |
171 | spin_unlock_irqrestore(&desc->lock, flags); | 162 | spin_unlock_irqrestore(&desc->lock, flags); |
@@ -208,8 +199,8 @@ static void ack_sb1250_irq(unsigned int irq) | |||
208 | * deliver the interrupts to all CPUs (which makes affinity | 199 | * deliver the interrupts to all CPUs (which makes affinity |
209 | * changing easier for us) | 200 | * changing easier for us) |
210 | */ | 201 | */ |
211 | pending = bus_readq(IOADDR(A_IMR_REGISTER(sb1250_irq_owner[irq], | 202 | pending = __raw_readq(IOADDR(A_IMR_REGISTER(sb1250_irq_owner[irq], |
212 | R_IMR_LDT_INTERRUPT))); | 203 | R_IMR_LDT_INTERRUPT))); |
213 | pending &= ((u64)1 << (irq)); | 204 | pending &= ((u64)1 << (irq)); |
214 | if (pending) { | 205 | if (pending) { |
215 | int i; | 206 | int i; |
@@ -224,8 +215,8 @@ static void ack_sb1250_irq(unsigned int irq) | |||
224 | * Clear for all CPUs so an affinity switch | 215 | * Clear for all CPUs so an affinity switch |
225 | * doesn't find an old status | 216 | * doesn't find an old status |
226 | */ | 217 | */ |
227 | bus_writeq(pending, | 218 | __raw_writeq(pending, |
228 | IOADDR(A_IMR_REGISTER(cpu, | 219 | IOADDR(A_IMR_REGISTER(cpu, |
229 | R_IMR_LDT_INTERRUPT_CLR))); | 220 | R_IMR_LDT_INTERRUPT_CLR))); |
230 | } | 221 | } |
231 | 222 | ||
@@ -340,12 +331,14 @@ void __init arch_init_irq(void) | |||
340 | 331 | ||
341 | /* Default everything to IP2 */ | 332 | /* Default everything to IP2 */ |
342 | for (i = 0; i < SB1250_NR_IRQS; i++) { /* was I0 */ | 333 | for (i = 0; i < SB1250_NR_IRQS; i++) { /* was I0 */ |
343 | bus_writeq(IMR_IP2_VAL, | 334 | __raw_writeq(IMR_IP2_VAL, |
344 | IOADDR(A_IMR_REGISTER(0, R_IMR_INTERRUPT_MAP_BASE) + | 335 | IOADDR(A_IMR_REGISTER(0, |
345 | (i << 3))); | 336 | R_IMR_INTERRUPT_MAP_BASE) + |
346 | bus_writeq(IMR_IP2_VAL, | 337 | (i << 3))); |
347 | IOADDR(A_IMR_REGISTER(1, R_IMR_INTERRUPT_MAP_BASE) + | 338 | __raw_writeq(IMR_IP2_VAL, |
348 | (i << 3))); | 339 | IOADDR(A_IMR_REGISTER(1, |
340 | R_IMR_INTERRUPT_MAP_BASE) + | ||
341 | (i << 3))); | ||
349 | } | 342 | } |
350 | 343 | ||
351 | init_sb1250_irqs(); | 344 | init_sb1250_irqs(); |
@@ -355,23 +348,23 @@ void __init arch_init_irq(void) | |||
355 | * inter-cpu messages | 348 | * inter-cpu messages |
356 | */ | 349 | */ |
357 | /* Was I1 */ | 350 | /* Was I1 */ |
358 | bus_writeq(IMR_IP3_VAL, | 351 | __raw_writeq(IMR_IP3_VAL, |
359 | IOADDR(A_IMR_REGISTER(0, R_IMR_INTERRUPT_MAP_BASE) + | 352 | IOADDR(A_IMR_REGISTER(0, R_IMR_INTERRUPT_MAP_BASE) + |
360 | (K_INT_MBOX_0 << 3))); | 353 | (K_INT_MBOX_0 << 3))); |
361 | bus_writeq(IMR_IP3_VAL, | 354 | __raw_writeq(IMR_IP3_VAL, |
362 | IOADDR(A_IMR_REGISTER(1, R_IMR_INTERRUPT_MAP_BASE) + | 355 | IOADDR(A_IMR_REGISTER(1, R_IMR_INTERRUPT_MAP_BASE) + |
363 | (K_INT_MBOX_0 << 3))); | 356 | (K_INT_MBOX_0 << 3))); |
364 | 357 | ||
365 | /* Clear the mailboxes. The firmware may leave them dirty */ | 358 | /* Clear the mailboxes. The firmware may leave them dirty */ |
366 | bus_writeq(0xffffffffffffffffULL, | 359 | __raw_writeq(0xffffffffffffffffULL, |
367 | IOADDR(A_IMR_REGISTER(0, R_IMR_MAILBOX_CLR_CPU))); | 360 | IOADDR(A_IMR_REGISTER(0, R_IMR_MAILBOX_CLR_CPU))); |
368 | bus_writeq(0xffffffffffffffffULL, | 361 | __raw_writeq(0xffffffffffffffffULL, |
369 | IOADDR(A_IMR_REGISTER(1, R_IMR_MAILBOX_CLR_CPU))); | 362 | IOADDR(A_IMR_REGISTER(1, R_IMR_MAILBOX_CLR_CPU))); |
370 | 363 | ||
371 | /* Mask everything except the mailbox registers for both cpus */ | 364 | /* Mask everything except the mailbox registers for both cpus */ |
372 | tmp = ~((u64) 0) ^ (((u64) 1) << K_INT_MBOX_0); | 365 | tmp = ~((u64) 0) ^ (((u64) 1) << K_INT_MBOX_0); |
373 | bus_writeq(tmp, IOADDR(A_IMR_REGISTER(0, R_IMR_INTERRUPT_MASK))); | 366 | __raw_writeq(tmp, IOADDR(A_IMR_REGISTER(0, R_IMR_INTERRUPT_MASK))); |
374 | bus_writeq(tmp, IOADDR(A_IMR_REGISTER(1, R_IMR_INTERRUPT_MASK))); | 367 | __raw_writeq(tmp, IOADDR(A_IMR_REGISTER(1, R_IMR_INTERRUPT_MASK))); |
375 | 368 | ||
376 | sb1250_steal_irq(K_INT_MBOX_0); | 369 | sb1250_steal_irq(K_INT_MBOX_0); |
377 | 370 | ||
@@ -396,12 +389,14 @@ void __init arch_init_irq(void) | |||
396 | sb1250_duart_present[kgdb_port] = 0; | 389 | sb1250_duart_present[kgdb_port] = 0; |
397 | #endif | 390 | #endif |
398 | /* Setup uart 1 settings, mapper */ | 391 | /* Setup uart 1 settings, mapper */ |
399 | bus_writeq(M_DUART_IMR_BRK, IOADDR(A_DUART_IMRREG(kgdb_port))); | 392 | __raw_writeq(M_DUART_IMR_BRK, |
393 | IOADDR(A_DUART_IMRREG(kgdb_port))); | ||
400 | 394 | ||
401 | sb1250_steal_irq(kgdb_irq); | 395 | sb1250_steal_irq(kgdb_irq); |
402 | bus_writeq(IMR_IP6_VAL, | 396 | __raw_writeq(IMR_IP6_VAL, |
403 | IOADDR(A_IMR_REGISTER(0, R_IMR_INTERRUPT_MAP_BASE) + | 397 | IOADDR(A_IMR_REGISTER(0, |
404 | (kgdb_irq<<3))); | 398 | R_IMR_INTERRUPT_MAP_BASE) + |
399 | (kgdb_irq << 3))); | ||
405 | sb1250_unmask_irq(0, kgdb_irq); | 400 | sb1250_unmask_irq(0, kgdb_irq); |
406 | } | 401 | } |
407 | #endif | 402 | #endif |