aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/irqchip/irq-gic.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/irqchip/irq-gic.c')
-rw-r--r--drivers/irqchip/irq-gic.c25
1 files changed, 23 insertions, 2 deletions
diff --git a/drivers/irqchip/irq-gic.c b/drivers/irqchip/irq-gic.c
index 69d9a395d54c..644d72468423 100644
--- a/drivers/irqchip/irq-gic.c
+++ b/drivers/irqchip/irq-gic.c
@@ -353,6 +353,25 @@ void __init gic_cascade_irq(unsigned int gic_nr, unsigned int irq)
353 irq_set_chained_handler(irq, gic_handle_cascade_irq); 353 irq_set_chained_handler(irq, gic_handle_cascade_irq);
354} 354}
355 355
356static u8 gic_get_cpumask(struct gic_chip_data *gic)
357{
358 void __iomem *base = gic_data_dist_base(gic);
359 u32 mask, i;
360
361 for (i = mask = 0; i < 32; i += 4) {
362 mask = readl_relaxed(base + GIC_DIST_TARGET + i);
363 mask |= mask >> 16;
364 mask |= mask >> 8;
365 if (mask)
366 break;
367 }
368
369 if (!mask)
370 pr_crit("GIC CPU mask not found - kernel will fail to boot.\n");
371
372 return mask;
373}
374
356static void __init gic_dist_init(struct gic_chip_data *gic) 375static void __init gic_dist_init(struct gic_chip_data *gic)
357{ 376{
358 unsigned int i; 377 unsigned int i;
@@ -371,7 +390,9 @@ static void __init gic_dist_init(struct gic_chip_data *gic)
371 /* 390 /*
372 * Set all global interrupts to this CPU only. 391 * Set all global interrupts to this CPU only.
373 */ 392 */
374 cpumask = readl_relaxed(base + GIC_DIST_TARGET + 0); 393 cpumask = gic_get_cpumask(gic);
394 cpumask |= cpumask << 8;
395 cpumask |= cpumask << 16;
375 for (i = 32; i < gic_irqs; i += 4) 396 for (i = 32; i < gic_irqs; i += 4)
376 writel_relaxed(cpumask, base + GIC_DIST_TARGET + i * 4 / 4); 397 writel_relaxed(cpumask, base + GIC_DIST_TARGET + i * 4 / 4);
377 398
@@ -402,7 +423,7 @@ static void __cpuinit gic_cpu_init(struct gic_chip_data *gic)
402 * Get what the GIC says our CPU mask is. 423 * Get what the GIC says our CPU mask is.
403 */ 424 */
404 BUG_ON(cpu >= NR_GIC_CPU_IF); 425 BUG_ON(cpu >= NR_GIC_CPU_IF);
405 cpu_mask = readl_relaxed(dist_base + GIC_DIST_TARGET + 0); 426 cpu_mask = gic_get_cpumask(gic);
406 gic_cpu_map[cpu] = cpu_mask; 427 gic_cpu_map[cpu] = cpu_mask;
407 428
408 /* 429 /*