Dave Gerlach <d-gerlach@xxxxxx> writes: > On 08/27/2013 04:45 PM, Kevin Hilman wrote: >> Dave Gerlach <d-gerlach@xxxxxx> writes: >> >>> From: Vaibhav Bedia <vaibhav.bedia@xxxxxx> >>> >>> AM335x supports various low power modes as documented >>> in section 8.1.4.3 of the AM335x TRM which is available >>> @ http://www.ti.com/litv/pdf/spruh73f >>> >>> DeepSleep0 mode offers the lowest power mode with limited >>> wakeup sources without a system reboot and is mapped as >>> the suspend state in the kernel. In this state, MPU and >>> PER domains are turned off with the internal RAM held in >>> retention to facilitate resume process. As part of the boot >>> process, the assembly code is copied over to OCMCRAM using >>> the OMAP SRAM code. >>> >>> AM335x has a Cortex-M3 (WKUP_M3) which assists the MPU >>> in DeepSleep0 entry and exit. WKUP_M3 takes care of the >>> clockdomain and powerdomain transitions based on the >>> intended low power state. MPU needs to load the appropriate >>> WKUP_M3 binary onto the WKUP_M3 memory space before it can >>> leverage any of the PM features like DeepSleep. >>> >>> The IPC mechanism between MPU and WKUP_M3 uses a mailbox >>> sub-module and 8 IPC registers in the Control module. MPU >>> uses the assigned Mailbox for issuing an interrupt to >>> WKUP_M3 which then goes and checks the IPC registers for >>> the payload. WKUP_M3 has the ability to trigger on interrupt >> >> s/trigger on interrupt/trigger an interrupt/ ?? > > Oops I will fix that. > >> >>> to MPU by executing the "sev" instruction. >>> >>> In the current implementation when the suspend process >>> is initiated MPU interrupts the WKUP_M3 to let it know about >>> the intent of entering DeepSleep0 and waits for an ACK. When >>> the ACK is received MPU continues with its suspend process >>> to suspend all the drivers and then jumps to assembly in >>> OCMC RAM. The assembly code puts the PLLs in bypass, puts the >>> external RAM in self-refresh mode and then finally execute the >>> WFI instruction. Execution of the WFI instruction triggers another >>> interrupt to the WKUP_M3 which then continues wiht the power down >>> sequence wherein the clockdomain and powerdomain transition takes >>> place. As part of the sleep sequence, WKUP_M3 unmasks the interrupt >>> lines for the wakeup sources. WFI execution on WKUP_M3 causes the >>> hardware to disable the main oscillator of the SoC. >>> >>> When a wakeup event occurs, WKUP_M3 starts the power-up >>> sequence by switching on the power domains and finally >>> enabling the clock to MPU. Since the MPU gets powered down >>> as part of the sleep sequence in the resume path ROM code >>> starts executing. The ROM code detects a wakeup from sleep >>> and then jumps to the resume location in OCMC which was >>> populated in one of the IPC registers as part of the suspend >>> sequence. >>> >>> The low level code in OCMC relocks the PLLs, enables access >>> to external RAM and then jumps to the cpu_resume code of >>> the kernel to finish the resume process. >> >> [...] >> >>> arch/arm/mach-omap2/pm33xx.c | 474 +++++++++++++++++++++++++++++++++++++++++ >>> arch/arm/mach-omap2/pm33xx.h | 77 +++++++ >>> arch/arm/mach-omap2/wkup_m3.c | 183 ++++++++++++++++ >> >> >> Looking closer at this code as I'm trying to fully get my head around >> all the IPC, I have some more comments. >> >> I think the split between pm33xx.c and the M3 driver is still confusing >> here. For example, am33xx_ping_wkup_m3(), >> am33xx_m3_state_machine_reset() and the guts of am33xx_pm_begin() all >> belong inside the M3 driver, along with all the wakeup_src stuff, which >> is info coming from the M3. >> >> IOW, the communication with M3 should be abstracted from pm33xx by the >> M3 driver (or possibly an eventual remoteproc/rpmsg implementation) with >> a well defined API. In this implementation, the interface is pretty >> fuzzy and mixed between pm33xx.c and wkup_m3.c. > > I have since moved much more of the m3 functionality, including the > ping and wakeup src code, into the wkup_m3 driver to make the split > more clear but I haven't yet moved the state machine portion into the > wkup_m3 driver. I feel that this is the portion of the IPC that could > potentially be the most variant between different SoC implementations > so leaving this in the pm code should allow for more flexibility. I still think this belogs in the M3 driver, because AFAICT, it's specific to the M3 firmware, not to the SoC. >> >> Kevin >> >> P.S. I'd also suggest renaming wakeup_src to something else since >> it's close to wakeup_source which has a rather different meaning in the >> kernel (c.f. linux/pm_wakeup.h) >> > > I will rename this to tie it into the M3 code. Great, thanks. Kevin -- To unsubscribe from this list: send the line "unsubscribe linux-omap" in the body of a message to majordomo@xxxxxxxxxxxxxxx More majordomo info at http://vger.kernel.org/majordomo-info.html