Ventana: KBC: Removing the KBC usage on ventana
[linux-2.6.git] / arch / arm / mach-tegra / pm-t3.c
1 /*
2  * arch/arm/mach-tegra/pm-t3.c
3  *
4  * Tegra3 SOC-specific power and cluster management
5  *
6  * Copyright (c) 2009-2011, NVIDIA Corporation.
7  *
8  * This program is free software; you can redistribute it and/or modify
9  * it under the terms of the GNU General Public License as published by
10  * the Free Software Foundation; either version 2 of the License, or
11  * (at your option) any later version.
12  *
13  * This program is distributed in the hope that it will be useful, but WITHOUT
14  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
15  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
16  * more details.
17  */
18
19 #include <linux/kernel.h>
20 #include <linux/init.h>
21 #include <linux/io.h>
22 #include <linux/smp.h>
23 #include <linux/interrupt.h>
24 #include <linux/clk.h>
25 #include <linux/delay.h>
26
27 #include <mach/gpio.h>
28 #include <mach/iomap.h>
29 #include <mach/irqs.h>
30
31 #include <asm/cpu_pm.h>
32 #include <asm/hardware/gic.h>
33
34 #include <trace/events/power.h>
35
36 #include "clock.h"
37 #include "cpuidle.h"
38 #include "gpio-names.h"
39 #include "pm.h"
40 #include "sleep.h"
41 #include "tegra3_emc.h"
42
43 #ifdef CONFIG_TEGRA_CLUSTER_CONTROL
44 #define CAR_CCLK_BURST_POLICY \
45         (IO_ADDRESS(TEGRA_CLK_RESET_BASE) + 0x20)
46
47 #define CAR_SUPER_CCLK_DIVIDER \
48         (IO_ADDRESS(TEGRA_CLK_RESET_BASE) + 0x24)
49
50 #define CAR_CCLKG_BURST_POLICY \
51         (IO_ADDRESS(TEGRA_CLK_RESET_BASE) + 0x368)
52
53 #define CAR_SUPER_CCLKG_DIVIDER \
54         (IO_ADDRESS(TEGRA_CLK_RESET_BASE) + 0x36C)
55
56 #define CAR_CCLKLP_BURST_POLICY \
57         (IO_ADDRESS(TEGRA_CLK_RESET_BASE) + 0x370)
58 #define PLLX_DIV2_BYPASS_LP     (1<<16)
59
60 #define CAR_SUPER_CCLKLP_DIVIDER \
61         (IO_ADDRESS(TEGRA_CLK_RESET_BASE) + 0x374)
62
63 #define CAR_BOND_OUT_V \
64         (IO_ADDRESS(TEGRA_CLK_RESET_BASE) + 0x390)
65 #define CAR_BOND_OUT_V_CPU_G    (1<<0)
66 #define CAR_BOND_OUT_V_CPU_LP   (1<<1)
67
68 #define CAR_CLK_ENB_V_SET \
69         (IO_ADDRESS(TEGRA_CLK_RESET_BASE) + 0x440)
70 #define CAR_CLK_ENB_V_CPU_G     (1<<0)
71 #define CAR_CLK_ENB_V_CPU_LP    (1<<1)
72
73 #define CAR_RST_CPUG_CMPLX_SET \
74         (IO_ADDRESS(TEGRA_CLK_RESET_BASE) + 0x450)
75
76 #define CAR_RST_CPUG_CMPLX_CLR \
77         (IO_ADDRESS(TEGRA_CLK_RESET_BASE) + 0x454)
78
79 #define CAR_RST_CPULP_CMPLX_SET \
80         (IO_ADDRESS(TEGRA_CLK_RESET_BASE) + 0x458)
81
82 #define CAR_RST_CPULP_CMPLX_CLR \
83         (IO_ADDRESS(TEGRA_CLK_RESET_BASE) + 0x45C)
84
85 #define CAR_CLK_CPUG_CMPLX_SET \
86         (IO_ADDRESS(TEGRA_CLK_RESET_BASE) + 0x460)
87
88 #define CAR_CLK_CPUG_CMPLX_CLR \
89         (IO_ADDRESS(TEGRA_CLK_RESET_BASE) + 0x464)
90
91 #define CAR_CLK_CPULP_CMPLX_SET \
92         (IO_ADDRESS(TEGRA_CLK_RESET_BASE) + 0x468)
93
94 #define CAR_CLK_CPULP_CMPLX_CLR \
95         (IO_ADDRESS(TEGRA_CLK_RESET_BASE) + 0x46C)
96
97 #define CPU_CLOCK(cpu)  (0x1<<(8+cpu))
98 #define CPU_RESET(cpu)  (0x1111ul<<(cpu))
99
100 static int cluster_switch_prolog_clock(unsigned int flags)
101 {
102         u32 reg;
103         u32 CclkBurstPolicy;
104         u32 SuperCclkDivier;
105
106         /* Read the bond out register containing the G and LP CPUs. */
107         reg = readl(CAR_BOND_OUT_V);
108
109         /* Sync G-PLLX divider bypass with LP (no effect on G, just to prevent
110            LP settings overwrite by save/restore code */
111         CclkBurstPolicy = ~PLLX_DIV2_BYPASS_LP & readl(CAR_CCLKG_BURST_POLICY);
112         CclkBurstPolicy |= PLLX_DIV2_BYPASS_LP & readl(CAR_CCLKLP_BURST_POLICY);
113         writel(CclkBurstPolicy, CAR_CCLKG_BURST_POLICY);
114
115         /* Switching to G? */
116         if (flags & TEGRA_POWER_CLUSTER_G) {
117                 /* Do the G CPUs exist? */
118                 if (reg & CAR_BOND_OUT_V_CPU_G)
119                         return -ENXIO;
120
121                 /* Keep G CPU clock policy set by upper laayer, with the
122                    exception of the transition via LP1 */
123                 if (flags & TEGRA_POWER_SDRAM_SELFREFRESH) {
124                         /* In LP1 power mode come up on CLKM (oscillator) */
125                         CclkBurstPolicy = readl(CAR_CCLKG_BURST_POLICY);
126                         CclkBurstPolicy &= ~0xF;
127                         SuperCclkDivier = 0;
128
129                         writel(CclkBurstPolicy, CAR_CCLKG_BURST_POLICY);
130                         writel(SuperCclkDivier, CAR_SUPER_CCLKG_DIVIDER);
131                 }
132
133                 /* Hold G CPUs 1-3 in reset after the switch */
134                 reg = CPU_RESET(1) | CPU_RESET(2) | CPU_RESET(3);
135                 writel(reg, CAR_RST_CPUG_CMPLX_SET);
136
137                 /* Take G CPU 0 out of reset after the switch */
138                 reg = CPU_RESET(0);
139                 writel(reg, CAR_RST_CPUG_CMPLX_CLR);
140
141                 /* Disable the clocks on G CPUs 1-3 after the switch */
142                 reg = CPU_CLOCK(1) | CPU_CLOCK(2) | CPU_CLOCK(3);
143                 writel(reg, CAR_CLK_CPUG_CMPLX_SET);
144
145                 /* Enable the clock on G CPU 0 after the switch */
146                 reg = CPU_CLOCK(0);
147                 writel(reg, CAR_CLK_CPUG_CMPLX_CLR);
148
149                 /* Enable the G CPU complex clock after the switch */
150                 reg = CAR_CLK_ENB_V_CPU_G;
151                 writel(reg, CAR_CLK_ENB_V_SET);
152         }
153         /* Switching to LP? */
154         else if (flags & TEGRA_POWER_CLUSTER_LP) {
155                 /* Does the LP CPU exist? */
156                 if (reg & CAR_BOND_OUT_V_CPU_LP)
157                         return -ENXIO;
158
159                 /* Keep LP CPU clock policy set by upper layer, with the
160                    exception of the transition via LP1 */
161                 if (flags & TEGRA_POWER_SDRAM_SELFREFRESH) {
162                         /* In LP1 power mode come up on CLKM (oscillator) */
163                         CclkBurstPolicy = readl(CAR_CCLKLP_BURST_POLICY);
164                         CclkBurstPolicy &= ~0xF;
165                         SuperCclkDivier = 0;
166
167                         writel(CclkBurstPolicy, CAR_CCLKLP_BURST_POLICY);
168                         writel(SuperCclkDivier, CAR_SUPER_CCLKLP_DIVIDER);
169                 }
170
171                 /* Take the LP CPU ut of reset after the switch */
172                 reg = CPU_RESET(0);
173                 writel(reg, CAR_RST_CPULP_CMPLX_CLR);
174
175                 /* Enable the clock on the LP CPU after the switch */
176                 reg = CPU_CLOCK(0);
177                 writel(reg, CAR_CLK_CPULP_CMPLX_CLR);
178
179                 /* Enable the LP CPU complex clock after the switch */
180                 reg = CAR_CLK_ENB_V_CPU_LP;
181                 writel(reg, CAR_CLK_ENB_V_SET);
182         }
183
184         return 0;
185 }
186
187 void tegra_cluster_switch_prolog(unsigned int flags)
188 {
189         unsigned int target_cluster = flags & TEGRA_POWER_CLUSTER_MASK;
190         unsigned int current_cluster = is_lp_cluster()
191                                         ? TEGRA_POWER_CLUSTER_LP
192                                         : TEGRA_POWER_CLUSTER_G;
193         u32 reg;
194
195         /* Read the flow controler CSR register and clear the CPU switch
196            and immediate flags. If an actual CPU switch is to be performed,
197            re-write the CSR register with the desired values. */
198         reg = readl(FLOW_CTRL_CPU_CSR(0));
199         reg &= ~(FLOW_CTRL_CPU_CSR_IMMEDIATE_WAKE |
200                  FLOW_CTRL_CPU_CSR_SWITCH_CLUSTER);
201
202         /* Program flow controller for immediate wake if requested */
203         if (flags & TEGRA_POWER_CLUSTER_IMMEDIATE)
204                 reg |= FLOW_CTRL_CPU_CSR_IMMEDIATE_WAKE;
205
206         /* Do nothing if no switch actions requested */
207         if (!target_cluster)
208                 goto done;
209
210         if ((current_cluster != target_cluster) ||
211                 (flags & TEGRA_POWER_CLUSTER_FORCE)) {
212                 if (current_cluster != target_cluster) {
213                         // Set up the clocks for the target CPU.
214                         if (cluster_switch_prolog_clock(flags)) {
215                                 /* The target CPU does not exist */
216                                 goto done;
217                         }
218
219                         /* Set up the flow controller to switch CPUs. */
220                         reg |= FLOW_CTRL_CPU_CSR_SWITCH_CLUSTER;
221                 }
222         }
223
224 done:
225         writel(reg, FLOW_CTRL_CPU_CSR(0));
226 }
227
228 static void cluster_switch_epilog_gic(void)
229 {
230         unsigned int max_irq, i;
231         void __iomem *gic_base = IO_ADDRESS(TEGRA_ARM_INT_DIST_BASE);
232
233         /* Nothing to do if currently running on the LP CPU. */
234         if (is_lp_cluster())
235                 return;
236
237         /* Reprogram the interrupt affinity because the on the LP CPU,
238            the interrupt distributor affinity regsiters are stubbed out
239            by ARM (reads as zero, writes ignored). So when the LP CPU
240            context save code runs, the affinity registers will read
241            as all zero. This causes all interrupts to be effectively
242            disabled when back on the G CPU because they aren't routable
243            to any CPU. See bug 667720 for details. */
244
245         max_irq = readl(gic_base + GIC_DIST_CTR) & 0x1f;
246         max_irq = (max_irq + 1) * 32;
247
248         for (i = 32; i < max_irq; i += 4)
249                 writel(0x01010101, gic_base + GIC_DIST_TARGET + i * 4 / 4);
250 }
251
252 void tegra_cluster_switch_epilog(unsigned int flags)
253 {
254         u32 reg;
255
256         /* Make sure the switch and immediate flags are cleared in
257            the flow controller to prevent undesirable side-effects
258            for future users of the flow controller. */
259         reg = readl(FLOW_CTRL_CPU_CSR(0));
260         reg &= ~(FLOW_CTRL_CPU_CSR_IMMEDIATE_WAKE |
261                  FLOW_CTRL_CPU_CSR_SWITCH_CLUSTER);
262         writel(reg, FLOW_CTRL_CPU_CSR(0));
263
264         /* Perform post-switch clean-up of the interrupt distributor */
265         cluster_switch_epilog_gic();
266
267         #if DEBUG_CLUSTER_SWITCH
268         {
269                 /* FIXME: clock functions below are taking mutex */
270                 struct clk *c = tegra_get_clock_by_name(
271                         is_lp_cluster() ? "cpu_lp" : "cpu_g");
272                 DEBUG_CLUSTER(("%s: %s freq %lu\r\n", __func__,
273                         is_lp_cluster() ? "LP" : "G", clk_get_rate(c)));
274         }
275         #endif
276 }
277
278 int tegra_cluster_control(unsigned int us, unsigned int flags)
279 {
280         static ktime_t last_g2lp;
281
282         unsigned int target_cluster = flags & TEGRA_POWER_CLUSTER_MASK;
283         unsigned int current_cluster = is_lp_cluster()
284                                         ? TEGRA_POWER_CLUSTER_LP
285                                         : TEGRA_POWER_CLUSTER_G;
286         unsigned long irq_flags;
287
288         if ((target_cluster == TEGRA_POWER_CLUSTER_MASK) || !target_cluster)
289                 return -EINVAL;
290
291         if (num_online_cpus() > 1)
292                 return -EBUSY;
293
294         if ((current_cluster == target_cluster)
295         && !(flags & TEGRA_POWER_CLUSTER_FORCE))
296                 return -EEXIST;
297
298         if (target_cluster == TEGRA_POWER_CLUSTER_G)
299                 if (!is_g_cluster_present())
300                         return -EPERM;
301
302         trace_power_start(POWER_PSTATE, target_cluster, 0);
303
304         if (flags & TEGRA_POWER_CLUSTER_IMMEDIATE)
305                 us = 0;
306
307         if (current_cluster != target_cluster && !timekeeping_suspended) {
308                 if (target_cluster == TEGRA_POWER_CLUSTER_G) {
309                         s64 t = ktime_to_us(ktime_sub(ktime_get(), last_g2lp));
310                         s64 t_off = tegra_cpu_power_off_time();
311                         if (t_off > t)
312                                 udelay((unsigned int)(t_off - t));
313                 }
314                 else
315                         last_g2lp = ktime_get();
316         }
317
318         DEBUG_CLUSTER(("%s(LP%d): %s->%s %s %s %d\r\n", __func__,
319                 (flags & TEGRA_POWER_SDRAM_SELFREFRESH) ? 1 : 2,
320                 is_lp_cluster() ? "LP" : "G",
321                 (target_cluster == TEGRA_POWER_CLUSTER_G) ? "G" : "LP",
322                 (flags & TEGRA_POWER_CLUSTER_IMMEDIATE) ? "immediate" : "",
323                 (flags & TEGRA_POWER_CLUSTER_FORCE) ? "force" : "",
324                 us));
325
326         local_irq_save(irq_flags);
327         if (flags & TEGRA_POWER_SDRAM_SELFREFRESH) {
328                 if (us)
329                         tegra_lp2_set_trigger(us);
330
331                 tegra_cluster_switch_prolog(flags);
332                 tegra_suspend_dram(TEGRA_SUSPEND_LP1, flags);
333                 tegra_cluster_switch_epilog(flags);
334
335                 if (us)
336                         tegra_lp2_set_trigger(0);
337         } else {
338                 tegra_set_cpu_in_lp2(0);
339                 cpu_pm_enter();
340                 tegra_idle_lp2_last(0, flags);
341                 cpu_pm_exit();
342                 tegra_clear_cpu_in_lp2(0);
343         }
344         local_irq_restore(irq_flags);
345
346         DEBUG_CLUSTER(("%s: %s\r\n", __func__, is_lp_cluster() ? "LP" : "G"));
347
348         return 0;
349 }
350 #endif
351
352 #ifdef CONFIG_PM_SLEEP
353 static u32 mc_reserved_rsv;
354 static u32 mc_emem_arb_override;
355
356 void tegra_lp0_suspend_mc(void)
357 {
358         void __iomem *mc = IO_ADDRESS(TEGRA_MC_BASE);
359         mc_reserved_rsv = readl(mc + MC_RESERVED_RSV);
360         mc_emem_arb_override = readl(mc + MC_EMEM_ARB_OVERRIDE);
361 }
362
363 void tegra_lp0_resume_mc(void)
364 {
365         void __iomem *mc = IO_ADDRESS(TEGRA_MC_BASE);
366         writel(mc_reserved_rsv, mc + MC_RESERVED_RSV);
367         writel(mc_emem_arb_override, mc + MC_EMEM_ARB_OVERRIDE);
368 }
369
370 void tegra_lp0_cpu_mode(bool enter)
371 {
372         static bool entered_on_g = false;
373         unsigned int flags;
374
375         if (enter)
376                 entered_on_g = !is_lp_cluster();
377
378         if (entered_on_g) {
379                 flags = enter ? TEGRA_POWER_CLUSTER_LP : TEGRA_POWER_CLUSTER_G;
380                 flags |= TEGRA_POWER_CLUSTER_IMMEDIATE;
381                 tegra_cluster_control(0, flags);
382         }
383 }
384 #endif