diff --git a/drivers/timer/Kconfig.nrf_grtc b/drivers/timer/Kconfig.nrf_grtc index 24534ae3f95c..ab230245ebfd 100644 --- a/drivers/timer/Kconfig.nrf_grtc +++ b/drivers/timer/Kconfig.nrf_grtc @@ -6,6 +6,7 @@ menuconfig NRF_GRTC_TIMER default y depends on DT_HAS_NORDIC_NRF_GRTC_ENABLED select TICKLESS_CAPABLE + select SYSTEM_TIMER_HAS_DISABLE_SUPPORT select TIMER_HAS_64BIT_CYCLE_COUNTER select NRFX_GRTC help diff --git a/drivers/timer/nrf_grtc_timer.c b/drivers/timer/nrf_grtc_timer.c index 22aed43d8e47..204690a04cd0 100644 --- a/drivers/timer/nrf_grtc_timer.c +++ b/drivers/timer/nrf_grtc_timer.c @@ -366,6 +366,10 @@ uint64_t z_nrf_grtc_timer_startup_value_get(void) #if defined(CONFIG_POWEROFF) && defined(CONFIG_NRF_GRTC_START_SYSCOUNTER) int z_nrf_grtc_wakeup_prepare(uint64_t wake_time_us) { + if (!nrfx_grtc_init_check()) { + return -ENOTSUP; + } + nrfx_err_t err_code; static uint8_t systemoff_channel; uint64_t now = counter(); @@ -463,6 +467,21 @@ ISR_DIRECT_DECLARE(nrfx_grtc_direct_irq_handler) } #endif +void sys_clock_disable(void) +{ + nrfx_grtc_uninit(); +#if defined(CONFIG_CLOCK_CONTROL_NRF) + int err; + struct onoff_manager *mgr = + z_nrf_clock_control_get_onoff((clock_control_subsys_t)CLOCK_CONTROL_NRF_TYPE_LFCLK); + + err = onoff_release(mgr); + __ASSERT_NO_MSG(err >= 0); + + nrfx_coredep_delay_us(1000); +#endif +} + static int sys_clock_driver_init(void) { nrfx_err_t err_code; diff --git a/samples/boards/nordic/system_off/Kconfig b/samples/boards/nordic/system_off/Kconfig index c7b4a9f85575..f5e5ce944acc 100644 --- a/samples/boards/nordic/system_off/Kconfig +++ b/samples/boards/nordic/system_off/Kconfig @@ -23,4 +23,9 @@ config LPCOMP_WAKEUP_ENABLE help Enable system off wakeup from analog comparator. +config SYS_CLOCK_DISABLE + bool "Power down system clock before system off" + help + System clock and GRTC will be switched off during system off. + source "Kconfig.zephyr" diff --git a/samples/boards/nordic/system_off/sample.yaml b/samples/boards/nordic/system_off/sample.yaml index b11f3439e7f6..ce9321a845b3 100644 --- a/samples/boards/nordic/system_off/sample.yaml +++ b/samples/boards/nordic/system_off/sample.yaml @@ -47,6 +47,44 @@ tests: - "Off count: 0" - "Active Ticks:" - "Entering system off; press sw0 to restart" + sample.boards.nrf.system_off.grtc_off: + platform_allow: + - nrf54l15dk/nrf54l05/cpuapp + - nrf54l15dk/nrf54l10/cpuapp + - nrf54l15dk/nrf54l15/cpuapp + - nrf54lm20dk/nrf54lm20a/cpuapp + extra_configs: + - CONFIG_SYS_CLOCK_DISABLE=y + harness: console + harness_config: + type: multi_line + ordered: true + regex: + - "system off demo" + - "Retained data not supported" + - "System clock will be disabled" + - "Entering system off; press sw0 to restart" + sample.boards.nrf.system_off.retained_mem.grtc_off: + platform_allow: + - nrf54l15dk/nrf54l05/cpuapp + - nrf54l15dk/nrf54l10/cpuapp + - nrf54l15dk/nrf54l15/cpuapp + - nrf54lm20dk/nrf54lm20a/cpuapp + extra_configs: + - CONFIG_APP_USE_RETAINED_MEM=y + - CONFIG_SYS_CLOCK_DISABLE=y + harness: console + harness_config: + type: multi_line + ordered: true + regex: + - "system off demo" + - "Retained data: valid" + - "Boot count: 1" + - "Off count: 0" + - "Active Ticks:" + - "System clock will be disabled" + - "Entering system off; press sw0 to restart" sample.boards.nrf.system_off.grtc_wakeup: platform_allow: - nrf54l15dk/nrf54l05/cpuapp diff --git a/samples/boards/nordic/system_off/src/main.c b/samples/boards/nordic/system_off/src/main.c index b4c2eeb2b1bb..020e88a5449e 100644 --- a/samples/boards/nordic/system_off/src/main.c +++ b/samples/boards/nordic/system_off/src/main.c @@ -17,6 +17,7 @@ #include #include #include +#include #define NON_WAKEUP_RESET_REASON (RESET_PIN | RESET_SOFTWARE | RESET_POR | RESET_DEBUG) @@ -97,11 +98,15 @@ int main(void) printf("Retained data not supported\n"); } +#if defined(CONFIG_SYS_CLOCK_DISABLE) + printf("System clock will be disabled\n"); +#endif #if defined(CONFIG_GRTC_WAKEUP_ENABLE) int err = z_nrf_grtc_wakeup_prepare(DEEP_SLEEP_TIME_S * USEC_PER_SEC); if (err < 0) { printk("Unable to prepare GRTC as a wake up source (err = %d).\n", err); + return 0; } else { printk("Entering system off; wait %u seconds to restart\n", DEEP_SLEEP_TIME_S); } @@ -141,6 +146,9 @@ int main(void) } hwinfo_clear_reset_cause(); +#if defined(CONFIG_SYS_CLOCK_DISABLE) + sys_clock_disable(); +#endif sys_poweroff(); return 0;