diff options
author | Vishwanath BS <vishwanath.bs@ti.com> | 2012-06-22 10:40:02 -0400 |
---|---|---|
committer | Paul Walmsley <paul@pwsan.com> | 2012-06-22 10:40:02 -0400 |
commit | 09659fa72bf638ae986b8b80cf99309768dd0b32 (patch) | |
tree | 208420cdcfb4c40b6b2fa0c33224caa68bc10aeb | |
parent | fe7ea0062f2f846bb68447c7b813b9230285dbeb (diff) |
ARM: OMAP3: PM: Move IO Daisychain function to omap3 prm file
Since IO Daisychain modifies only PRM registers, it makes sense to move
it to PRM File. Also changed the timeout value for IO chain enable to
100us and added a wait for status disable at the end.
Thanks to Nishanth Menon <nm@ti.com> for contributing a fix to the
timeout code waiting for WUCLKOUT to go high.
Signed-off-by: Vishwanath BS <vishwanath.bs@ti.com>
Signed-off-by: Tero Kristo <t-kristo@ti.com>
Cc: Nishanth Menon <nm@ti.com>
Reviewed-by: Rajendra Nayak <rnayak@ti.com>
[paul@pwsan.com: renamed omap3_trigger_io_chain() to better describe the
end result and to match other PRM functions; removed
omap3_disable_io_chain(); moved MAX_IOPAD_LATCH_TIME to prcm-common as it
will also be used by the OMAP4 code; removed unnecessary barrier;
added kerneldoc; added credit for fix from Nishanth]
Signed-off-by: Paul Walmsley <paul@pwsan.com>
-rw-r--r-- | arch/arm/mach-omap2/pm34xx.c | 35 | ||||
-rw-r--r-- | arch/arm/mach-omap2/prcm-common.h | 8 | ||||
-rw-r--r-- | arch/arm/mach-omap2/prm2xxx_3xxx.c | 31 | ||||
-rw-r--r-- | arch/arm/mach-omap2/prm2xxx_3xxx.h | 2 |
4 files changed, 43 insertions, 33 deletions
diff --git a/arch/arm/mach-omap2/pm34xx.c b/arch/arm/mach-omap2/pm34xx.c index 6d7f0d8a3103..9d6cb7cc94ab 100644 --- a/arch/arm/mach-omap2/pm34xx.c +++ b/arch/arm/mach-omap2/pm34xx.c | |||
@@ -72,34 +72,6 @@ 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; | 73 | static struct powerdomain *cam_pwrdm; |
74 | 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_WKST) & | ||
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 | } | ||
92 | omap2_prm_clear_mod_reg_bits(OMAP3430_EN_IO_CHAIN_MASK, WKUP_MOD, | ||
93 | PM_WKEN); | ||
94 | |||
95 | } | ||
96 | |||
97 | static void omap3_disable_io_chain(void) | ||
98 | { | ||
99 | omap2_prm_clear_mod_reg_bits(OMAP3430_EN_IO_CHAIN_MASK, WKUP_MOD, | ||
100 | PM_WKEN); | ||
101 | } | ||
102 | |||
103 | static void omap3_core_save_context(void) | 75 | static void omap3_core_save_context(void) |
104 | { | 76 | { |
105 | omap3_ctrl_save_padconf(); | 77 | omap3_ctrl_save_padconf(); |
@@ -305,7 +277,7 @@ void omap_sram_idle(void) | |||
305 | core_next_state < PWRDM_POWER_ON)) { | 277 | core_next_state < PWRDM_POWER_ON)) { |
306 | omap2_prm_set_mod_reg_bits(OMAP3430_EN_IO_MASK, WKUP_MOD, PM_WKEN); | 278 | omap2_prm_set_mod_reg_bits(OMAP3430_EN_IO_MASK, WKUP_MOD, PM_WKEN); |
307 | if (omap3_has_io_chain_ctrl()) | 279 | if (omap3_has_io_chain_ctrl()) |
308 | omap3_enable_io_chain(); | 280 | omap3xxx_prm_reconfigure_io_chain(); |
309 | } | 281 | } |
310 | 282 | ||
311 | pwrdm_pre_transition(); | 283 | pwrdm_pre_transition(); |
@@ -382,12 +354,9 @@ void omap_sram_idle(void) | |||
382 | /* Disable IO-PAD and IO-CHAIN wakeup */ | 354 | /* Disable IO-PAD and IO-CHAIN wakeup */ |
383 | if (omap3_has_io_wakeup() && | 355 | if (omap3_has_io_wakeup() && |
384 | (per_next_state < PWRDM_POWER_ON || | 356 | (per_next_state < PWRDM_POWER_ON || |
385 | core_next_state < PWRDM_POWER_ON)) { | 357 | core_next_state < PWRDM_POWER_ON)) |
386 | omap2_prm_clear_mod_reg_bits(OMAP3430_EN_IO_MASK, WKUP_MOD, | 358 | omap2_prm_clear_mod_reg_bits(OMAP3430_EN_IO_MASK, WKUP_MOD, |
387 | PM_WKEN); | 359 | PM_WKEN); |
388 | if (omap3_has_io_chain_ctrl()) | ||
389 | omap3_disable_io_chain(); | ||
390 | } | ||
391 | 360 | ||
392 | clkdm_allow_idle(mpu_pwrdm->pwrdm_clkdms[0]); | 361 | clkdm_allow_idle(mpu_pwrdm->pwrdm_clkdms[0]); |
393 | } | 362 | } |
diff --git a/arch/arm/mach-omap2/prcm-common.h b/arch/arm/mach-omap2/prcm-common.h index 6da3ba483ad1..fca23cbea708 100644 --- a/arch/arm/mach-omap2/prcm-common.h +++ b/arch/arm/mach-omap2/prcm-common.h | |||
@@ -410,6 +410,14 @@ | |||
410 | */ | 410 | */ |
411 | #define MAX_MODULE_HARDRESET_WAIT 10000 | 411 | #define MAX_MODULE_HARDRESET_WAIT 10000 |
412 | 412 | ||
413 | /* | ||
414 | * Maximum time(us) it takes to output the signal WUCLKOUT of the last | ||
415 | * pad of the I/O ring after asserting WUCLKIN high. Tero measured | ||
416 | * the actual time at 7 to 8 microseconds on OMAP3 and 2 to 4 | ||
417 | * microseconds on OMAP4, so this timeout may be too high. | ||
418 | */ | ||
419 | #define MAX_IOPAD_LATCH_TIME 100 | ||
420 | |||
413 | # ifndef __ASSEMBLER__ | 421 | # ifndef __ASSEMBLER__ |
414 | extern void __iomem *prm_base; | 422 | extern void __iomem *prm_base; |
415 | extern void __iomem *cm_base; | 423 | extern void __iomem *cm_base; |
diff --git a/arch/arm/mach-omap2/prm2xxx_3xxx.c b/arch/arm/mach-omap2/prm2xxx_3xxx.c index 9ce765407ad5..7d62bd654dbe 100644 --- a/arch/arm/mach-omap2/prm2xxx_3xxx.c +++ b/arch/arm/mach-omap2/prm2xxx_3xxx.c | |||
@@ -301,6 +301,37 @@ void omap3xxx_prm_restore_irqen(u32 *saved_mask) | |||
301 | OMAP3_PRM_IRQENABLE_MPU_OFFSET); | 301 | OMAP3_PRM_IRQENABLE_MPU_OFFSET); |
302 | } | 302 | } |
303 | 303 | ||
304 | /** | ||
305 | * omap3xxx_prm_reconfigure_io_chain - clear latches and reconfigure I/O chain | ||
306 | * | ||
307 | * Clear any previously-latched I/O wakeup events and ensure that the | ||
308 | * I/O wakeup gates are aligned with the current mux settings. Works | ||
309 | * by asserting WUCLKIN, waiting for WUCLKOUT to be asserted, and then | ||
310 | * deasserting WUCLKIN and clearing the ST_IO_CHAIN WKST bit. No | ||
311 | * return value. | ||
312 | */ | ||
313 | void omap3xxx_prm_reconfigure_io_chain(void) | ||
314 | { | ||
315 | int i = 0; | ||
316 | |||
317 | omap2_prm_set_mod_reg_bits(OMAP3430_EN_IO_CHAIN_MASK, WKUP_MOD, | ||
318 | PM_WKEN); | ||
319 | |||
320 | omap_test_timeout(omap2_prm_read_mod_reg(WKUP_MOD, PM_WKST) & | ||
321 | OMAP3430_ST_IO_CHAIN_MASK, | ||
322 | MAX_IOPAD_LATCH_TIME, i); | ||
323 | if (i == MAX_IOPAD_LATCH_TIME) | ||
324 | pr_warn("PRM: I/O chain clock line assertion timed out\n"); | ||
325 | |||
326 | omap2_prm_clear_mod_reg_bits(OMAP3430_EN_IO_CHAIN_MASK, WKUP_MOD, | ||
327 | PM_WKEN); | ||
328 | |||
329 | omap2_prm_set_mod_reg_bits(OMAP3430_ST_IO_CHAIN_MASK, WKUP_MOD, | ||
330 | PM_WKST); | ||
331 | |||
332 | omap2_prm_read_mod_reg(WKUP_MOD, PM_WKST); | ||
333 | } | ||
334 | |||
304 | static int __init omap3xxx_prcm_init(void) | 335 | static int __init omap3xxx_prcm_init(void) |
305 | { | 336 | { |
306 | if (cpu_is_omap34xx()) | 337 | if (cpu_is_omap34xx()) |
diff --git a/arch/arm/mach-omap2/prm2xxx_3xxx.h b/arch/arm/mach-omap2/prm2xxx_3xxx.h index 491c72dd20a0..a8c946f318ab 100644 --- a/arch/arm/mach-omap2/prm2xxx_3xxx.h +++ b/arch/arm/mach-omap2/prm2xxx_3xxx.h | |||
@@ -317,6 +317,8 @@ extern u32 omap3_prm_vcvp_read(u8 offset); | |||
317 | extern void omap3_prm_vcvp_write(u32 val, u8 offset); | 317 | extern void omap3_prm_vcvp_write(u32 val, u8 offset); |
318 | extern u32 omap3_prm_vcvp_rmw(u32 mask, u32 bits, u8 offset); | 318 | extern u32 omap3_prm_vcvp_rmw(u32 mask, u32 bits, u8 offset); |
319 | 319 | ||
320 | extern void omap3xxx_prm_reconfigure_io_chain(void); | ||
321 | |||
320 | /* PRM interrupt-related functions */ | 322 | /* PRM interrupt-related functions */ |
321 | extern void omap3xxx_prm_read_pending_irqs(unsigned long *events); | 323 | extern void omap3xxx_prm_read_pending_irqs(unsigned long *events); |
322 | extern void omap3xxx_prm_ocp_barrier(void); | 324 | extern void omap3xxx_prm_ocp_barrier(void); |