]> www.pilppa.org Git - linux-2.6-omap-h63xx.git/blob - arch/arm/mach-omap2/pm34xx.c
OMAP3: PM: Force IVA2 into idle during bootup
[linux-2.6-omap-h63xx.git] / arch / arm / mach-omap2 / pm34xx.c
1 /*
2  * linux/arch/arm/mach-omap2/pm34xx.c
3  *
4  * OMAP3 Power Management Routines
5  *
6  * Copyright (C) 2006-2008 Nokia Corporation
7  * Tony Lindgren <tony@atomide.com>
8  * Jouni Hogander
9  *
10  * Copyright (C) 2005 Texas Instruments, Inc.
11  * Richard Woodruff <r-woodruff2@ti.com>
12  *
13  * Based on pm.c for omap1
14  *
15  * This program is free software; you can redistribute it and/or modify
16  * it under the terms of the GNU General Public License version 2 as
17  * published by the Free Software Foundation.
18  */
19
20 #include <linux/pm.h>
21 #include <linux/suspend.h>
22 #include <linux/interrupt.h>
23 #include <linux/module.h>
24 #include <linux/list.h>
25 #include <linux/err.h>
26
27 #include <mach/gpio.h>
28 #include <mach/sram.h>
29 #include <mach/pm.h>
30 #include <mach/clockdomain.h>
31 #include <mach/powerdomain.h>
32 #include <mach/serial.h>
33 #include <mach/control.h>
34
35 #include "cm.h"
36 #include "cm-regbits-34xx.h"
37 #include "prm-regbits-34xx.h"
38
39 #include "prm.h"
40 #include "pm.h"
41 #include "smartreflex.h"
42
43 struct power_state {
44         struct powerdomain *pwrdm;
45         u32 next_state;
46         u32 saved_state;
47         struct list_head node;
48 };
49
50 static LIST_HEAD(pwrst_list);
51
52 static void (*_omap_sram_idle)(u32 *addr, int save_state);
53
54 static void (*saved_idle)(void);
55
56 static struct powerdomain *mpu_pwrdm;
57
58 /* PRCM Interrupt Handler for wakeups */
59 static irqreturn_t prcm_interrupt_handler (int irq, void *dev_id)
60 {
61         u32 wkst, irqstatus_mpu;
62         u32 fclk, iclk;
63
64         /* WKUP */
65         wkst = prm_read_mod_reg(WKUP_MOD, PM_WKST);
66         if (wkst) {
67                 iclk = cm_read_mod_reg(WKUP_MOD, CM_ICLKEN);
68                 fclk = cm_read_mod_reg(WKUP_MOD, CM_FCLKEN);
69                 cm_set_mod_reg_bits(wkst, WKUP_MOD, CM_ICLKEN);
70                 cm_set_mod_reg_bits(wkst, WKUP_MOD, CM_FCLKEN);
71                 prm_write_mod_reg(wkst, WKUP_MOD, PM_WKST);
72                 while (prm_read_mod_reg(WKUP_MOD, PM_WKST));
73                 cm_write_mod_reg(iclk, WKUP_MOD, CM_ICLKEN);
74                 cm_write_mod_reg(fclk, WKUP_MOD, CM_FCLKEN);
75         }
76
77         /* CORE */
78         wkst = prm_read_mod_reg(CORE_MOD, PM_WKST1);
79         if (wkst) {
80                 iclk = cm_read_mod_reg(CORE_MOD, CM_ICLKEN1);
81                 fclk = cm_read_mod_reg(CORE_MOD, CM_FCLKEN1);
82                 cm_set_mod_reg_bits(wkst, CORE_MOD, CM_ICLKEN1);
83                 cm_set_mod_reg_bits(wkst, CORE_MOD, CM_FCLKEN1);
84                 prm_write_mod_reg(wkst, CORE_MOD, PM_WKST1);
85                 while (prm_read_mod_reg(CORE_MOD, PM_WKST1));
86                 cm_write_mod_reg(iclk, CORE_MOD, CM_ICLKEN1);
87                 cm_write_mod_reg(fclk, CORE_MOD, CM_FCLKEN1);
88         }
89         wkst = prm_read_mod_reg(CORE_MOD, OMAP3430ES2_PM_WKST3);
90         if (wkst) {
91                 iclk = cm_read_mod_reg(CORE_MOD, CM_ICLKEN3);
92                 fclk = cm_read_mod_reg(CORE_MOD, OMAP3430ES2_CM_FCLKEN3);
93                 cm_set_mod_reg_bits(wkst, CORE_MOD, CM_ICLKEN3);
94                 cm_set_mod_reg_bits(wkst, CORE_MOD, OMAP3430ES2_CM_FCLKEN3);
95                 prm_write_mod_reg(wkst, CORE_MOD, OMAP3430ES2_PM_WKST3);
96                 while (prm_read_mod_reg(CORE_MOD, OMAP3430ES2_PM_WKST3));
97                 cm_write_mod_reg(iclk, CORE_MOD, CM_ICLKEN3);
98                 cm_write_mod_reg(fclk, CORE_MOD, OMAP3430ES2_CM_FCLKEN3);
99         }
100
101         /* PER */
102         wkst = prm_read_mod_reg(OMAP3430_PER_MOD, PM_WKST);
103         if (wkst) {
104                 iclk = cm_read_mod_reg(OMAP3430_PER_MOD, CM_ICLKEN);
105                 fclk = cm_read_mod_reg(OMAP3430_PER_MOD, CM_FCLKEN);
106                 cm_set_mod_reg_bits(wkst, OMAP3430_PER_MOD, CM_ICLKEN);
107                 cm_set_mod_reg_bits(wkst, OMAP3430_PER_MOD, CM_FCLKEN);
108                 prm_write_mod_reg(wkst, OMAP3430_PER_MOD, PM_WKST);
109                 while (prm_read_mod_reg(OMAP3430_PER_MOD, PM_WKST));
110                 cm_write_mod_reg(iclk, OMAP3430_PER_MOD, CM_ICLKEN);
111                 cm_write_mod_reg(fclk, OMAP3430_PER_MOD, CM_FCLKEN);
112         }
113
114         if (omap_rev() > OMAP3430_REV_ES1_0) {
115                 /* USBHOST */
116                 wkst = prm_read_mod_reg(OMAP3430ES2_USBHOST_MOD, PM_WKST);
117                 if (wkst) {
118                         iclk = cm_read_mod_reg(OMAP3430ES2_USBHOST_MOD,
119                                                CM_ICLKEN);
120                         fclk = cm_read_mod_reg(OMAP3430ES2_USBHOST_MOD,
121                                                CM_FCLKEN);
122                         cm_set_mod_reg_bits(wkst, OMAP3430ES2_USBHOST_MOD,
123                                          CM_ICLKEN);
124                         cm_set_mod_reg_bits(wkst, OMAP3430ES2_USBHOST_MOD,
125                                          CM_FCLKEN);
126                         prm_write_mod_reg(wkst, OMAP3430ES2_USBHOST_MOD,
127                                           PM_WKST);
128                         while (prm_read_mod_reg(OMAP3430ES2_USBHOST_MOD,
129                                                 PM_WKST));
130                         cm_write_mod_reg(iclk, OMAP3430ES2_USBHOST_MOD,
131                                          CM_ICLKEN);
132                         cm_write_mod_reg(fclk, OMAP3430ES2_USBHOST_MOD,
133                                          CM_FCLKEN);
134                 }
135         }
136
137         irqstatus_mpu = prm_read_mod_reg(OCP_MOD,
138                                         OMAP2_PRM_IRQSTATUS_MPU_OFFSET);
139         prm_write_mod_reg(irqstatus_mpu, OCP_MOD,
140                                         OMAP2_PRM_IRQSTATUS_MPU_OFFSET);
141
142         while (prm_read_mod_reg(OCP_MOD, OMAP2_PRM_IRQSTATUS_MPU_OFFSET));
143
144         return IRQ_HANDLED;
145 }
146
147 static void omap_sram_idle(void)
148 {
149         /* Variable to tell what needs to be saved and restored
150          * in omap_sram_idle*/
151         /* save_state = 0 => Nothing to save and restored */
152         /* save_state = 1 => Only L1 and logic lost */
153         /* save_state = 2 => Only L2 lost */
154         /* save_state = 3 => L1, L2 and logic lost */
155         int save_state = 0, mpu_next_state;
156
157         if (!_omap_sram_idle)
158                 return;
159
160         mpu_next_state = pwrdm_read_next_pwrst(mpu_pwrdm);
161         switch (mpu_next_state) {
162         case PWRDM_POWER_RET:
163                 /* No need to save context */
164                 save_state = 0;
165                 break;
166         default:
167                 /* Invalid state */
168                 printk(KERN_ERR "Invalid mpu state in sram_idle\n");
169                 return;
170         }
171         /* Disable smartreflex before entering WFI */
172         disable_smartreflex(SR1);
173         disable_smartreflex(SR2);
174
175         omap2_gpio_prepare_for_retention();
176         omap_uart_prepare_idle(0);
177         omap_uart_prepare_idle(1);
178         omap_uart_prepare_idle(2);
179
180         _omap_sram_idle(NULL, save_state);
181
182         omap_uart_resume_idle(2);
183         omap_uart_resume_idle(1);
184         omap_uart_resume_idle(0);
185         omap2_gpio_resume_after_retention();
186
187         /* Enable smartreflex after WFI */
188         enable_smartreflex(SR1);
189         enable_smartreflex(SR2);
190 }
191
192 /*
193  * Check if functional clocks are enabled before entering
194  * sleep. This function could be behind CONFIG_PM_DEBUG
195  * when all drivers are configuring their sysconfig registers
196  * properly and using their clocks properly.
197  */
198 static int omap3_fclks_active(void)
199 {
200         u32 fck_core1 = 0, fck_core3 = 0, fck_sgx = 0, fck_dss = 0,
201                 fck_cam = 0, fck_per = 0, fck_usbhost = 0;
202
203         fck_core1 = cm_read_mod_reg(CORE_MOD,
204                                     CM_FCLKEN1);
205         if (omap_rev() > OMAP3430_REV_ES1_0) {
206                 fck_core3 = cm_read_mod_reg(CORE_MOD,
207                                             OMAP3430ES2_CM_FCLKEN3);
208                 fck_sgx = cm_read_mod_reg(OMAP3430ES2_SGX_MOD,
209                                           CM_FCLKEN);
210                 fck_usbhost = cm_read_mod_reg(OMAP3430ES2_USBHOST_MOD,
211                                               CM_FCLKEN);
212         } else
213                 fck_sgx = cm_read_mod_reg(GFX_MOD,
214                                           OMAP3430ES2_CM_FCLKEN3);
215         fck_dss = cm_read_mod_reg(OMAP3430_DSS_MOD,
216                                   CM_FCLKEN);
217         fck_cam = cm_read_mod_reg(OMAP3430_CAM_MOD,
218                                   CM_FCLKEN);
219         fck_per = cm_read_mod_reg(OMAP3430_PER_MOD,
220                                   CM_FCLKEN);
221
222         /* Ignore UART clocks.  These are handled by UART core (serial.c) */
223         fck_core1 &= ~(OMAP3430_EN_UART1 | OMAP3430_EN_UART2);
224         fck_per &= ~OMAP3430_EN_UART3;
225
226         if (fck_core1 | fck_core3 | fck_sgx | fck_dss |
227             fck_cam | fck_per | fck_usbhost)
228                 return 1;
229         return 0;
230 }
231
232 static int omap3_can_sleep(void)
233 {
234         if (!enable_dyn_sleep)
235                 return 0;
236         if (!omap_uart_can_sleep())
237                 return 0;
238         if (omap3_fclks_active())
239                 return 0;
240         if (atomic_read(&sleep_block) > 0)
241                 return 0;
242         return 1;
243 }
244
245 /* This sets pwrdm state (other than mpu & core. Currently only ON &
246  * RET are supported. Function is assuming that clkdm doesn't have
247  * hw_sup mode enabled. */
248 static int set_pwrdm_state(struct powerdomain *pwrdm, u32 state)
249 {
250         u32 cur_state;
251         int sleep_switch = 0;
252         int ret = 0;
253
254         if (pwrdm == NULL || IS_ERR(pwrdm))
255                 return -EINVAL;
256
257         while (!(pwrdm->pwrsts & (1 << state))) {
258                 if (state == PWRDM_POWER_OFF)
259                         return ret;
260                 state--;
261         }
262
263         cur_state = pwrdm_read_next_pwrst(pwrdm);
264         if (cur_state == state)
265                 return ret;
266
267         if (pwrdm_read_pwrst(pwrdm) < PWRDM_POWER_ON) {
268                 omap2_clkdm_wakeup(pwrdm->pwrdm_clkdms[0]);
269                 sleep_switch = 1;
270                 pwrdm_wait_transition(pwrdm);
271         }
272
273         ret = pwrdm_set_next_pwrst(pwrdm, state);
274         if (ret) {
275                 printk(KERN_ERR "Unable to set state of powerdomain: %s\n",
276                        pwrdm->name);
277                 goto err;
278         }
279
280         if (sleep_switch) {
281                 omap2_clkdm_allow_idle(pwrdm->pwrdm_clkdms[0]);
282                 pwrdm_wait_transition(pwrdm);
283         }
284
285 err:
286         return ret;
287 }
288
289 static void omap3_pm_idle(void)
290 {
291         local_irq_disable();
292         local_fiq_disable();
293
294         if (!omap3_can_sleep())
295                 goto out;
296
297         if (omap_irq_pending())
298                 goto out;
299
300         omap_sram_idle();
301
302 out:
303         local_fiq_enable();
304         local_irq_enable();
305 }
306
307 static int omap3_pm_prepare(void)
308 {
309         saved_idle = pm_idle;
310         pm_idle = NULL;
311         return 0;
312 }
313
314 static int omap3_pm_suspend(void)
315 {
316         struct power_state *pwrst;
317         int state, ret = 0;
318
319         /* Read current next_pwrsts */
320         list_for_each_entry(pwrst, &pwrst_list, node)
321                 pwrst->saved_state = pwrdm_read_next_pwrst(pwrst->pwrdm);
322         /* Set ones wanted by suspend */
323         list_for_each_entry(pwrst, &pwrst_list, node) {
324                 if (set_pwrdm_state(pwrst->pwrdm, pwrst->next_state))
325                         goto restore;
326                 if (pwrdm_clear_all_prev_pwrst(pwrst->pwrdm))
327                         goto restore;
328         }
329
330         omap_uart_prepare_suspend();
331         omap_sram_idle();
332
333 restore:
334         /* Restore next_pwrsts */
335         list_for_each_entry(pwrst, &pwrst_list, node) {
336                 set_pwrdm_state(pwrst->pwrdm, pwrst->saved_state);
337                 state = pwrdm_read_prev_pwrst(pwrst->pwrdm);
338                 if (state > pwrst->next_state) {
339                         printk(KERN_INFO "Powerdomain (%s) didn't enter "
340                                "target state %d\n",
341                                pwrst->pwrdm->name, pwrst->next_state);
342                         ret = -1;
343                 }
344         }
345         if (ret)
346                 printk(KERN_ERR "Could not enter target state in pm_suspend\n");
347         else
348                 printk(KERN_INFO "Successfully put all powerdomains "
349                        "to target state\n");
350
351         return ret;
352 }
353
354 static int omap3_pm_enter(suspend_state_t state)
355 {
356         int ret = 0;
357
358         switch (state) {
359         case PM_SUSPEND_STANDBY:
360         case PM_SUSPEND_MEM:
361                 ret = omap3_pm_suspend();
362                 break;
363         default:
364                 ret = -EINVAL;
365         }
366
367         return ret;
368 }
369
370 static void omap3_pm_finish(void)
371 {
372         pm_idle = saved_idle;
373 }
374
375 static struct platform_suspend_ops omap_pm_ops = {
376         .prepare        = omap3_pm_prepare,
377         .enter          = omap3_pm_enter,
378         .finish         = omap3_pm_finish,
379         .valid          = suspend_valid_only_mem,
380 };
381
382
383 /**
384  * omap3_iva_idle(): ensure IVA is in idle so it can be put into
385  *                   retention
386  *
387  * In cases where IVA2 is activated by bootcode, it may prevent
388  * full-chip retention or off-mode because it is not idle.  This
389  * function forces the IVA2 into idle state so it can go
390  * into retention/off and thus allow full-chip retention/off.
391  *
392  **/
393 static void __init omap3_iva_idle(void)
394 {
395         /* ensure IVA2 clock is disabled */
396         cm_write_mod_reg(0, OMAP3430_IVA2_MOD, CM_FCLKEN);
397
398         /* Reset IVA2 */
399         prm_write_mod_reg(OMAP3430_RST1_IVA2 |
400                           OMAP3430_RST2_IVA2 |
401                           OMAP3430_RST3_IVA2,
402                           OMAP3430_IVA2_MOD, RM_RSTCTRL);
403
404         /* Enable IVA2 clock */
405         cm_write_mod_reg(OMAP3430_CM_FCLKEN_IVA2_EN_IVA2, 
406                          OMAP3430_IVA2_MOD, CM_FCLKEN);
407
408         /* Set IVA2 boot mode to 'idle' */
409         omap_ctrl_writel(OMAP3_IVA2_BOOTMOD_IDLE,
410                          OMAP343X_CONTROL_IVA2_BOOTMOD);
411
412         /* Un-reset IVA2 */
413         prm_write_mod_reg(0, OMAP3430_IVA2_MOD, RM_RSTCTRL);
414
415         /* Disable IVA2 clock */
416         cm_write_mod_reg(0, OMAP3430_IVA2_MOD, CM_FCLKEN);
417
418         /* Reset IVA2 */
419         prm_write_mod_reg(OMAP3430_RST1_IVA2 |
420                           OMAP3430_RST2_IVA2 |
421                           OMAP3430_RST3_IVA2,
422                           OMAP3430_IVA2_MOD, RM_RSTCTRL);
423 }
424
425 static void __init prcm_setup_regs(void)
426 {
427         /* XXX Reset all wkdeps. This should be done when initializing
428          * powerdomains */
429         prm_write_mod_reg(0, OMAP3430_IVA2_MOD, PM_WKDEP);
430         prm_write_mod_reg(0, MPU_MOD, PM_WKDEP);
431         prm_write_mod_reg(0, OMAP3430_DSS_MOD, PM_WKDEP);
432         prm_write_mod_reg(0, OMAP3430_NEON_MOD, PM_WKDEP);
433         prm_write_mod_reg(0, OMAP3430_CAM_MOD, PM_WKDEP);
434         prm_write_mod_reg(0, OMAP3430_PER_MOD, PM_WKDEP);
435         if (omap_rev() > OMAP3430_REV_ES1_0) {
436                 prm_write_mod_reg(0, OMAP3430ES2_SGX_MOD, PM_WKDEP);
437                 prm_write_mod_reg(0, OMAP3430ES2_USBHOST_MOD, PM_WKDEP);
438         } else
439                 prm_write_mod_reg(0, GFX_MOD, PM_WKDEP);
440
441         /*
442          * Enable interface clock autoidle for all modules.
443          * Note that in the long run this should be done by clockfw
444          */
445         cm_write_mod_reg(
446                 OMAP3430ES2_AUTO_MMC3 |
447                 OMAP3430ES2_AUTO_ICR |
448                 OMAP3430_AUTO_AES2 |
449                 OMAP3430_AUTO_SHA12 |
450                 OMAP3430_AUTO_DES2 |
451                 OMAP3430_AUTO_MMC2 |
452                 OMAP3430_AUTO_MMC1 |
453                 OMAP3430_AUTO_MSPRO |
454                 OMAP3430_AUTO_HDQ |
455                 OMAP3430_AUTO_MCSPI4 |
456                 OMAP3430_AUTO_MCSPI3 |
457                 OMAP3430_AUTO_MCSPI2 |
458                 OMAP3430_AUTO_MCSPI1 |
459                 OMAP3430_AUTO_I2C3 |
460                 OMAP3430_AUTO_I2C2 |
461                 OMAP3430_AUTO_I2C1 |
462                 OMAP3430_AUTO_UART2 |
463                 OMAP3430_AUTO_UART1 |
464                 OMAP3430_AUTO_GPT11 |
465                 OMAP3430_AUTO_GPT10 |
466                 OMAP3430_AUTO_MCBSP5 |
467                 OMAP3430_AUTO_MCBSP1 |
468                 OMAP3430ES1_AUTO_FAC | /* This is es1 only */
469                 OMAP3430_AUTO_MAILBOXES |
470                 OMAP3430_AUTO_OMAPCTRL |
471                 OMAP3430ES1_AUTO_FSHOSTUSB |
472                 OMAP3430_AUTO_HSOTGUSB |
473                 OMAP3430ES1_AUTO_D2D | /* This is es1 only */
474                 OMAP3430_AUTO_SSI,
475                 CORE_MOD, CM_AUTOIDLE1);
476
477         cm_write_mod_reg(
478                 OMAP3430_AUTO_PKA |
479                 OMAP3430_AUTO_AES1 |
480                 OMAP3430_AUTO_RNG |
481                 OMAP3430_AUTO_SHA11 |
482                 OMAP3430_AUTO_DES1,
483                 CORE_MOD, CM_AUTOIDLE2);
484
485         if (omap_rev() > OMAP3430_REV_ES1_0) {
486                 cm_write_mod_reg(
487                         OMAP3430ES2_AUTO_USBTLL,
488                         CORE_MOD, CM_AUTOIDLE3);
489         }
490
491         cm_write_mod_reg(
492                 OMAP3430_AUTO_WDT2 |
493                 OMAP3430_AUTO_WDT1 |
494                 OMAP3430_AUTO_GPIO1 |
495                 OMAP3430_AUTO_32KSYNC |
496                 OMAP3430_AUTO_GPT12 |
497                 OMAP3430_AUTO_GPT1 ,
498                 WKUP_MOD, CM_AUTOIDLE);
499
500         cm_write_mod_reg(
501                 OMAP3430_AUTO_DSS,
502                 OMAP3430_DSS_MOD,
503                 CM_AUTOIDLE);
504
505         cm_write_mod_reg(
506                 OMAP3430_AUTO_CAM,
507                 OMAP3430_CAM_MOD,
508                 CM_AUTOIDLE);
509
510         cm_write_mod_reg(
511                 OMAP3430_AUTO_GPIO6 |
512                 OMAP3430_AUTO_GPIO5 |
513                 OMAP3430_AUTO_GPIO4 |
514                 OMAP3430_AUTO_GPIO3 |
515                 OMAP3430_AUTO_GPIO2 |
516                 OMAP3430_AUTO_WDT3 |
517                 OMAP3430_AUTO_UART3 |
518                 OMAP3430_AUTO_GPT9 |
519                 OMAP3430_AUTO_GPT8 |
520                 OMAP3430_AUTO_GPT7 |
521                 OMAP3430_AUTO_GPT6 |
522                 OMAP3430_AUTO_GPT5 |
523                 OMAP3430_AUTO_GPT4 |
524                 OMAP3430_AUTO_GPT3 |
525                 OMAP3430_AUTO_GPT2 |
526                 OMAP3430_AUTO_MCBSP4 |
527                 OMAP3430_AUTO_MCBSP3 |
528                 OMAP3430_AUTO_MCBSP2,
529                 OMAP3430_PER_MOD,
530                 CM_AUTOIDLE);
531
532         if (omap_rev() > OMAP3430_REV_ES1_0) {
533                 cm_write_mod_reg(
534                         OMAP3430ES2_AUTO_USBHOST,
535                         OMAP3430ES2_USBHOST_MOD,
536                         CM_AUTOIDLE);
537         }
538
539         /*
540          * Set all plls to autoidle. This is needed until autoidle is
541          * enabled by clockfw
542          */
543         cm_write_mod_reg(1 << OMAP3430_AUTO_IVA2_DPLL_SHIFT,
544                          OMAP3430_IVA2_MOD, CM_AUTOIDLE2);
545         cm_write_mod_reg(1 << OMAP3430_AUTO_MPU_DPLL_SHIFT,
546                          MPU_MOD,
547                          CM_AUTOIDLE2);
548         cm_write_mod_reg((1 << OMAP3430_AUTO_PERIPH_DPLL_SHIFT) |
549                          (1 << OMAP3430_AUTO_CORE_DPLL_SHIFT),
550                          PLL_MOD,
551                          CM_AUTOIDLE);
552         cm_write_mod_reg(1 << OMAP3430ES2_AUTO_PERIPH2_DPLL_SHIFT,
553                          PLL_MOD,
554                          CM_AUTOIDLE2);
555
556         /*
557          * Enable control of expternal oscillator through
558          * sys_clkreq. In the long run clock framework should
559          * take care of this.
560          */
561         prm_rmw_mod_reg_bits(OMAP_AUTOEXTCLKMODE_MASK,
562                              1 << OMAP_AUTOEXTCLKMODE_SHIFT,
563                              OMAP3430_GR_MOD,
564                              OMAP3_PRM_CLKSRC_CTRL_OFFSET);
565
566         /* setup wakup source */
567         prm_write_mod_reg(OMAP3430_EN_IO | OMAP3430_EN_GPIO1 |
568                           OMAP3430_EN_GPT1 | OMAP3430_EN_GPT12,
569                           WKUP_MOD, PM_WKEN);
570         /* No need to write EN_IO, that is always enabled */
571         prm_write_mod_reg(OMAP3430_EN_GPIO1 | OMAP3430_EN_GPT1 |
572                           OMAP3430_EN_GPT12,
573                           WKUP_MOD, OMAP3430_PM_MPUGRPSEL);
574         /* For some reason IO doesn't generate wakeup event even if
575          * it is selected to mpu wakeup goup */
576         prm_write_mod_reg(OMAP3430_IO_EN | OMAP3430_WKUP_EN,
577                         OCP_MOD, OMAP2_PRM_IRQENABLE_MPU_OFFSET);
578
579         omap3_iva_idle();
580 }
581
582 static int __init pwrdms_setup(struct powerdomain *pwrdm)
583 {
584         struct power_state *pwrst;
585
586         if (!pwrdm->pwrsts)
587                 return 0;
588
589         pwrst = kmalloc(sizeof(struct power_state), GFP_KERNEL);
590         if (!pwrst)
591                 return -ENOMEM;
592         pwrst->pwrdm = pwrdm;
593         pwrst->next_state = PWRDM_POWER_RET;
594         list_add(&pwrst->node, &pwrst_list);
595
596         if (pwrdm_has_hdwr_sar(pwrdm))
597                 pwrdm_enable_hdwr_sar(pwrdm);
598
599         return set_pwrdm_state(pwrst->pwrdm, pwrst->next_state);
600 }
601
602 static int __init clkdms_setup(struct clockdomain *clkdm)
603 {
604         omap2_clkdm_allow_idle(clkdm);
605         return 0;
606 }
607
608 int __init omap3_pm_init(void)
609 {
610         struct power_state *pwrst, *tmp;
611         int ret;
612
613         printk(KERN_ERR "Power Management for TI OMAP3.\n");
614
615         /* XXX prcm_setup_regs needs to be before enabling hw
616          * supervised mode for powerdomains */
617         prcm_setup_regs();
618
619         ret = request_irq(INT_34XX_PRCM_MPU_IRQ,
620                           (irq_handler_t)prcm_interrupt_handler,
621                           IRQF_DISABLED, "prcm", NULL);
622         if (ret) {
623                 printk(KERN_ERR "request_irq failed to register for 0x%x\n",
624                        INT_34XX_PRCM_MPU_IRQ);
625                 goto err1;
626         }
627
628         ret = pwrdm_for_each(pwrdms_setup);
629         if (ret) {
630                 printk(KERN_ERR "Failed to setup powerdomains\n");
631                 goto err2;
632         }
633
634         (void) clkdm_for_each(clkdms_setup);
635
636         mpu_pwrdm = pwrdm_lookup("mpu_pwrdm");
637         if (mpu_pwrdm == NULL) {
638                 printk(KERN_ERR "Failed to get mpu_pwrdm\n");
639                 goto err2;
640         }
641
642         _omap_sram_idle = omap_sram_push(omap34xx_cpu_suspend,
643                                         omap34xx_cpu_suspend_sz);
644
645         suspend_set_ops(&omap_pm_ops);
646
647         pm_idle = omap3_pm_idle;
648
649 err1:
650         return ret;
651 err2:
652         free_irq(INT_34XX_PRCM_MPU_IRQ, NULL);
653         list_for_each_entry_safe(pwrst, tmp, &pwrst_list, node) {
654                 list_del(&pwrst->node);
655                 kfree(pwrst);
656         }
657         return ret;
658 }
659
660 static void __init configure_vc(void)
661 {
662         prm_write_mod_reg((R_SRI2C_SLAVE_ADDR << OMAP3430_SMPS_SA1_SHIFT) |
663                         (R_SRI2C_SLAVE_ADDR << OMAP3430_SMPS_SA0_SHIFT),
664                         OMAP3430_GR_MOD, OMAP3_PRM_VC_SMPS_SA_OFFSET);
665         prm_write_mod_reg((R_VDD2_SR_CONTROL << OMAP3430_VOLRA1_SHIFT) |
666                         (R_VDD1_SR_CONTROL << OMAP3430_VOLRA0_SHIFT),
667                         OMAP3430_GR_MOD, OMAP3_PRM_VC_SMPS_VOL_RA_OFFSET);
668
669         prm_write_mod_reg((OMAP3430_VC_CMD_VAL0_ON <<
670                 OMAP3430_VC_CMD_ON_SHIFT) |
671                 (OMAP3430_VC_CMD_VAL0_ONLP << OMAP3430_VC_CMD_ONLP_SHIFT) |
672                 (OMAP3430_VC_CMD_VAL0_RET << OMAP3430_VC_CMD_RET_SHIFT) |
673                 (OMAP3430_VC_CMD_VAL0_OFF << OMAP3430_VC_CMD_OFF_SHIFT),
674                 OMAP3430_GR_MOD, OMAP3_PRM_VC_CMD_VAL_0_OFFSET);
675
676         prm_write_mod_reg((OMAP3430_VC_CMD_VAL1_ON <<
677                 OMAP3430_VC_CMD_ON_SHIFT) |
678                 (OMAP3430_VC_CMD_VAL1_ONLP << OMAP3430_VC_CMD_ONLP_SHIFT) |
679                 (OMAP3430_VC_CMD_VAL1_RET << OMAP3430_VC_CMD_RET_SHIFT) |
680                 (OMAP3430_VC_CMD_VAL1_OFF << OMAP3430_VC_CMD_OFF_SHIFT),
681                 OMAP3430_GR_MOD, OMAP3_PRM_VC_CMD_VAL_1_OFFSET);
682
683         prm_write_mod_reg(OMAP3430_CMD1 | OMAP3430_RAV1,
684                                 OMAP3430_GR_MOD,
685                                 OMAP3_PRM_VC_CH_CONF_OFFSET);
686
687         prm_write_mod_reg(OMAP3430_MCODE_SHIFT | OMAP3430_HSEN | OMAP3430_SREN,
688                                 OMAP3430_GR_MOD,
689                                 OMAP3_PRM_VC_I2C_CFG_OFFSET);
690
691         /* Setup voltctrl and other setup times */
692         prm_write_mod_reg(OMAP3430_AUTO_RET, OMAP3430_GR_MOD,
693                         OMAP3_PRM_VOLTCTRL_OFFSET);
694
695         prm_write_mod_reg(OMAP3430_CLKSETUP_DURATION, OMAP3430_GR_MOD,
696                         OMAP3_PRM_CLKSETUP_OFFSET);
697         prm_write_mod_reg((OMAP3430_VOLTSETUP_TIME2 <<
698                         OMAP3430_SETUP_TIME2_SHIFT) |
699                         (OMAP3430_VOLTSETUP_TIME1 <<
700                         OMAP3430_SETUP_TIME1_SHIFT),
701                         OMAP3430_GR_MOD, OMAP3_PRM_VOLTSETUP1_OFFSET);
702
703         prm_write_mod_reg(OMAP3430_VOLTOFFSET_DURATION, OMAP3430_GR_MOD,
704                         OMAP3_PRM_VOLTOFFSET_OFFSET);
705         prm_write_mod_reg(OMAP3430_VOLTSETUP2_DURATION, OMAP3430_GR_MOD,
706                         OMAP3_PRM_VOLTSETUP2_OFFSET);
707 }
708
709 static int __init omap3_pm_early_init(void)
710 {
711         prm_clear_mod_reg_bits(OMAP3430_OFFMODE_POL, OMAP3430_GR_MOD,
712                                 OMAP3_PRM_POLCTRL_OFFSET);
713
714         configure_vc();
715
716         return 0;
717 }
718
719 arch_initcall(omap3_pm_early_init);