Commit 5df718d84679936454e815451d748ccca0e9edad

Authored by Tomasz Figa
Committed by Daniel Lezcano
1 parent 7b0dd72a44

clocksource: exynos_mct: Set IRQ affinity when the CPU goes online

Some variants of Exynos MCT, namely exynos4210-mct at the moment, use
normal, shared interrupts for local timers. This means that each
interrupt must have correct affinity set to fire only on CPU
corresponding to given local timer.

However after recent conversion of clocksource drivers to not use the
local timer API for local timer initialization any more, the point of
time when local timers get initialized changed and irq_set_affinity()
fails because the CPU is not marked as online yet.

This patch fixes this by moving the call to irq_set_affinity() to
CPU_ONLINE notification, so the affinity is being set when the CPU goes
online.

This fixes a regression introduced by commit
	ee98d27df6 ARM: EXYNOS4: Divorce mct from local timer API
which rendered all Exynos4210 based boards unbootable due to
failing irq_set_affinity() making local timers inoperatible.

Signed-off-by: Tomasz Figa <t.figa@samsung.com>
Signed-off-by: Kyungmin Park <kyungmin.park@samsung.com>
Acked-by: Stephen Boyd <sboyd@codeaurora.org>
Signed-off-by: Daniel Lezcano <daniel.lezcano@linaro.org>

Showing 1 changed file with 9 additions and 1 deletions Side-by-side Diff

drivers/clocksource/exynos_mct.c
... ... @@ -428,7 +428,6 @@
428 428 evt->irq);
429 429 return -EIO;
430 430 }
431   - irq_set_affinity(evt->irq, cpumask_of(cpu));
432 431 } else {
433 432 enable_percpu_irq(mct_irqs[MCT_L0_IRQ], 0);
434 433 }
... ... @@ -449,6 +448,7 @@
449 448 unsigned long action, void *hcpu)
450 449 {
451 450 struct mct_clock_event_device *mevt;
  451 + unsigned int cpu;
452 452  
453 453 /*
454 454 * Grab cpu pointer in each case to avoid spurious
... ... @@ -459,6 +459,12 @@
459 459 mevt = this_cpu_ptr(&percpu_mct_tick);
460 460 exynos4_local_timer_setup(&mevt->evt);
461 461 break;
  462 + case CPU_ONLINE:
  463 + cpu = (unsigned long)hcpu;
  464 + if (mct_int_type == MCT_INT_SPI)
  465 + irq_set_affinity(mct_irqs[MCT_L0_IRQ + cpu],
  466 + cpumask_of(cpu));
  467 + break;
462 468 case CPU_DYING:
463 469 mevt = this_cpu_ptr(&percpu_mct_tick);
464 470 exynos4_local_timer_stop(&mevt->evt);
... ... @@ -500,6 +506,8 @@
500 506 &percpu_mct_tick);
501 507 WARN(err, "MCT: can't request IRQ %d (%d)\n",
502 508 mct_irqs[MCT_L0_IRQ], err);
  509 + } else {
  510 + irq_set_affinity(mct_irqs[MCT_L0_IRQ], cpumask_of(0));
503 511 }
504 512  
505 513 err = register_cpu_notifier(&exynos4_mct_cpu_nb);