aboutsummaryrefslogtreecommitdiffstats
path: root/arch/arm/mach-omap2/omap_hwmod.c
diff options
context:
space:
mode:
authorOlof Johansson <olof@lixom.net>2012-04-05 20:09:45 -0400
committerOlof Johansson <olof@lixom.net>2012-04-05 20:09:45 -0400
commita8f5b6e5ef0faf64997bfa87698aaabc989e64c4 (patch)
tree9eb41f6030258dc174c72c5431e690ee70ae750c /arch/arm/mach-omap2/omap_hwmod.c
parent1ac02d795889d1828a66d4b3a3fd66492d1d7cf2 (diff)
parenta9dd31b744a033b4324c93cec4ecb4c74061e2cf (diff)
Merge tag 'omap-fixes-a2-for-3.4rc' of git://git.kernel.org/pub/scm/linux/kernel/git/pjw/omap-pending into fixes
From Paul Walmsley: OMAP clock, powerdomain, clockdomain, and hwmod fixes intended for the early v3.4-rc series. Also contains an HSMMC integration refinement of an earlier hardware bug workaround. * tag 'omap-fixes-a2-for-3.4rc' of git://git.kernel.org/pub/scm/linux/kernel/git/pjw/omap-pending: ARM: OMAP2+: hwmod: Fix wrong SYSC_TYPE1_XXX_MASK bit definitions ARM: OMAP2+: hwmod: Make omap_hwmod_softreset wait for reset status ARM: OMAP2+: hwmod: Restore sysc after a reset ARM: OMAP2+: omap_hwmod: Allow io_ring wakeup configuration for all modules ARM: OMAP3: clock data: fill in some missing clockdomains ARM: OMAP4: clock data: Force a DPLL clkdm/pwrdm ON before a relock ARM: OMAP4: clock data: fix mult and div mask for USB_DPLL ARM: OMAP2+: powerdomain: Wait for powerdomain transition in pwrdm_state_switch() ARM: OMAP AM3517/3505: clock data: change EMAC clocks aliases ARM: OMAP: clock: fix race in disable all clocks ARM: OMAP4: hwmod data: Add aliases for McBSP fclk clocks ARM: OMAP3xxx: clock data: fix DPLL4 CLKSEL masks ARM: OMAP3xxx: HSMMC: avoid erratum workaround when transceiver is attached ARM: OMAP44xx: clockdomain data: correct the emu_sys_clkdm CLKTRCTRL data
Diffstat (limited to 'arch/arm/mach-omap2/omap_hwmod.c')
-rw-r--r--arch/arm/mach-omap2/omap_hwmod.c88
1 files changed, 38 insertions, 50 deletions
diff --git a/arch/arm/mach-omap2/omap_hwmod.c b/arch/arm/mach-omap2/omap_hwmod.c
index f9b9bb9c3e3..2c27fdb61e6 100644
--- a/arch/arm/mach-omap2/omap_hwmod.c
+++ b/arch/arm/mach-omap2/omap_hwmod.c
@@ -1479,6 +1479,11 @@ static int _reset(struct omap_hwmod *oh)
1479 1479
1480 ret = (oh->class->reset) ? oh->class->reset(oh) : _ocp_softreset(oh); 1480 ret = (oh->class->reset) ? oh->class->reset(oh) : _ocp_softreset(oh);
1481 1481
1482 if (oh->class->sysc) {
1483 _update_sysc_cache(oh);
1484 _enable_sysc(oh);
1485 }
1486
1482 return ret; 1487 return ret;
1483} 1488}
1484 1489
@@ -1788,20 +1793,9 @@ static int _setup(struct omap_hwmod *oh, void *data)
1788 return 0; 1793 return 0;
1789 } 1794 }
1790 1795
1791 if (!(oh->flags & HWMOD_INIT_NO_RESET)) { 1796 if (!(oh->flags & HWMOD_INIT_NO_RESET))
1792 _reset(oh); 1797 _reset(oh);
1793 1798
1794 /*
1795 * OCP_SYSCONFIG bits need to be reprogrammed after a softreset.
1796 * The _enable() function should be split to
1797 * avoid the rewrite of the OCP_SYSCONFIG register.
1798 */
1799 if (oh->class->sysc) {
1800 _update_sysc_cache(oh);
1801 _enable_sysc(oh);
1802 }
1803 }
1804
1805 postsetup_state = oh->_postsetup_state; 1799 postsetup_state = oh->_postsetup_state;
1806 if (postsetup_state == _HWMOD_STATE_UNKNOWN) 1800 if (postsetup_state == _HWMOD_STATE_UNKNOWN)
1807 postsetup_state = _HWMOD_STATE_ENABLED; 1801 postsetup_state = _HWMOD_STATE_ENABLED;
@@ -1909,20 +1903,10 @@ void omap_hwmod_write(u32 v, struct omap_hwmod *oh, u16 reg_offs)
1909 */ 1903 */
1910int omap_hwmod_softreset(struct omap_hwmod *oh) 1904int omap_hwmod_softreset(struct omap_hwmod *oh)
1911{ 1905{
1912 u32 v; 1906 if (!oh)
1913 int ret;
1914
1915 if (!oh || !(oh->_sysc_cache))
1916 return -EINVAL; 1907 return -EINVAL;
1917 1908
1918 v = oh->_sysc_cache; 1909 return _ocp_softreset(oh);
1919 ret = _set_softreset(oh, &v);
1920 if (ret)
1921 goto error;
1922 _write_sysconfig(v, oh);
1923
1924error:
1925 return ret;
1926} 1910}
1927 1911
1928/** 1912/**
@@ -2465,26 +2449,28 @@ int omap_hwmod_del_initiator_dep(struct omap_hwmod *oh,
2465 * @oh: struct omap_hwmod * 2449 * @oh: struct omap_hwmod *
2466 * 2450 *
2467 * Sets the module OCP socket ENAWAKEUP bit to allow the module to 2451 * Sets the module OCP socket ENAWAKEUP bit to allow the module to
2468 * send wakeups to the PRCM. Eventually this should sets PRCM wakeup 2452 * send wakeups to the PRCM, and enable I/O ring wakeup events for
2469 * registers to cause the PRCM to receive wakeup events from the 2453 * this IP block if it has dynamic mux entries. Eventually this
2470 * module. Does not set any wakeup routing registers beyond this 2454 * should set PRCM wakeup registers to cause the PRCM to receive
2471 * point - if the module is to wake up any other module or subsystem, 2455 * wakeup events from the module. Does not set any wakeup routing
2472 * that must be set separately. Called by omap_device code. Returns 2456 * registers beyond this point - if the module is to wake up any other
2473 * -EINVAL on error or 0 upon success. 2457 * module or subsystem, that must be set separately. Called by
2458 * omap_device code. Returns -EINVAL on error or 0 upon success.
2474 */ 2459 */
2475int omap_hwmod_enable_wakeup(struct omap_hwmod *oh) 2460int omap_hwmod_enable_wakeup(struct omap_hwmod *oh)
2476{ 2461{
2477 unsigned long flags; 2462 unsigned long flags;
2478 u32 v; 2463 u32 v;
2479 2464
2480 if (!oh->class->sysc ||
2481 !(oh->class->sysc->sysc_flags & SYSC_HAS_ENAWAKEUP))
2482 return -EINVAL;
2483
2484 spin_lock_irqsave(&oh->_lock, flags); 2465 spin_lock_irqsave(&oh->_lock, flags);
2485 v = oh->_sysc_cache; 2466
2486 _enable_wakeup(oh, &v); 2467 if (oh->class->sysc &&
2487 _write_sysconfig(v, oh); 2468 (oh->class->sysc->sysc_flags & SYSC_HAS_ENAWAKEUP)) {
2469 v = oh->_sysc_cache;
2470 _enable_wakeup(oh, &v);
2471 _write_sysconfig(v, oh);
2472 }
2473
2488 _set_idle_ioring_wakeup(oh, true); 2474 _set_idle_ioring_wakeup(oh, true);
2489 spin_unlock_irqrestore(&oh->_lock, flags); 2475 spin_unlock_irqrestore(&oh->_lock, flags);
2490 2476
@@ -2496,26 +2482,28 @@ int omap_hwmod_enable_wakeup(struct omap_hwmod *oh)
2496 * @oh: struct omap_hwmod * 2482 * @oh: struct omap_hwmod *
2497 * 2483 *
2498 * Clears the module OCP socket ENAWAKEUP bit to prevent the module 2484 * Clears the module OCP socket ENAWAKEUP bit to prevent the module
2499 * from sending wakeups to the PRCM. Eventually this should clear 2485 * from sending wakeups to the PRCM, and disable I/O ring wakeup
2500 * PRCM wakeup registers to cause the PRCM to ignore wakeup events 2486 * events for this IP block if it has dynamic mux entries. Eventually
2501 * from the module. Does not set any wakeup routing registers beyond 2487 * this should clear PRCM wakeup registers to cause the PRCM to ignore
2502 * this point - if the module is to wake up any other module or 2488 * wakeup events from the module. Does not set any wakeup routing
2503 * subsystem, that must be set separately. Called by omap_device 2489 * registers beyond this point - if the module is to wake up any other
2504 * code. Returns -EINVAL on error or 0 upon success. 2490 * module or subsystem, that must be set separately. Called by
2491 * omap_device code. Returns -EINVAL on error or 0 upon success.
2505 */ 2492 */
2506int omap_hwmod_disable_wakeup(struct omap_hwmod *oh) 2493int omap_hwmod_disable_wakeup(struct omap_hwmod *oh)
2507{ 2494{
2508 unsigned long flags; 2495 unsigned long flags;
2509 u32 v; 2496 u32 v;
2510 2497
2511 if (!oh->class->sysc ||
2512 !(oh->class->sysc->sysc_flags & SYSC_HAS_ENAWAKEUP))
2513 return -EINVAL;
2514
2515 spin_lock_irqsave(&oh->_lock, flags); 2498 spin_lock_irqsave(&oh->_lock, flags);
2516 v = oh->_sysc_cache; 2499
2517 _disable_wakeup(oh, &v); 2500 if (oh->class->sysc &&
2518 _write_sysconfig(v, oh); 2501 (oh->class->sysc->sysc_flags & SYSC_HAS_ENAWAKEUP)) {
2502 v = oh->_sysc_cache;
2503 _disable_wakeup(oh, &v);
2504 _write_sysconfig(v, oh);
2505 }
2506
2519 _set_idle_ioring_wakeup(oh, false); 2507 _set_idle_ioring_wakeup(oh, false);
2520 spin_unlock_irqrestore(&oh->_lock, flags); 2508 spin_unlock_irqrestore(&oh->_lock, flags);
2521 2509