diff options
Diffstat (limited to 'arch/arm/mach-omap2/pm34xx.c')
-rw-r--r-- | arch/arm/mach-omap2/pm34xx.c | 79 |
1 files changed, 24 insertions, 55 deletions
diff --git a/arch/arm/mach-omap2/pm34xx.c b/arch/arm/mach-omap2/pm34xx.c index a34023d0ca7c..e4fc88c65dbd 100644 --- a/arch/arm/mach-omap2/pm34xx.c +++ b/arch/arm/mach-omap2/pm34xx.c | |||
@@ -70,34 +70,6 @@ void (*omap3_do_wfi_sram)(void); | |||
70 | 70 | ||
71 | static struct powerdomain *mpu_pwrdm, *neon_pwrdm; | 71 | static struct powerdomain *mpu_pwrdm, *neon_pwrdm; |
72 | static struct powerdomain *core_pwrdm, *per_pwrdm; | 72 | static struct powerdomain *core_pwrdm, *per_pwrdm; |
73 | static struct powerdomain *cam_pwrdm; | ||
74 | |||
75 | static void omap3_enable_io_chain(void) | ||
76 | { | ||
77 | int timeout = 0; | ||
78 | |||
79 | omap2_prm_set_mod_reg_bits(OMAP3430_EN_IO_CHAIN_MASK, WKUP_MOD, | ||
80 | PM_WKEN); | ||
81 | /* Do a readback to assure write has been done */ | ||
82 | omap2_prm_read_mod_reg(WKUP_MOD, PM_WKEN); | ||
83 | |||
84 | while (!(omap2_prm_read_mod_reg(WKUP_MOD, PM_WKEN) & | ||
85 | OMAP3430_ST_IO_CHAIN_MASK)) { | ||
86 | timeout++; | ||
87 | if (timeout > 1000) { | ||
88 | pr_err("Wake up daisy chain activation failed.\n"); | ||
89 | return; | ||
90 | } | ||
91 | omap2_prm_set_mod_reg_bits(OMAP3430_ST_IO_CHAIN_MASK, | ||
92 | WKUP_MOD, PM_WKEN); | ||
93 | } | ||
94 | } | ||
95 | |||
96 | static void omap3_disable_io_chain(void) | ||
97 | { | ||
98 | omap2_prm_clear_mod_reg_bits(OMAP3430_EN_IO_CHAIN_MASK, WKUP_MOD, | ||
99 | PM_WKEN); | ||
100 | } | ||
101 | 73 | ||
102 | static void omap3_core_save_context(void) | 74 | static void omap3_core_save_context(void) |
103 | { | 75 | { |
@@ -299,24 +271,22 @@ void omap_sram_idle(void) | |||
299 | /* Enable IO-PAD and IO-CHAIN wakeups */ | 271 | /* Enable IO-PAD and IO-CHAIN wakeups */ |
300 | per_next_state = pwrdm_read_next_pwrst(per_pwrdm); | 272 | per_next_state = pwrdm_read_next_pwrst(per_pwrdm); |
301 | core_next_state = pwrdm_read_next_pwrst(core_pwrdm); | 273 | core_next_state = pwrdm_read_next_pwrst(core_pwrdm); |
302 | if (omap3_has_io_wakeup() && | ||
303 | (per_next_state < PWRDM_POWER_ON || | ||
304 | core_next_state < PWRDM_POWER_ON)) { | ||
305 | omap2_prm_set_mod_reg_bits(OMAP3430_EN_IO_MASK, WKUP_MOD, PM_WKEN); | ||
306 | if (omap3_has_io_chain_ctrl()) | ||
307 | omap3_enable_io_chain(); | ||
308 | } | ||
309 | 274 | ||
310 | pwrdm_pre_transition(); | 275 | if (mpu_next_state < PWRDM_POWER_ON) { |
276 | pwrdm_pre_transition(mpu_pwrdm); | ||
277 | pwrdm_pre_transition(neon_pwrdm); | ||
278 | } | ||
311 | 279 | ||
312 | /* PER */ | 280 | /* PER */ |
313 | if (per_next_state < PWRDM_POWER_ON) { | 281 | if (per_next_state < PWRDM_POWER_ON) { |
282 | pwrdm_pre_transition(per_pwrdm); | ||
314 | per_going_off = (per_next_state == PWRDM_POWER_OFF) ? 1 : 0; | 283 | per_going_off = (per_next_state == PWRDM_POWER_OFF) ? 1 : 0; |
315 | omap2_gpio_prepare_for_idle(per_going_off); | 284 | omap2_gpio_prepare_for_idle(per_going_off); |
316 | } | 285 | } |
317 | 286 | ||
318 | /* CORE */ | 287 | /* CORE */ |
319 | if (core_next_state < PWRDM_POWER_ON) { | 288 | if (core_next_state < PWRDM_POWER_ON) { |
289 | pwrdm_pre_transition(core_pwrdm); | ||
320 | if (core_next_state == PWRDM_POWER_OFF) { | 290 | if (core_next_state == PWRDM_POWER_OFF) { |
321 | omap3_core_save_context(); | 291 | omap3_core_save_context(); |
322 | omap3_cm_save_context(); | 292 | omap3_cm_save_context(); |
@@ -369,26 +339,20 @@ void omap_sram_idle(void) | |||
369 | omap2_prm_clear_mod_reg_bits(OMAP3430_AUTO_OFF_MASK, | 339 | omap2_prm_clear_mod_reg_bits(OMAP3430_AUTO_OFF_MASK, |
370 | OMAP3430_GR_MOD, | 340 | OMAP3430_GR_MOD, |
371 | OMAP3_PRM_VOLTCTRL_OFFSET); | 341 | OMAP3_PRM_VOLTCTRL_OFFSET); |
342 | pwrdm_post_transition(core_pwrdm); | ||
372 | } | 343 | } |
373 | omap3_intc_resume_idle(); | 344 | omap3_intc_resume_idle(); |
374 | 345 | ||
375 | pwrdm_post_transition(); | ||
376 | |||
377 | /* PER */ | 346 | /* PER */ |
378 | if (per_next_state < PWRDM_POWER_ON) | 347 | if (per_next_state < PWRDM_POWER_ON) { |
379 | omap2_gpio_resume_after_idle(); | 348 | omap2_gpio_resume_after_idle(); |
380 | 349 | pwrdm_post_transition(per_pwrdm); | |
381 | /* Disable IO-PAD and IO-CHAIN wakeup */ | ||
382 | if (omap3_has_io_wakeup() && | ||
383 | (per_next_state < PWRDM_POWER_ON || | ||
384 | core_next_state < PWRDM_POWER_ON)) { | ||
385 | omap2_prm_clear_mod_reg_bits(OMAP3430_EN_IO_MASK, WKUP_MOD, | ||
386 | PM_WKEN); | ||
387 | if (omap3_has_io_chain_ctrl()) | ||
388 | omap3_disable_io_chain(); | ||
389 | } | 350 | } |
390 | 351 | ||
391 | clkdm_allow_idle(mpu_pwrdm->pwrdm_clkdms[0]); | 352 | if (mpu_next_state < PWRDM_POWER_ON) { |
353 | pwrdm_post_transition(mpu_pwrdm); | ||
354 | pwrdm_post_transition(neon_pwrdm); | ||
355 | } | ||
392 | } | 356 | } |
393 | 357 | ||
394 | static void omap3_pm_idle(void) | 358 | static void omap3_pm_idle(void) |
@@ -581,10 +545,13 @@ static void __init prcm_setup_regs(void) | |||
581 | OMAP3430_PER_MOD, OMAP3430_PM_MPUGRPSEL); | 545 | OMAP3430_PER_MOD, OMAP3430_PM_MPUGRPSEL); |
582 | 546 | ||
583 | /* Don't attach IVA interrupts */ | 547 | /* Don't attach IVA interrupts */ |
584 | omap2_prm_write_mod_reg(0, WKUP_MOD, OMAP3430_PM_IVAGRPSEL); | 548 | if (omap3_has_iva()) { |
585 | omap2_prm_write_mod_reg(0, CORE_MOD, OMAP3430_PM_IVAGRPSEL1); | 549 | omap2_prm_write_mod_reg(0, WKUP_MOD, OMAP3430_PM_IVAGRPSEL); |
586 | omap2_prm_write_mod_reg(0, CORE_MOD, OMAP3430ES2_PM_IVAGRPSEL3); | 550 | omap2_prm_write_mod_reg(0, CORE_MOD, OMAP3430_PM_IVAGRPSEL1); |
587 | omap2_prm_write_mod_reg(0, OMAP3430_PER_MOD, OMAP3430_PM_IVAGRPSEL); | 551 | omap2_prm_write_mod_reg(0, CORE_MOD, OMAP3430ES2_PM_IVAGRPSEL3); |
552 | omap2_prm_write_mod_reg(0, OMAP3430_PER_MOD, | ||
553 | OMAP3430_PM_IVAGRPSEL); | ||
554 | } | ||
588 | 555 | ||
589 | /* Clear any pending 'reset' flags */ | 556 | /* Clear any pending 'reset' flags */ |
590 | omap2_prm_write_mod_reg(0xffffffff, MPU_MOD, OMAP2_RM_RSTST); | 557 | omap2_prm_write_mod_reg(0xffffffff, MPU_MOD, OMAP2_RM_RSTST); |
@@ -598,7 +565,9 @@ static void __init prcm_setup_regs(void) | |||
598 | /* Clear any pending PRCM interrupts */ | 565 | /* Clear any pending PRCM interrupts */ |
599 | omap2_prm_write_mod_reg(0, OCP_MOD, OMAP3_PRM_IRQSTATUS_MPU_OFFSET); | 566 | omap2_prm_write_mod_reg(0, OCP_MOD, OMAP3_PRM_IRQSTATUS_MPU_OFFSET); |
600 | 567 | ||
601 | omap3_iva_idle(); | 568 | if (omap3_has_iva()) |
569 | omap3_iva_idle(); | ||
570 | |||
602 | omap3_d2d_idle(); | 571 | omap3_d2d_idle(); |
603 | } | 572 | } |
604 | 573 | ||
@@ -724,6 +693,7 @@ int __init omap3_pm_init(void) | |||
724 | ret = request_irq(omap_prcm_event_to_irq("io"), | 693 | ret = request_irq(omap_prcm_event_to_irq("io"), |
725 | _prcm_int_handle_io, IRQF_SHARED | IRQF_NO_SUSPEND, "pm_io", | 694 | _prcm_int_handle_io, IRQF_SHARED | IRQF_NO_SUSPEND, "pm_io", |
726 | omap3_pm_init); | 695 | omap3_pm_init); |
696 | enable_irq(omap_prcm_event_to_irq("io")); | ||
727 | 697 | ||
728 | if (ret) { | 698 | if (ret) { |
729 | pr_err("pm: Failed to request pm_io irq\n"); | 699 | pr_err("pm: Failed to request pm_io irq\n"); |
@@ -748,7 +718,6 @@ int __init omap3_pm_init(void) | |||
748 | neon_pwrdm = pwrdm_lookup("neon_pwrdm"); | 718 | neon_pwrdm = pwrdm_lookup("neon_pwrdm"); |
749 | per_pwrdm = pwrdm_lookup("per_pwrdm"); | 719 | per_pwrdm = pwrdm_lookup("per_pwrdm"); |
750 | core_pwrdm = pwrdm_lookup("core_pwrdm"); | 720 | core_pwrdm = pwrdm_lookup("core_pwrdm"); |
751 | cam_pwrdm = pwrdm_lookup("cam_pwrdm"); | ||
752 | 721 | ||
753 | neon_clkdm = clkdm_lookup("neon_clkdm"); | 722 | neon_clkdm = clkdm_lookup("neon_clkdm"); |
754 | mpu_clkdm = clkdm_lookup("mpu_clkdm"); | 723 | mpu_clkdm = clkdm_lookup("mpu_clkdm"); |