diff options
author | Alex Frid <afrid@nvidia.com> | 2013-08-13 00:14:20 -0700 |
---|---|---|
committer | Dan Willemsen <dwillemsen@nvidia.com> | 2013-09-14 13:41:09 -0700 |
commit | 052ca0ae17cc32784e95e9762b197d7fa179076f (patch) | |
tree | 5e6f3ca03961ef14cf88959a983aa732449e5df4 /arch/arm/mach-tegra/pm-t3.c | |
parent | e2478be857fd99abf772ee39d6644bac72a70722 (diff) |
ARM: tegra: power: Keep interrupts ON for LP CPU delay
- Moved LP CPU minimum residency delay out of the interrupt-disabled
section of the cluster switch to reduce interrupt disabled time.
- Time stamped start of LP CPU residency, and rail statistic after the
cluster switch is completed, still within interrupt disabled section
to make sure LP residency restriction is applied on top of cluster
transition latency.
Change-Id: I55f769af197bbd757966bafe37a10a6e43b7bf2e
Signed-off-by: Alex Frid <afrid@nvidia.com>
Reviewed-on: http://git-master/r/261328
GVS: Gerrit_Virtual_Submit
Reviewed-by: Yu-Huan Hsu <yhsu@nvidia.com>
Diffstat (limited to 'arch/arm/mach-tegra/pm-t3.c')
-rw-r--r-- | arch/arm/mach-tegra/pm-t3.c | 28 |
1 files changed, 19 insertions, 9 deletions
diff --git a/arch/arm/mach-tegra/pm-t3.c b/arch/arm/mach-tegra/pm-t3.c index 8f9ac0c77259..c346cb356400 100644 --- a/arch/arm/mach-tegra/pm-t3.c +++ b/arch/arm/mach-tegra/pm-t3.c @@ -3,7 +3,7 @@ * * Tegra3 SOC-specific power and cluster management * - * Copyright (c) 2009-2012, NVIDIA CORPORATION. All rights reserved. + * Copyright (c) 2009-2013, NVIDIA CORPORATION. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -409,28 +409,28 @@ int tegra_cluster_control(unsigned int us, unsigned int flags) (flags & TEGRA_POWER_CLUSTER_FORCE) ? "force" : "", us)); - local_irq_save(irq_flags); - if (current_cluster != target_cluster && !timekeeping_suspended) { - ktime_t now = ktime_get(); if (target_cluster == TEGRA_POWER_CLUSTER_G) { + ktime_t now = ktime_get(); s64 t = ktime_to_us(ktime_sub(now, last_g2lp)); s64 t_off = tegra_cpu_power_off_time(); if (t_off > t) udelay((unsigned int)(t_off - t)); + } + } + + local_irq_save(irq_flags); - tegra_dvfs_rail_on(tegra_cpu_rail, now); - } else { #ifdef CONFIG_TEGRA_VIRTUAL_CPUID + if (current_cluster != target_cluster && !timekeeping_suspended) { + if (target_cluster == TEGRA_POWER_CLUSTER_LP) { u32 cpu; cpu = cpu_logical_map(smp_processor_id()); writel(cpu, FLOW_CTRL_MPID); -#endif - last_g2lp = now; - tegra_dvfs_rail_off(tegra_cpu_rail, now); } } +#endif if (flags & TEGRA_POWER_SDRAM_SELFREFRESH) { if (us) @@ -459,6 +459,16 @@ int tegra_cluster_control(unsigned int us, unsigned int flags) cpu_pm_exit(); tegra_clear_cpu_in_pd(cpu); } + + if (current_cluster != target_cluster && !timekeeping_suspended) { + ktime_t now = ktime_get(); + if (target_cluster == TEGRA_POWER_CLUSTER_G) { + tegra_dvfs_rail_on(tegra_cpu_rail, now); + } else { + last_g2lp = now; + tegra_dvfs_rail_off(tegra_cpu_rail, now); + } + } local_irq_restore(irq_flags); DEBUG_CLUSTER(("%s: %s\r\n", __func__, is_lp_cluster() ? "LP" : "G")); |