All of lore.kernel.org
 help / color / mirror / Atom feed
From: Joseph Lo <josephl-DDmLM1+adcrQT0dZR+AlfA@public.gmane.org>
To: Stephen Warren <swarren-3lzwWm7+Weoh9ZMKESR00Q@public.gmane.org>
Cc: linux-tegra-u79uwXL29TY76Z2rM5mHXA@public.gmane.org,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r@public.gmane.org,
	Colin Cross <ccross-z5hGa2qSFaRBDgjK7y7TUQ@public.gmane.org>,
	Joseph Lo <josephl-DDmLM1+adcrQT0dZR+AlfA@public.gmane.org>
Subject: [PATCH V3 3/5] ARM: tegra20: clocks: add CPU low-power function into tegra_cpu_car_ops
Date: Tue, 18 Dec 2012 10:30:59 +0800	[thread overview]
Message-ID: <1355797861-12759-4-git-send-email-josephl@nvidia.com> (raw)
In-Reply-To: <1355797861-12759-1-git-send-email-josephl-DDmLM1+adcrQT0dZR+AlfA@public.gmane.org>

Add suspend, resume and rail_off_ready API into tegra_cpu_car_ops. These
functions were used for CPU powered-down state maintenance.

Signed-off-by: Joseph Lo <josephl-DDmLM1+adcrQT0dZR+AlfA@public.gmane.org>
---
V3:
* no change
V2:
* refine the code sequence in "tegra20_cpu_rail_off_ready"
---
 arch/arm/mach-tegra/tegra20_clocks.c |   99 ++++++++++++++++++++++++++++++++++
 1 files changed, 99 insertions(+), 0 deletions(-)

diff --git a/arch/arm/mach-tegra/tegra20_clocks.c b/arch/arm/mach-tegra/tegra20_clocks.c
index 4eb6bc8..1780268 100644
--- a/arch/arm/mach-tegra/tegra20_clocks.c
+++ b/arch/arm/mach-tegra/tegra20_clocks.c
@@ -159,6 +159,31 @@
 #define CPU_CLOCK(cpu)	(0x1 << (8 + cpu))
 #define CPU_RESET(cpu)	(0x1111ul << (cpu))
 
+#define CLK_RESET_CCLK_BURST	0x20
+#define CLK_RESET_CCLK_DIVIDER  0x24
+#define CLK_RESET_PLLX_BASE	0xe0
+#define CLK_RESET_PLLX_MISC	0xe4
+
+#define CLK_RESET_SOURCE_CSITE	0x1d4
+
+#define CLK_RESET_CCLK_BURST_POLICY_SHIFT	28
+#define CLK_RESET_CCLK_RUN_POLICY_SHIFT		4
+#define CLK_RESET_CCLK_IDLE_POLICY_SHIFT	0
+#define CLK_RESET_CCLK_IDLE_POLICY		1
+#define CLK_RESET_CCLK_RUN_POLICY		2
+#define CLK_RESET_CCLK_BURST_POLICY_PLLX	8
+
+#ifdef CONFIG_PM_SLEEP
+static struct cpu_clk_suspend_context {
+	u32 pllx_misc;
+	u32 pllx_base;
+
+	u32 cpu_burst;
+	u32 clk_csite_src;
+	u32 cclk_divider;
+} tegra20_cpu_clk_sctx;
+#endif
+
 static void __iomem *reg_clk_base = IO_ADDRESS(TEGRA_CLK_RESET_BASE);
 static void __iomem *reg_pmc_base = IO_ADDRESS(TEGRA_PMC_BASE);
 
@@ -1609,12 +1634,86 @@ static void tegra20_disable_cpu_clock(u32 cpu)
 	       reg_clk_base + TEGRA_CLK_RST_CONTROLLER_CLK_CPU_CMPLX);
 }
 
+#ifdef CONFIG_PM_SLEEP
+static bool tegra20_cpu_rail_off_ready(void)
+{
+	unsigned int cpu_rst_status;
+
+	cpu_rst_status = readl(reg_clk_base +
+			       TEGRA_CLK_RST_CONTROLLER_RST_CPU_CMPLX_SET);
+
+	return !!(cpu_rst_status & 0x2);
+}
+
+static void tegra20_cpu_clock_suspend(void)
+{
+	/* switch coresite to clk_m, save off original source */
+	tegra20_cpu_clk_sctx.clk_csite_src =
+				readl(reg_clk_base + CLK_RESET_SOURCE_CSITE);
+	writel(3<<30, reg_clk_base + CLK_RESET_SOURCE_CSITE);
+
+	tegra20_cpu_clk_sctx.cpu_burst =
+				readl(reg_clk_base + CLK_RESET_CCLK_BURST);
+	tegra20_cpu_clk_sctx.pllx_base =
+				readl(reg_clk_base + CLK_RESET_PLLX_BASE);
+	tegra20_cpu_clk_sctx.pllx_misc =
+				readl(reg_clk_base + CLK_RESET_PLLX_MISC);
+	tegra20_cpu_clk_sctx.cclk_divider =
+				readl(reg_clk_base + CLK_RESET_CCLK_DIVIDER);
+}
+
+static void tegra20_cpu_clock_resume(void)
+{
+	unsigned int reg, policy;
+
+	/* Is CPU complex already running on PLLX? */
+	reg = readl(reg_clk_base + CLK_RESET_CCLK_BURST);
+	policy = (reg >> CLK_RESET_CCLK_BURST_POLICY_SHIFT) & 0xF;
+
+	if (policy == CLK_RESET_CCLK_IDLE_POLICY)
+		reg = (reg >> CLK_RESET_CCLK_IDLE_POLICY_SHIFT) & 0xF;
+	else if (policy == CLK_RESET_CCLK_RUN_POLICY)
+		reg = (reg >> CLK_RESET_CCLK_RUN_POLICY_SHIFT) & 0xF;
+	else
+		BUG();
+
+	if (reg != CLK_RESET_CCLK_BURST_POLICY_PLLX) {
+		/* restore PLLX settings if CPU is on different PLL */
+		writel(tegra20_cpu_clk_sctx.pllx_misc,
+					reg_clk_base + CLK_RESET_PLLX_MISC);
+		writel(tegra20_cpu_clk_sctx.pllx_base,
+					reg_clk_base + CLK_RESET_PLLX_BASE);
+
+		/* wait for PLL stabilization if PLLX was enabled */
+		if (tegra20_cpu_clk_sctx.pllx_base & (1 << 30))
+			udelay(300);
+	}
+
+	/*
+	 * Restore original burst policy setting for calls resulting from CPU
+	 * LP2 in idle or system suspend.
+	 */
+	writel(tegra20_cpu_clk_sctx.cclk_divider,
+					reg_clk_base + CLK_RESET_CCLK_DIVIDER);
+	writel(tegra20_cpu_clk_sctx.cpu_burst,
+					reg_clk_base + CLK_RESET_CCLK_BURST);
+
+	writel(tegra20_cpu_clk_sctx.clk_csite_src,
+					reg_clk_base + CLK_RESET_SOURCE_CSITE);
+}
+#endif
+
 static struct tegra_cpu_car_ops tegra20_cpu_car_ops = {
 	.wait_for_reset	= tegra20_wait_cpu_in_reset,
 	.put_in_reset	= tegra20_put_cpu_in_reset,
 	.out_of_reset	= tegra20_cpu_out_of_reset,
 	.enable_clock	= tegra20_enable_cpu_clock,
 	.disable_clock	= tegra20_disable_cpu_clock,
+#ifdef CONFIG_PM_SLEEP
+	.rail_off_ready = tegra20_cpu_rail_off_ready,
+	.suspend	= tegra20_cpu_clock_suspend,
+	.resume		= tegra20_cpu_clock_resume,
+#endif
 };
 
 void __init tegra20_cpu_car_ops_init(void)
-- 
1.7.0.4

WARNING: multiple messages have this Message-ID (diff)
From: josephl@nvidia.com (Joseph Lo)
To: linux-arm-kernel@lists.infradead.org
Subject: [PATCH V3 3/5] ARM: tegra20: clocks: add CPU low-power function into tegra_cpu_car_ops
Date: Tue, 18 Dec 2012 10:30:59 +0800	[thread overview]
Message-ID: <1355797861-12759-4-git-send-email-josephl@nvidia.com> (raw)
In-Reply-To: <1355797861-12759-1-git-send-email-josephl@nvidia.com>

Add suspend, resume and rail_off_ready API into tegra_cpu_car_ops. These
functions were used for CPU powered-down state maintenance.

Signed-off-by: Joseph Lo <josephl@nvidia.com>
---
V3:
* no change
V2:
* refine the code sequence in "tegra20_cpu_rail_off_ready"
---
 arch/arm/mach-tegra/tegra20_clocks.c |   99 ++++++++++++++++++++++++++++++++++
 1 files changed, 99 insertions(+), 0 deletions(-)

diff --git a/arch/arm/mach-tegra/tegra20_clocks.c b/arch/arm/mach-tegra/tegra20_clocks.c
index 4eb6bc8..1780268 100644
--- a/arch/arm/mach-tegra/tegra20_clocks.c
+++ b/arch/arm/mach-tegra/tegra20_clocks.c
@@ -159,6 +159,31 @@
 #define CPU_CLOCK(cpu)	(0x1 << (8 + cpu))
 #define CPU_RESET(cpu)	(0x1111ul << (cpu))
 
+#define CLK_RESET_CCLK_BURST	0x20
+#define CLK_RESET_CCLK_DIVIDER  0x24
+#define CLK_RESET_PLLX_BASE	0xe0
+#define CLK_RESET_PLLX_MISC	0xe4
+
+#define CLK_RESET_SOURCE_CSITE	0x1d4
+
+#define CLK_RESET_CCLK_BURST_POLICY_SHIFT	28
+#define CLK_RESET_CCLK_RUN_POLICY_SHIFT		4
+#define CLK_RESET_CCLK_IDLE_POLICY_SHIFT	0
+#define CLK_RESET_CCLK_IDLE_POLICY		1
+#define CLK_RESET_CCLK_RUN_POLICY		2
+#define CLK_RESET_CCLK_BURST_POLICY_PLLX	8
+
+#ifdef CONFIG_PM_SLEEP
+static struct cpu_clk_suspend_context {
+	u32 pllx_misc;
+	u32 pllx_base;
+
+	u32 cpu_burst;
+	u32 clk_csite_src;
+	u32 cclk_divider;
+} tegra20_cpu_clk_sctx;
+#endif
+
 static void __iomem *reg_clk_base = IO_ADDRESS(TEGRA_CLK_RESET_BASE);
 static void __iomem *reg_pmc_base = IO_ADDRESS(TEGRA_PMC_BASE);
 
@@ -1609,12 +1634,86 @@ static void tegra20_disable_cpu_clock(u32 cpu)
 	       reg_clk_base + TEGRA_CLK_RST_CONTROLLER_CLK_CPU_CMPLX);
 }
 
+#ifdef CONFIG_PM_SLEEP
+static bool tegra20_cpu_rail_off_ready(void)
+{
+	unsigned int cpu_rst_status;
+
+	cpu_rst_status = readl(reg_clk_base +
+			       TEGRA_CLK_RST_CONTROLLER_RST_CPU_CMPLX_SET);
+
+	return !!(cpu_rst_status & 0x2);
+}
+
+static void tegra20_cpu_clock_suspend(void)
+{
+	/* switch coresite to clk_m, save off original source */
+	tegra20_cpu_clk_sctx.clk_csite_src =
+				readl(reg_clk_base + CLK_RESET_SOURCE_CSITE);
+	writel(3<<30, reg_clk_base + CLK_RESET_SOURCE_CSITE);
+
+	tegra20_cpu_clk_sctx.cpu_burst =
+				readl(reg_clk_base + CLK_RESET_CCLK_BURST);
+	tegra20_cpu_clk_sctx.pllx_base =
+				readl(reg_clk_base + CLK_RESET_PLLX_BASE);
+	tegra20_cpu_clk_sctx.pllx_misc =
+				readl(reg_clk_base + CLK_RESET_PLLX_MISC);
+	tegra20_cpu_clk_sctx.cclk_divider =
+				readl(reg_clk_base + CLK_RESET_CCLK_DIVIDER);
+}
+
+static void tegra20_cpu_clock_resume(void)
+{
+	unsigned int reg, policy;
+
+	/* Is CPU complex already running on PLLX? */
+	reg = readl(reg_clk_base + CLK_RESET_CCLK_BURST);
+	policy = (reg >> CLK_RESET_CCLK_BURST_POLICY_SHIFT) & 0xF;
+
+	if (policy == CLK_RESET_CCLK_IDLE_POLICY)
+		reg = (reg >> CLK_RESET_CCLK_IDLE_POLICY_SHIFT) & 0xF;
+	else if (policy == CLK_RESET_CCLK_RUN_POLICY)
+		reg = (reg >> CLK_RESET_CCLK_RUN_POLICY_SHIFT) & 0xF;
+	else
+		BUG();
+
+	if (reg != CLK_RESET_CCLK_BURST_POLICY_PLLX) {
+		/* restore PLLX settings if CPU is on different PLL */
+		writel(tegra20_cpu_clk_sctx.pllx_misc,
+					reg_clk_base + CLK_RESET_PLLX_MISC);
+		writel(tegra20_cpu_clk_sctx.pllx_base,
+					reg_clk_base + CLK_RESET_PLLX_BASE);
+
+		/* wait for PLL stabilization if PLLX was enabled */
+		if (tegra20_cpu_clk_sctx.pllx_base & (1 << 30))
+			udelay(300);
+	}
+
+	/*
+	 * Restore original burst policy setting for calls resulting from CPU
+	 * LP2 in idle or system suspend.
+	 */
+	writel(tegra20_cpu_clk_sctx.cclk_divider,
+					reg_clk_base + CLK_RESET_CCLK_DIVIDER);
+	writel(tegra20_cpu_clk_sctx.cpu_burst,
+					reg_clk_base + CLK_RESET_CCLK_BURST);
+
+	writel(tegra20_cpu_clk_sctx.clk_csite_src,
+					reg_clk_base + CLK_RESET_SOURCE_CSITE);
+}
+#endif
+
 static struct tegra_cpu_car_ops tegra20_cpu_car_ops = {
 	.wait_for_reset	= tegra20_wait_cpu_in_reset,
 	.put_in_reset	= tegra20_put_cpu_in_reset,
 	.out_of_reset	= tegra20_cpu_out_of_reset,
 	.enable_clock	= tegra20_enable_cpu_clock,
 	.disable_clock	= tegra20_disable_cpu_clock,
+#ifdef CONFIG_PM_SLEEP
+	.rail_off_ready = tegra20_cpu_rail_off_ready,
+	.suspend	= tegra20_cpu_clock_suspend,
+	.resume		= tegra20_cpu_clock_resume,
+#endif
 };
 
 void __init tegra20_cpu_car_ops_init(void)
-- 
1.7.0.4

  parent reply	other threads:[~2012-12-18  2:30 UTC|newest]

Thread overview: 66+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2012-12-18  2:30 [PATCH V3 0/5] ARM: tegra20: cpuidle: add power-down state Joseph Lo
2012-12-18  2:30 ` Joseph Lo
     [not found] ` <1355797861-12759-1-git-send-email-josephl-DDmLM1+adcrQT0dZR+AlfA@public.gmane.org>
2012-12-18  2:30   ` [PATCH V3 1/5] ARM: tegra: add pending SGI checking API Joseph Lo
2012-12-18  2:30     ` Joseph Lo
2012-12-18  2:42     ` Colin Cross
2012-12-18  2:42       ` Colin Cross
     [not found]       ` <CAMbhsRSorDf-BebFn+t39zOK4VX4N0Fu0iPrM7XpKZcssTgX9A-JsoAwUIsXosN+BqQ9rBEUg@public.gmane.org>
2012-12-18  2:57         ` Joseph Lo
2012-12-18  2:57           ` Joseph Lo
2012-12-18 10:15         ` Peter De Schrijver
2012-12-18 10:15           ` Peter De Schrijver
     [not found]           ` <20121218101548.GO19258-Rysk9IDjsxmJz7etNGeUX8VPkgjIgRvpAL8bYrjMMd8@public.gmane.org>
2012-12-18 19:36             ` Colin Cross
2012-12-18 19:36               ` Colin Cross
     [not found]               ` <CAMbhsRSDwSoHoEs93NZhDchCS28-vQCuW2p+kqfNKeqLygL2sQ-JsoAwUIsXosN+BqQ9rBEUg@public.gmane.org>
2012-12-19  1:06                 ` Joseph Lo
2012-12-19  1:06                   ` Joseph Lo
     [not found]                   ` <1355879172.4449.10.camel-yx3yKKdKkHfc7b1ADBJPm0n48jw8i0AO@public.gmane.org>
2012-12-19  3:47                     ` Joseph Lo
2012-12-19  3:47                       ` Joseph Lo
2012-12-20  7:16                 ` Santosh Shilimkar
2012-12-20  7:16                   ` Santosh Shilimkar
     [not found]                   ` <50D2BB51.9000109-l0cyMroinI0@public.gmane.org>
2012-12-20  9:34                     ` Peter De Schrijver
2012-12-20  9:34                       ` Peter De Schrijver
     [not found]                       ` <20121220093412.GE19258-Rysk9IDjsxmJz7etNGeUX8VPkgjIgRvpAL8bYrjMMd8@public.gmane.org>
2012-12-20  9:49                         ` Santosh Shilimkar
2012-12-20  9:49                           ` Santosh Shilimkar
     [not found]                           ` <50D2DF45.1000305-l0cyMroinI0@public.gmane.org>
2012-12-20  9:59                             ` Peter De Schrijver
2012-12-20  9:59                               ` Peter De Schrijver
     [not found]                               ` <20121220095951.GG19258-Rysk9IDjsxmJz7etNGeUX8VPkgjIgRvpAL8bYrjMMd8@public.gmane.org>
2012-12-20 10:24                                 ` Santosh Shilimkar
2012-12-20 10:24                                   ` Santosh Shilimkar
     [not found]                                   ` <50D2E76C.7050309-l0cyMroinI0@public.gmane.org>
2012-12-20 11:14                                     ` Peter De Schrijver
2012-12-20 11:14                                       ` Peter De Schrijver
     [not found]                                       ` <20121220111409.GH19258-Rysk9IDjsxmJz7etNGeUX8VPkgjIgRvpAL8bYrjMMd8@public.gmane.org>
2012-12-20 12:06                                         ` Santosh Shilimkar
2012-12-20 12:06                                           ` Santosh Shilimkar
2012-12-18  2:30   ` [PATCH V3 2/5] ARM: tegra20: cpuidle: add powered-down state for secondary CPU Joseph Lo
2012-12-18  2:30     ` Joseph Lo
2012-12-18  2:46     ` Colin Cross
2012-12-18  2:46       ` Colin Cross
     [not found]       ` <CAMbhsRTLo6jS_7hqVVtgaa8_ZweAwicrgghaaFWfnzHpc6f1Pg-JsoAwUIsXosN+BqQ9rBEUg@public.gmane.org>
2012-12-18  3:06         ` Joseph Lo
2012-12-18  3:06           ` Joseph Lo
     [not found]     ` <1355797861-12759-3-git-send-email-josephl-DDmLM1+adcrQT0dZR+AlfA@public.gmane.org>
2012-12-20 17:43       ` Stephen Warren
2012-12-20 17:43         ` Stephen Warren
     [not found]         ` <50D34E28.5000208-3lzwWm7+Weoh9ZMKESR00Q@public.gmane.org>
2012-12-21  6:36           ` Joseph Lo
2012-12-21  6:36             ` Joseph Lo
     [not found]             ` <1356071804.26029.34.camel-yx3yKKdKkHfc7b1ADBJPm0n48jw8i0AO@public.gmane.org>
2012-12-21 21:04               ` Stephen Warren
2012-12-21 21:04                 ` Stephen Warren
2012-12-18  2:30   ` Joseph Lo [this message]
2012-12-18  2:30     ` [PATCH V3 3/5] ARM: tegra20: clocks: add CPU low-power function into tegra_cpu_car_ops Joseph Lo
     [not found]     ` <1355797861-12759-4-git-send-email-josephl-DDmLM1+adcrQT0dZR+AlfA@public.gmane.org>
2012-12-20 17:46       ` Stephen Warren
2012-12-20 17:46         ` Stephen Warren
     [not found]         ` <50D34F12.9080801-3lzwWm7+Weoh9ZMKESR00Q@public.gmane.org>
2012-12-21  5:02           ` Joseph Lo
2012-12-21  5:02             ` Joseph Lo
     [not found]             ` <1356066131.26029.26.camel-yx3yKKdKkHfc7b1ADBJPm0n48jw8i0AO@public.gmane.org>
2012-12-21 21:10               ` Stephen Warren
2012-12-21 21:10                 ` Stephen Warren
2012-12-18  2:31   ` [PATCH V3 4/5] ARM: tegra20: flowctrl: add support for cpu_suspend_enter/exit Joseph Lo
2012-12-18  2:31     ` Joseph Lo
2012-12-18  2:31   ` [PATCH V3 5/5] ARM: tegra20: cpuidle: apply coupled cpuidle for powered-down mode Joseph Lo
2012-12-18  2:31     ` Joseph Lo
     [not found]     ` <1355797861-12759-6-git-send-email-josephl-DDmLM1+adcrQT0dZR+AlfA@public.gmane.org>
2012-12-18 10:18       ` Peter De Schrijver
2012-12-18 10:18         ` Peter De Schrijver
2012-12-20 17:54       ` Stephen Warren
2012-12-20 17:54         ` Stephen Warren
     [not found]         ` <50D350C1.6070400-3lzwWm7+Weoh9ZMKESR00Q@public.gmane.org>
2012-12-21  7:10           ` Joseph Lo
2012-12-21  7:10             ` Joseph Lo
     [not found]             ` <1356073828.26029.49.camel-yx3yKKdKkHfc7b1ADBJPm0n48jw8i0AO@public.gmane.org>
2012-12-21 21:06               ` Stephen Warren
2012-12-21 21:06                 ` Stephen Warren
2013-01-02 19:05   ` [PATCH V3 0/5] ARM: tegra20: cpuidle: add power-down state Stephen Warren
2013-01-02 19:05     ` Stephen Warren
     [not found]     ` <50E484ED.90108-3lzwWm7+Weoh9ZMKESR00Q@public.gmane.org>
2013-01-03  8:39       ` Joseph Lo
2013-01-03  8:39         ` Joseph Lo

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=1355797861-12759-4-git-send-email-josephl@nvidia.com \
    --to=josephl-ddmlm1+adcrqt0dzr+alfa@public.gmane.org \
    --cc=ccross-z5hGa2qSFaRBDgjK7y7TUQ@public.gmane.org \
    --cc=linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r@public.gmane.org \
    --cc=linux-tegra-u79uwXL29TY76Z2rM5mHXA@public.gmane.org \
    --cc=swarren-3lzwWm7+Weoh9ZMKESR00Q@public.gmane.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.