aboutsummaryrefslogtreecommitdiffstats
path: root/arch/xtensa/kernel/irq.c
diff options
context:
space:
mode:
authorMax Filippov <jcmvbkbc@gmail.com>2013-10-16 18:42:28 -0400
committerChris Zankel <chris@zankel.net>2014-01-14 13:19:59 -0500
commit49b424fedaf88d0fa9913082b8c1ccd012a8a972 (patch)
tree1a1fac57b578fe828b54b0367df4ed1fd94940b9 /arch/xtensa/kernel/irq.c
parentf615136c06a791364f5afa8b8ba965315a6440f1 (diff)
xtensa: implement CPU hotplug
Signed-off-by: Max Filippov <jcmvbkbc@gmail.com> Signed-off-by: Chris Zankel <chris@zankel.net>
Diffstat (limited to 'arch/xtensa/kernel/irq.c')
-rw-r--r--arch/xtensa/kernel/irq.c49
1 files changed, 49 insertions, 0 deletions
diff --git a/arch/xtensa/kernel/irq.c b/arch/xtensa/kernel/irq.c
index fad9e0059765..482868a2de6e 100644
--- a/arch/xtensa/kernel/irq.c
+++ b/arch/xtensa/kernel/irq.c
@@ -153,3 +153,52 @@ void __init init_IRQ(void)
153#endif 153#endif
154 variant_init_irq(); 154 variant_init_irq();
155} 155}
156
157#ifdef CONFIG_HOTPLUG_CPU
158static void route_irq(struct irq_data *data, unsigned int irq, unsigned int cpu)
159{
160 struct irq_desc *desc = irq_to_desc(irq);
161 struct irq_chip *chip = irq_data_get_irq_chip(data);
162 unsigned long flags;
163
164 raw_spin_lock_irqsave(&desc->lock, flags);
165 if (chip->irq_set_affinity)
166 chip->irq_set_affinity(data, cpumask_of(cpu), false);
167 raw_spin_unlock_irqrestore(&desc->lock, flags);
168}
169
170/*
171 * The CPU has been marked offline. Migrate IRQs off this CPU. If
172 * the affinity settings do not allow other CPUs, force them onto any
173 * available CPU.
174 */
175void migrate_irqs(void)
176{
177 unsigned int i, cpu = smp_processor_id();
178 struct irq_desc *desc;
179
180 for_each_irq_desc(i, desc) {
181 struct irq_data *data = irq_desc_get_irq_data(desc);
182 unsigned int newcpu;
183
184 if (irqd_is_per_cpu(data))
185 continue;
186
187 if (!cpumask_test_cpu(cpu, data->affinity))
188 continue;
189
190 newcpu = cpumask_any_and(data->affinity, cpu_online_mask);
191
192 if (newcpu >= nr_cpu_ids) {
193 pr_info_ratelimited("IRQ%u no longer affine to CPU%u\n",
194 i, cpu);
195
196 cpumask_setall(data->affinity);
197 newcpu = cpumask_any_and(data->affinity,
198 cpu_online_mask);
199 }
200
201 route_irq(data, i, newcpu);
202 }
203}
204#endif /* CONFIG_HOTPLUG_CPU */