aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/irqchip
diff options
context:
space:
mode:
authorSudeep Holla <sudeep.holla@arm.com>2014-08-26 11:03:34 -0400
committerJason Cooper <jason@lakedaemon.net>2014-09-14 04:57:25 -0400
commita2c225101234bcef8f40497bd50ccb5e9c1fb527 (patch)
tree8dce7f0a6645eefe13069c4484995ccf9c895c40 /drivers/irqchip
parent3228950621d92f0f212378f95a6998ef3a1be0bb (diff)
irqchip: gic-v3: Refactor gic_enable_redist to support both enabling and disabling
Currently gic_enable_redist configures the redistributors to never assert WakeRequest signal. However when powering down the processors with wake-up enabled(i.e suspend), we need to configure it to assert that signal. This patch extends gic_enable_redist so that the redistributor can be configure to assert WakeRequest and hold interrupts as pending. This is useful in suspending the processors. This patch also adds check to make sure GICR_WAKER is accessible when configuring it. Cc: Lorenzo Pieralisi <lorenzo.pieralisi@arm.com> Signed-off-by: Sudeep Holla <sudeep.holla@arm.com> [maz: removed reference to GICD_CTLR.DS and added read-back of GICR_WAKER to check that it is not RAZ/WI] Signed-off-by: Marc Zyngier <marc.zyngier@arm.com> Acked-by: Marc Zyngier <marc.zyngier@arm.com> Link: https://lkml.kernel.org/r/1409065415-20176-2-git-send-email-sudeep.holla@arm.com Signed-off-by: Jason Cooper <jason@lakedaemon.net>
Diffstat (limited to 'drivers/irqchip')
-rw-r--r--drivers/irqchip/irq-gic-v3.c30
1 files changed, 20 insertions, 10 deletions
diff --git a/drivers/irqchip/irq-gic-v3.c b/drivers/irqchip/irq-gic-v3.c
index 57eaa5a0b1e3..37062ba6704b 100644
--- a/drivers/irqchip/irq-gic-v3.c
+++ b/drivers/irqchip/irq-gic-v3.c
@@ -155,7 +155,7 @@ static void gic_enable_sre(void)
155 pr_err("GIC: unable to set SRE (disabled at EL2), panic ahead\n"); 155 pr_err("GIC: unable to set SRE (disabled at EL2), panic ahead\n");
156} 156}
157 157
158static void gic_enable_redist(void) 158static void gic_enable_redist(bool enable)
159{ 159{
160 void __iomem *rbase; 160 void __iomem *rbase;
161 u32 count = 1000000; /* 1s! */ 161 u32 count = 1000000; /* 1s! */
@@ -163,20 +163,30 @@ static void gic_enable_redist(void)
163 163
164 rbase = gic_data_rdist_rd_base(); 164 rbase = gic_data_rdist_rd_base();
165 165
166 /* Wake up this CPU redistributor */
167 val = readl_relaxed(rbase + GICR_WAKER); 166 val = readl_relaxed(rbase + GICR_WAKER);
168 val &= ~GICR_WAKER_ProcessorSleep; 167 if (enable)
168 /* Wake up this CPU redistributor */
169 val &= ~GICR_WAKER_ProcessorSleep;
170 else
171 val |= GICR_WAKER_ProcessorSleep;
169 writel_relaxed(val, rbase + GICR_WAKER); 172 writel_relaxed(val, rbase + GICR_WAKER);
170 173
171 while (readl_relaxed(rbase + GICR_WAKER) & GICR_WAKER_ChildrenAsleep) { 174 if (!enable) { /* Check that GICR_WAKER is writeable */
172 count--; 175 val = readl_relaxed(rbase + GICR_WAKER);
173 if (!count) { 176 if (!(val & GICR_WAKER_ProcessorSleep))
174 pr_err_ratelimited("redist didn't wake up...\n"); 177 return; /* No PM support in this redistributor */
175 return; 178 }
176 } 179
180 while (count--) {
181 val = readl_relaxed(rbase + GICR_WAKER);
182 if (enable ^ (val & GICR_WAKER_ChildrenAsleep))
183 break;
177 cpu_relax(); 184 cpu_relax();
178 udelay(1); 185 udelay(1);
179 }; 186 };
187 if (!count)
188 pr_err_ratelimited("redistributor failed to %s...\n",
189 enable ? "wakeup" : "sleep");
180} 190}
181 191
182/* 192/*
@@ -381,7 +391,7 @@ static void gic_cpu_init(void)
381 if (gic_populate_rdist()) 391 if (gic_populate_rdist())
382 return; 392 return;
383 393
384 gic_enable_redist(); 394 gic_enable_redist(true);
385 395
386 rbase = gic_data_rdist_sgi_base(); 396 rbase = gic_data_rdist_sgi_base();
387 397