diff mbox

[V6,06/10] soc: tegra: pmc: Wait for powergate state to change

Message ID 1456501724-28477-7-git-send-email-jonathanh@nvidia.com (mailing list archive)
State Not Applicable, archived
Headers show

Commit Message

Jon Hunter Feb. 26, 2016, 3:48 p.m. UTC
Currently, the function tegra_powergate_set() simply sets the desired
powergate state but does not wait for the state to change. In most cases
we should wait for the state to change before proceeding. Currently, there
is a case for tegra114 and tegra124 devices where we do not wait when
starting the secondary CPU as this is not necessary. However, this is only
done at boot time and so waiting here will only have a small impact on
boot time. Therefore, update tegra_powergate_set() to wait when setting
the powergate.

By adding this feature, we can also eliminate the polling loop from
tegra30_boot_secondary().

A function has been added for checking the status of the powergate and
so update the tegra_powergate_is_powered() to use this macro as well.

Signed-off-by: Jon Hunter <jonathanh@nvidia.com>
---
 arch/arm/mach-tegra/platsmp.c | 16 +++-------------
 drivers/soc/tegra/pmc.c       |  9 ++++++++-
 2 files changed, 11 insertions(+), 14 deletions(-)

Comments

Thierry Reding Feb. 29, 2016, 7:24 a.m. UTC | #1
On Fri, Feb 26, 2016 at 03:48:40PM +0000, Jon Hunter wrote:
> Currently, the function tegra_powergate_set() simply sets the desired
> powergate state but does not wait for the state to change. In most cases
> we should wait for the state to change before proceeding. Currently, there
> is a case for tegra114 and tegra124 devices where we do not wait when
> starting the secondary CPU as this is not necessary. However, this is only
> done at boot time and so waiting here will only have a small impact on
> boot time. Therefore, update tegra_powergate_set() to wait when setting
> the powergate.
> 
> By adding this feature, we can also eliminate the polling loop from
> tegra30_boot_secondary().
> 
> A function has been added for checking the status of the powergate and
> so update the tegra_powergate_is_powered() to use this macro as well.
> 
> Signed-off-by: Jon Hunter <jonathanh@nvidia.com>
> ---
>  arch/arm/mach-tegra/platsmp.c | 16 +++-------------
>  drivers/soc/tegra/pmc.c       |  9 ++++++++-
>  2 files changed, 11 insertions(+), 14 deletions(-)

This looks to be independent from the generic power domain support. Can
I apply this separately (for 4.6, without waiting for the power domain
series' dependencies to go in)?

Thierry
Jon Hunter Feb. 29, 2016, 10:38 a.m. UTC | #2
On 29/02/16 07:24, Thierry Reding wrote:
> * PGP Signed by an unknown key
> 
> On Fri, Feb 26, 2016 at 03:48:40PM +0000, Jon Hunter wrote:
>> Currently, the function tegra_powergate_set() simply sets the desired
>> powergate state but does not wait for the state to change. In most cases
>> we should wait for the state to change before proceeding. Currently, there
>> is a case for tegra114 and tegra124 devices where we do not wait when
>> starting the secondary CPU as this is not necessary. However, this is only
>> done at boot time and so waiting here will only have a small impact on
>> boot time. Therefore, update tegra_powergate_set() to wait when setting
>> the powergate.
>>
>> By adding this feature, we can also eliminate the polling loop from
>> tegra30_boot_secondary().
>>
>> A function has been added for checking the status of the powergate and
>> so update the tegra_powergate_is_powered() to use this macro as well.
>>
>> Signed-off-by: Jon Hunter <jonathanh@nvidia.com>
>> ---
>>  arch/arm/mach-tegra/platsmp.c | 16 +++-------------
>>  drivers/soc/tegra/pmc.c       |  9 ++++++++-
>>  2 files changed, 11 insertions(+), 14 deletions(-)
> 
> This looks to be independent from the generic power domain support. Can
> I apply this separately (for 4.6, without waiting for the power domain
> series' dependencies to go in)?

Yes this could be applied independently of this series for v4.6. I just
wanted to make sure that this change is added before the genpd changes
are applied.

Cheers
Jon
--
To unsubscribe from this list: send the line "unsubscribe linux-pm" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html
Thierry Reding Feb. 29, 2016, 12:14 p.m. UTC | #3
On Fri, Feb 26, 2016 at 03:48:40PM +0000, Jon Hunter wrote:
> Currently, the function tegra_powergate_set() simply sets the desired
> powergate state but does not wait for the state to change. In most cases
> we should wait for the state to change before proceeding. Currently, there
> is a case for tegra114 and tegra124 devices where we do not wait when
> starting the secondary CPU as this is not necessary. However, this is only
> done at boot time and so waiting here will only have a small impact on
> boot time. Therefore, update tegra_powergate_set() to wait when setting
> the powergate.
> 
> By adding this feature, we can also eliminate the polling loop from
> tegra30_boot_secondary().
> 
> A function has been added for checking the status of the powergate and
> so update the tegra_powergate_is_powered() to use this macro as well.
> 
> Signed-off-by: Jon Hunter <jonathanh@nvidia.com>
> ---
>  arch/arm/mach-tegra/platsmp.c | 16 +++-------------
>  drivers/soc/tegra/pmc.c       |  9 ++++++++-
>  2 files changed, 11 insertions(+), 14 deletions(-)

Applied, thanks.

Thierry
diff mbox

Patch

diff --git a/arch/arm/mach-tegra/platsmp.c b/arch/arm/mach-tegra/platsmp.c
index f3f61dbbda97..75620ae73913 100644
--- a/arch/arm/mach-tegra/platsmp.c
+++ b/arch/arm/mach-tegra/platsmp.c
@@ -108,19 +108,9 @@  static int tegra30_boot_secondary(unsigned int cpu, struct task_struct *idle)
 	 * be un-gated by un-toggling the power gate register
 	 * manually.
 	 */
-	if (!tegra_pmc_cpu_is_powered(cpu)) {
-		ret = tegra_pmc_cpu_power_on(cpu);
-		if (ret)
-			return ret;
-
-		/* Wait for the power to come up. */
-		timeout = jiffies + msecs_to_jiffies(100);
-		while (!tegra_pmc_cpu_is_powered(cpu)) {
-			if (time_after(jiffies, timeout))
-				return -ETIMEDOUT;
-			udelay(10);
-		}
-	}
+	ret = tegra_pmc_cpu_power_on(cpu);
+	if (ret)
+		return ret;
 
 remove_clamps:
 	/* CPU partition is powered. Enable the CPU clock. */
diff --git a/drivers/soc/tegra/pmc.c b/drivers/soc/tegra/pmc.c
index e4fd40fa27e8..08966c26d65c 100644
--- a/drivers/soc/tegra/pmc.c
+++ b/drivers/soc/tegra/pmc.c
@@ -28,6 +28,7 @@ 
 #include <linux/export.h>
 #include <linux/init.h>
 #include <linux/io.h>
+#include <linux/iopoll.h>
 #include <linux/of.h>
 #include <linux/of_address.h>
 #include <linux/platform_device.h>
@@ -194,6 +195,9 @@  static inline bool tegra_powergate_is_valid(int id)
  */
 static int tegra_powergate_set(unsigned int id, bool new_state)
 {
+	bool status;
+	int err;
+
 	if (id == TEGRA_POWERGATE_3D && pmc->soc->has_gpu_clamps)
 		return -EINVAL;
 
@@ -206,9 +210,12 @@  static int tegra_powergate_set(unsigned int id, bool new_state)
 
 	tegra_pmc_writel(PWRGATE_TOGGLE_START | id, PWRGATE_TOGGLE);
 
+	err = readx_poll_timeout(tegra_powergate_state, id, status,
+				 status == new_state, 10, 100000);
+
 	mutex_unlock(&pmc->powergates_lock);
 
-	return 0;
+	return err;
 }
 
 /**