diff options
Diffstat (limited to 'arch/arm/mach-omap2/pm44xx.c')
-rwxr-xr-x[-rw-r--r--] | arch/arm/mach-omap2/pm44xx.c | 52 |
1 files changed, 44 insertions, 8 deletions
diff --git a/arch/arm/mach-omap2/pm44xx.c b/arch/arm/mach-omap2/pm44xx.c index 7cef8ce..770cc1f 100644..100755 --- a/arch/arm/mach-omap2/pm44xx.c +++ b/arch/arm/mach-omap2/pm44xx.c @@ -23,7 +23,10 @@ #include <linux/irq.h> #include <asm/hardware/gic.h> +#include <asm/mach-types.h> + #include <mach/omap4-common.h> + #include <plat/omap_hsi.h> #include <plat/common.h> #include <plat/temperature_sensor.h> @@ -78,10 +81,30 @@ static struct powerdomain *tesla_pwrdm; /* Yet un-named erratum which requires AUTORET to be disabled for IVA PD */ #define OMAP4_PM_ERRATUM_IVA_AUTO_RET_iXXX BIT(1) +/* +* HSI - OMAP4430-2.2BUG00055: +* HSI: DSP Swakeup generated is the same than MPU Swakeup. +* System can’t enter in off mode due to the DSP. +*/ +#define OMAP4_PM_ERRATUM_HSI_SWAKEUP_iXXX BIT(2) -static u8 pm44xx_errata; + +u8 pm44xx_errata; #define is_pm44xx_erratum(erratum) (pm44xx_errata & OMAP4_PM_ERRATUM_##erratum) +/* HACK: check CAWAKE wakeup event */ +#define USBB1_ULPITLL_CLK 0x4A1000C0 +#define CONTROL_PADCONF_WAKEUPEVENT_2 0x4A1001E0 +static int cawake_event_flag = 0; +void check_cawake_wakeup_event(void) +{ + if ((omap_readl(USBB1_ULPITLL_CLK) & 0x80000000) || + (omap_readl(CONTROL_PADCONF_WAKEUPEVENT_2) & 0x2)) { + pr_info("[HSI] PORT 1 CAWAKE WAKEUP EVENT\n"); + cawake_event_flag = 1; + } +} + #define MAX_IOPAD_LATCH_TIME 1000 void omap4_trigger_ioctrl(void) { @@ -630,6 +653,10 @@ static int omap4_pm_suspend(void) * More details can be found in OMAP4430 TRM section 4.3.4.2. */ omap4_enter_sleep(0, PWRDM_POWER_OFF, true); + + /* HACK: check CAWAKE wakeup event */ + check_cawake_wakeup_event(); + omap4_print_wakeirq(); prcmdebug_dump(PRCMDEBUG_LASTSLEEP); @@ -874,7 +901,7 @@ static void __init prcm_setup_regs(void) * * Bug ref is HSI-C1BUG00106 : dsp swakeup generated by HSI same as mpu swakeup */ -static void omap_pm_clear_dsp_wake_up(void) +void omap_pm_clear_dsp_wake_up(void) { int ret; int timeout = 10; @@ -929,6 +956,7 @@ static void omap_pm_clear_dsp_wake_up(void) static irqreturn_t prcm_interrupt_handler (int irq, void *dev_id) { u32 irqenable_mpu, irqstatus_mpu; + int hsi_port; irqenable_mpu = omap4_prm_read_inst_reg(OMAP4430_PRM_OCP_SOCKET_INST, OMAP4_PRM_IRQENABLE_MPU_OFFSET); @@ -938,12 +966,19 @@ static irqreturn_t prcm_interrupt_handler (int irq, void *dev_id) /* Check if a IO_ST interrupt */ if (irqstatus_mpu & OMAP4430_IO_ST_MASK) { /* Check if HSI caused the IO wakeup */ - if (omap_hsi_is_io_wakeup_from_hsi()) { - omap_pm_clear_dsp_wake_up(); - omap_hsi_wakeup(0); - } + + /* HACK: check CAWAKE wakeup event */ + if (cawake_event_flag) { + hsi_port = 1; + cawake_event_flag = 0; + omap_hsi_wakeup(hsi_port); + } else + if (omap_hsi_is_io_wakeup_from_hsi(&hsi_port)) + omap_hsi_wakeup(hsi_port); + omap_uart_resume_idle(); - usbhs_wakeup(); + if (!machine_is_tuna()) + usbhs_wakeup(); omap_debug_uart_resume_idle(); omap4_trigger_ioctrl(); } @@ -1047,7 +1082,8 @@ static void __init omap4_pm_setup_errata(void) * all OMAP4 silica */ if (cpu_is_omap44xx()) - pm44xx_errata |= OMAP4_PM_ERRATUM_IVA_AUTO_RET_iXXX; + pm44xx_errata |= OMAP4_PM_ERRATUM_IVA_AUTO_RET_iXXX | + OMAP4_PM_ERRATUM_HSI_SWAKEUP_iXXX; } /** |