arch: arm: cortex_m: pm_s2ram: Add option for custom marking
s2ram procedure used RAM magic word for marking suspend-to-RAM. This method may not work in some cases, e.g. when global reset does not reset RAM content. In that case resuming from s2ram is detected when global reset occurred. RAM magic word method is the default but with CONFIG_PM_S2RAM_CUSTOM_MARKING a custom implementation can be provided. Signed-off-by: Krzysztof Chruściński <krzysztof.chruscinski@nordicsemi.no>
This commit is contained in:
parent
c547079cc2
commit
24082d582f
4 changed files with 67 additions and 25 deletions
|
@ -14,12 +14,11 @@
|
|||
#include <zephyr/arch/cpu.h>
|
||||
#include <zephyr/arch/common/pm_s2ram.h>
|
||||
|
||||
#define MAGIC (0xDABBAD00)
|
||||
|
||||
_ASM_FILE_PROLOGUE
|
||||
|
||||
GTEXT(pm_s2ram_mark_set)
|
||||
GTEXT(pm_s2ram_mark_check_and_clear)
|
||||
GDATA(_cpu_context)
|
||||
GDATA(marker)
|
||||
|
||||
SECTION_FUNC(TEXT, arch_pm_s2ram_suspend)
|
||||
/*
|
||||
|
@ -64,11 +63,9 @@ SECTION_FUNC(TEXT, arch_pm_s2ram_suspend)
|
|||
str r2, [r1, #___cpu_context_t_control_OFFSET]
|
||||
|
||||
/*
|
||||
* Set the marker to MAGIC value
|
||||
* Mark entering suspend to RAM.
|
||||
*/
|
||||
ldr r1, =marker
|
||||
ldr r2, =MAGIC
|
||||
str r2, [r1]
|
||||
bl pm_s2ram_mark_set
|
||||
|
||||
/*
|
||||
* Call the system_off function passed as parameter. This should never
|
||||
|
@ -82,35 +79,29 @@ SECTION_FUNC(TEXT, arch_pm_s2ram_suspend)
|
|||
*/
|
||||
|
||||
/*
|
||||
* Reset the marker
|
||||
* Reset the marking of suspend to RAM, return is ignored.
|
||||
*/
|
||||
ldr r1, =marker
|
||||
mov r2, #0x0
|
||||
str r2, [r1]
|
||||
push {r0}
|
||||
bl pm_s2ram_mark_check_and_clear
|
||||
pop {r0}
|
||||
|
||||
pop {r4-r12, lr}
|
||||
bx lr
|
||||
|
||||
|
||||
GTEXT(arch_pm_s2ram_resume)
|
||||
SECTION_FUNC(TEXT, arch_pm_s2ram_resume)
|
||||
/*
|
||||
* Check if the marker is set
|
||||
* Check if reset occurred after suspending to RAM.
|
||||
*/
|
||||
ldr r0, =marker
|
||||
ldr r0, [r0]
|
||||
ldr r1, =MAGIC
|
||||
cmp r0, r1
|
||||
push {lr}
|
||||
bl pm_s2ram_mark_check_and_clear
|
||||
cmp r0, #0x1
|
||||
pop {lr}
|
||||
beq resume
|
||||
bx lr
|
||||
|
||||
resume:
|
||||
/*
|
||||
* Reset the marker
|
||||
*/
|
||||
ldr r0, =marker
|
||||
mov r1, #0x0
|
||||
str r1, [r0]
|
||||
|
||||
/*
|
||||
* Restore the CPU context
|
||||
*/
|
||||
|
|
|
@ -9,12 +9,33 @@
|
|||
|
||||
#include <zephyr/arch/common/pm_s2ram.h>
|
||||
|
||||
#define MAGIC (0xDABBAD00)
|
||||
|
||||
/**
|
||||
* CPU context for S2RAM
|
||||
*/
|
||||
__noinit _cpu_context_t _cpu_context;
|
||||
|
||||
#ifndef CONFIG_PM_S2RAM_CUSTOM_MARKING
|
||||
/**
|
||||
* S2RAM Marker
|
||||
*/
|
||||
__noinit uint32_t marker;
|
||||
static __noinit uint32_t marker;
|
||||
|
||||
void pm_s2ram_mark_set(void)
|
||||
{
|
||||
marker = MAGIC;
|
||||
}
|
||||
|
||||
bool pm_s2ram_mark_check_and_clear(void)
|
||||
{
|
||||
if (marker == MAGIC) {
|
||||
marker = 0;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
#endif /* CONFIG_PM_S2RAM_CUSTOM_MARKING */
|
||||
|
|
|
@ -7,7 +7,6 @@
|
|||
*
|
||||
* @brief public S2RAM APIs.
|
||||
* @defgroup pm_s2ram S2RAM APIs
|
||||
* @ingroup subsys_pm
|
||||
* @{
|
||||
*/
|
||||
|
||||
|
@ -57,6 +56,30 @@ typedef int (*pm_s2ram_system_off_fn_t)(void);
|
|||
*/
|
||||
int arch_pm_s2ram_suspend(pm_s2ram_system_off_fn_t system_off);
|
||||
|
||||
/**
|
||||
* @brief Mark that core is entering suspend-to-RAM state.
|
||||
*
|
||||
* Function is called when system state is stored to RAM, just before going to system
|
||||
* off.
|
||||
*
|
||||
* Default implementation is setting a magic word in RAM. CONFIG_PM_S2RAM_CUSTOM_MARKING
|
||||
* allows custom implementation.
|
||||
*/
|
||||
void pm_s2ram_mark_set(void);
|
||||
|
||||
/**
|
||||
* @brief Check suspend-to-RAM marking and clear its state.
|
||||
*
|
||||
* Function is used to determine if resuming after suspend-to-RAM shall be performed
|
||||
* or standard boot code shall be executed.
|
||||
*
|
||||
* Default implementation is checking a magic word in RAM. CONFIG_PM_S2RAM_CUSTOM_MARKING
|
||||
* allows custom implementation.
|
||||
*
|
||||
* @retval true if marking is found which indicates resuming after suspend-to-RAM.
|
||||
* @retval false if marking is not found which indicates standard boot.
|
||||
*/
|
||||
bool pm_s2ram_mark_check_and_clear(void);
|
||||
/**
|
||||
* @}
|
||||
*/
|
||||
|
|
|
@ -37,6 +37,13 @@ config PM_S2RAM
|
|||
help
|
||||
This option enables suspend-to-RAM (S2RAM).
|
||||
|
||||
config PM_S2RAM_CUSTOM_MARKING
|
||||
bool "Use custom marking functions"
|
||||
depends on PM_S2RAM
|
||||
help
|
||||
By default a magic word in RAM is used to mark entering suspend-to-RAM. Enabling
|
||||
this option allows custom implementation of functions which handles the marking.
|
||||
|
||||
config PM_NEED_ALL_DEVICES_IDLE
|
||||
bool "System Low Power Mode Needs All Devices Idle"
|
||||
depends on PM_DEVICE && !SMP
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue