I'm trying to use the LLWU triggered by LPTMR0 on a K22F to wake from sleep. I've based my code so far on this guide:
Starting Point for Kinetis Low Power LLS Mode | MCU on Eclipse
My goal is to put the system into low-power mode, then periodically wake using a low-power timer *without* resetting system state. So, I don't want to re-enter at main; I just want the MCU to pause while it's sleeping until the timer goes off.
The timer interrupt is being triggered but Cpu_OnLLSWakeUpINT is never executed after the processor goes back to sleep. Here's some background on my configuration:
-LPTMR0 configured to use LPO_1kHzSrc
-Very low power mode, Low leakage stop mode, Very low leakage stop mode all enabled under Cpu component
-LPTMR0 checked under "LLWU Settings" under Cpu component
-interrupt request enabled under LLWU Settings, Interrupts
-interrupt priority set to Highest
-Return to wait after ISR is disabled for both WAIT and SLEEP
My best guess is that this is happening because the TimerUnit_LDD interrupt handler is clearing the LPTMR0 before Cpu_OnLLSWakeUpINT gets executed. In fact, I can see this line in the PE-generated code for the timer unit:
PE_ISR(WakeupTimer_Interrupt)
{
/* {Default RTOS Adapter} ISR parameter is passed through the global variable */
WakeupTimer_TDeviceDataPtr DeviceDataPrv = INT_LPTMR0__DEFAULT_RTOS_ISRPARAM;
LPTMR_PDD_ClearInterruptFlag(LPTMR0_BASE_PTR); /* Clear interrupt flag */
WakeupTimer_OnCounterRestart(DeviceDataPrv->UserDataPtr); /* Invoke OnCounterRestart event */
}
What I don't understand: in the blog post above, the PE-generated code seems to be working fine according to the author.
Something I don't quite understand: what's the distinction between the TimerInterrupt event vs. the Cpu_OnLLSWakeUpINT event? If I have configured LPTMR0 as a LLWU source, I would expect that both the TimerInterrupt event and the LLSWakeUp event to occur.
-------------------
Updates:
1) Could this be caused by the fact that LPTMR is enabled as an LLWU source but LPTMR_CMR is not?
2) Somehow, *other* interrupts (not the LPTMR) are able to wake the processor and start it running again. I've set a breakpoint in Cpu_OnLLSWakeUpINT and it doesn't appear to be executed, so I'm not sure how or if the processor is waking. For example, I can transmit a UART character into my MCU (which triggers a different interrupt) and then everything starts running again. These other interrupts are not LLWU sources.
已解决! 转到解答。
Ok, I've got this partially solved: Cpu_OnLLSWakeUpINT is now being executed as intended.
I think the big change was using the mode DOM_STOP instead of DOM_WAIT. I never saw Cpu_OnLLSWakeUpINT execute after transitioning to DOM_WAIT.
Under the Cpu component settings for PE, I noticed that the configuration under Low Power Mode Settings -> Operation Mode Settings -> WAIT does not have any drop-down box for selecting the equivalent ARM Cortex mode. This made me suspect that I was entering some unknown state using the function Cpu_SetOperationMode(DOM_WAIT, NULL, NULL).
To answer some of my other questions in case someone else is reading:
-I didn't have to modify any PE-generated code to get this working
-both Cpu_OnLLSWakeUpINT and the timer interrupt are being executed on wake despite the fact that both interrupts perform the following flag-clearing (this is the desired behavior from my perspective):
LPTMR_PDD_ClearInterruptFlag(LPTMR0_BASE_PTR); /* Clear interrupt flag */
The flag-clearing may be redundant and there may be other factors here, but at least future readers can confirm that waking from LLWU using LPTMR along with a TimerInt is possible (without reseting MCU either).
Ok, I've got this partially solved: Cpu_OnLLSWakeUpINT is now being executed as intended.
I think the big change was using the mode DOM_STOP instead of DOM_WAIT. I never saw Cpu_OnLLSWakeUpINT execute after transitioning to DOM_WAIT.
Under the Cpu component settings for PE, I noticed that the configuration under Low Power Mode Settings -> Operation Mode Settings -> WAIT does not have any drop-down box for selecting the equivalent ARM Cortex mode. This made me suspect that I was entering some unknown state using the function Cpu_SetOperationMode(DOM_WAIT, NULL, NULL).
To answer some of my other questions in case someone else is reading:
-I didn't have to modify any PE-generated code to get this working
-both Cpu_OnLLSWakeUpINT and the timer interrupt are being executed on wake despite the fact that both interrupts perform the following flag-clearing (this is the desired behavior from my perspective):
LPTMR_PDD_ClearInterruptFlag(LPTMR0_BASE_PTR); /* Clear interrupt flag */
The flag-clearing may be redundant and there may be other factors here, but at least future readers can confirm that waking from LLWU using LPTMR along with a TimerInt is possible (without reseting MCU either).