aboutsummaryrefslogtreecommitdiffstats
path: root/arch/ia64/kernel/irq_ia64.c
diff options
context:
space:
mode:
authorYasuaki Ishimatsu <isimatu.yasuaki@jp.fujitsu.com>2007-07-17 08:22:48 -0400
committerTony Luck <tony.luck@intel.com>2007-07-17 12:57:42 -0400
commitcd378f18cf73d92bf0b6e1e6b5759b5dd729a9f2 (patch)
tree6960768a1ddecb74e6a5fa1dfc978e5df8635eb2 /arch/ia64/kernel/irq_ia64.c
parent4994be1b3fe9120c88022ff5c0c33f6312b17adb (diff)
[IA64] Support irq migration across domain
Add support for IRQ migration across vector domain. Signed-off-by: Kenji Kaneshige <kaneshige.kenji@jp.fujitsu.com> Signed-off-by: Yasuaki Ishimatsu <isimatu.yasuaki@jp.fujitsu.com> Signed-off-by: Tony Luck <tony.luck@intel.com>
Diffstat (limited to 'arch/ia64/kernel/irq_ia64.c')
-rw-r--r--arch/ia64/kernel/irq_ia64.c42
1 files changed, 39 insertions, 3 deletions
diff --git a/arch/ia64/kernel/irq_ia64.c b/arch/ia64/kernel/irq_ia64.c
index a3667631ed80..22806b94025a 100644
--- a/arch/ia64/kernel/irq_ia64.c
+++ b/arch/ia64/kernel/irq_ia64.c
@@ -172,15 +172,13 @@ int bind_irq_vector(int irq, int vector, cpumask_t domain)
172 return ret; 172 return ret;
173} 173}
174 174
175static void clear_irq_vector(int irq) 175static void __clear_irq_vector(int irq)
176{ 176{
177 unsigned long flags;
178 int vector, cpu, pos; 177 int vector, cpu, pos;
179 cpumask_t mask; 178 cpumask_t mask;
180 cpumask_t domain; 179 cpumask_t domain;
181 struct irq_cfg *cfg = &irq_cfg[irq]; 180 struct irq_cfg *cfg = &irq_cfg[irq];
182 181
183 spin_lock_irqsave(&vector_lock, flags);
184 BUG_ON((unsigned)irq >= NR_IRQS); 182 BUG_ON((unsigned)irq >= NR_IRQS);
185 BUG_ON(cfg->vector == IRQ_VECTOR_UNASSIGNED); 183 BUG_ON(cfg->vector == IRQ_VECTOR_UNASSIGNED);
186 vector = cfg->vector; 184 vector = cfg->vector;
@@ -193,6 +191,14 @@ static void clear_irq_vector(int irq)
193 irq_status[irq] = IRQ_UNUSED; 191 irq_status[irq] = IRQ_UNUSED;
194 pos = vector - IA64_FIRST_DEVICE_VECTOR; 192 pos = vector - IA64_FIRST_DEVICE_VECTOR;
195 cpus_andnot(vector_table[pos], vector_table[pos], domain); 193 cpus_andnot(vector_table[pos], vector_table[pos], domain);
194}
195
196static void clear_irq_vector(int irq)
197{
198 unsigned long flags;
199
200 spin_lock_irqsave(&vector_lock, flags);
201 __clear_irq_vector(irq);
196 spin_unlock_irqrestore(&vector_lock, flags); 202 spin_unlock_irqrestore(&vector_lock, flags);
197} 203}
198 204
@@ -275,6 +281,36 @@ void destroy_and_reserve_irq(unsigned int irq)
275 reserve_irq(irq); 281 reserve_irq(irq);
276} 282}
277 283
284static int __reassign_irq_vector(int irq, int cpu)
285{
286 struct irq_cfg *cfg = &irq_cfg[irq];
287 int vector;
288 cpumask_t domain;
289
290 if (cfg->vector == IRQ_VECTOR_UNASSIGNED || !cpu_online(cpu))
291 return -EINVAL;
292 if (cpu_isset(cpu, cfg->domain))
293 return 0;
294 domain = vector_allocation_domain(cpu);
295 vector = find_unassigned_vector(domain);
296 if (vector < 0)
297 return -ENOSPC;
298 __clear_irq_vector(irq);
299 BUG_ON(__bind_irq_vector(irq, vector, domain));
300 return 0;
301}
302
303int reassign_irq_vector(int irq, int cpu)
304{
305 unsigned long flags;
306 int ret;
307
308 spin_lock_irqsave(&vector_lock, flags);
309 ret = __reassign_irq_vector(irq, cpu);
310 spin_unlock_irqrestore(&vector_lock, flags);
311 return ret;
312}
313
278/* 314/*
279 * Dynamic irq allocate and deallocation for MSI 315 * Dynamic irq allocate and deallocation for MSI
280 */ 316 */