drivers: hwinfo: Add reset cause support
Add `hwinfo_get_reset_cause` and `hwinfo_clear_reset_cause` to retrieve and to clear cause of system reset on supported platforms. Different platforms can provide different causes of reset, however there is a great deal of overlap. `enum reset_cause` can be expanded in the future to support additional reasons, as additional platforms are supported. Signed-off-by: Arvin Farahmand <arvinf@ip-logix.com>
This commit is contained in:
parent
38eaabc9c7
commit
98a0ccd5c5
9 changed files with 409 additions and 35 deletions
|
@ -10,9 +10,6 @@ menuconfig HWINFO
|
|||
|
||||
if HWINFO
|
||||
|
||||
config HWINFO_HAS_DRIVER
|
||||
bool
|
||||
|
||||
config HWINFO_SHELL
|
||||
bool "Enable HWINFO Shell"
|
||||
default y
|
||||
|
@ -24,7 +21,6 @@ config HWINFO_STM32
|
|||
bool "STM32 hwinfo"
|
||||
default y
|
||||
depends on SOC_FAMILY_STM32
|
||||
select HWINFO_HAS_DRIVER
|
||||
help
|
||||
Enable STM32 hwinfo driver.
|
||||
|
||||
|
@ -32,7 +28,6 @@ config HWINFO_NRF
|
|||
bool "NRF device ID"
|
||||
default y
|
||||
depends on SOC_FAMILY_NRF && !TRUSTED_EXECUTION_NONSECURE
|
||||
select HWINFO_HAS_DRIVER
|
||||
help
|
||||
Enable Nordic NRF hwinfo driver.
|
||||
|
||||
|
@ -40,7 +35,6 @@ config HWINFO_MCUX_SIM
|
|||
bool "NXP kinetis device ID"
|
||||
default y
|
||||
depends on HAS_MCUX_SIM
|
||||
select HWINFO_HAS_DRIVER
|
||||
help
|
||||
Enable NXP kinetis mcux hwinfo driver.
|
||||
|
||||
|
@ -48,7 +42,6 @@ config HWINFO_IMXRT
|
|||
bool "NXP i.mx RT device ID"
|
||||
default y
|
||||
depends on SOC_SERIES_IMX_RT
|
||||
select HWINFO_HAS_DRIVER
|
||||
help
|
||||
Enable NXP i.mx RT hwinfo driver.
|
||||
|
||||
|
@ -56,7 +49,6 @@ config HWINFO_SAM
|
|||
bool "Atmel SAM device ID"
|
||||
default y
|
||||
depends on SOC_FAMILY_SAM && !SOC_SERIES_SAM4L
|
||||
select HWINFO_HAS_DRIVER
|
||||
help
|
||||
Enable Atmel SAM hwinfo driver.
|
||||
|
||||
|
@ -64,7 +56,6 @@ config HWINFO_SAM4L
|
|||
bool "Atmel SAM4L device ID"
|
||||
default y
|
||||
depends on SOC_SERIES_SAM4L
|
||||
select HWINFO_HAS_DRIVER
|
||||
help
|
||||
Enable Atmel SAM4L hwinfo driver.
|
||||
|
||||
|
@ -72,7 +63,6 @@ config HWINFO_SAM0
|
|||
bool "Atmel SAM0 device ID"
|
||||
default y
|
||||
depends on SOC_FAMILY_SAM0
|
||||
select HWINFO_HAS_DRIVER
|
||||
help
|
||||
Enable Atmel SAM0 hwinfo driver.
|
||||
|
||||
|
@ -80,7 +70,6 @@ config HWINFO_ESP32
|
|||
bool "ESP32 device ID"
|
||||
default y
|
||||
depends on SOC_ESP32
|
||||
select HWINFO_HAS_DRIVER
|
||||
help
|
||||
Enable ESP32 hwinfo driver.
|
||||
|
||||
|
@ -88,7 +77,6 @@ config HWINFO_LITEX
|
|||
bool "LiteX device ID"
|
||||
default y
|
||||
depends on SOC_RISCV32_LITEX_VEXRISCV
|
||||
select HWINFO_HAS_DRIVER
|
||||
help
|
||||
Enable LiteX hwinfo driver
|
||||
|
||||
|
@ -96,7 +84,6 @@ config HWINFO_PSOC6
|
|||
bool "Cypress PSoC-6 unique device ID"
|
||||
default y
|
||||
depends on SOC_FAMILY_PSOC6
|
||||
select HWINFO_HAS_DRIVER
|
||||
help
|
||||
Enable Cypress PSoC-6 hwinfo driver.
|
||||
|
||||
|
@ -104,7 +91,6 @@ config HWINFO_GECKO
|
|||
bool "GECKO hwinfo"
|
||||
default y
|
||||
depends on SOC_FAMILY_EXX32
|
||||
select HWINFO_HAS_DRIVER
|
||||
help
|
||||
Enable Silabs GECKO hwinfo driver.
|
||||
|
||||
|
|
|
@ -14,3 +14,34 @@ ssize_t z_vrfy_hwinfo_get_device_id(uint8_t *buffer, size_t length)
|
|||
return z_impl_hwinfo_get_device_id((uint8_t *)buffer, (size_t)length);
|
||||
}
|
||||
#include <syscalls/hwinfo_get_device_id_mrsh.c>
|
||||
|
||||
int z_vrfy_hwinfo_get_reset_cause(uint32_t *cause)
|
||||
{
|
||||
int ret;
|
||||
uint32_t cause_copy;
|
||||
|
||||
ret = z_impl_hwinfo_get_reset_cause(&cause_copy);
|
||||
Z_OOPS(z_user_to_copy(cause, &cause_copy, sizeof(uint32_t)));
|
||||
|
||||
return ret;
|
||||
}
|
||||
#include <syscalls/hwinfo_get_reset_cause_mrsh.c>
|
||||
|
||||
|
||||
int z_vrfy_hwinfo_clear_reset_cause(void)
|
||||
{
|
||||
return z_impl_hwinfo_clear_reset_cause();
|
||||
}
|
||||
#include <syscalls/hwinfo_clear_reset_cause_mrsh.c>
|
||||
|
||||
int z_vrfy_hwinfo_get_supported_reset_cause(uint32_t *supported)
|
||||
{
|
||||
int ret;
|
||||
uint32_t supported_copy;
|
||||
|
||||
ret = z_impl_hwinfo_get_supported_reset_cause(&supported_copy);
|
||||
Z_OOPS(z_user_to_copy(supported, &supported_copy, sizeof(uint32_t)));
|
||||
|
||||
return ret;
|
||||
}
|
||||
#include <syscalls/hwinfo_get_supported_reset_cause_mrsh.c>
|
||||
|
|
|
@ -9,6 +9,9 @@
|
|||
#include <string.h>
|
||||
#include <hal/nrf_ficr.h>
|
||||
#include <sys/byteorder.h>
|
||||
#ifndef CONFIG_BOARD_QEMU_CORTEX_M0
|
||||
#include <helpers/nrfx_reset_reason.h>
|
||||
#endif
|
||||
|
||||
struct nrf_uid {
|
||||
uint32_t id[2];
|
||||
|
@ -29,3 +32,88 @@ ssize_t z_impl_hwinfo_get_device_id(uint8_t *buffer, size_t length)
|
|||
|
||||
return length;
|
||||
}
|
||||
|
||||
#ifndef CONFIG_BOARD_QEMU_CORTEX_M0
|
||||
int z_impl_hwinfo_get_reset_cause(uint32_t *cause)
|
||||
{
|
||||
uint32_t flags = 0;
|
||||
|
||||
uint32_t reason = nrfx_reset_reason_get();
|
||||
|
||||
if (reason & NRFX_RESET_REASON_RESETPIN_MASK) {
|
||||
flags |= RESET_PIN;
|
||||
}
|
||||
if (reason & NRFX_RESET_REASON_DOG_MASK) {
|
||||
flags |= RESET_WATCHDOG;
|
||||
}
|
||||
if (reason & NRFX_RESET_REASON_LOCKUP_MASK) {
|
||||
flags |= RESET_CPU_LOCKUP;
|
||||
}
|
||||
if (reason & NRFX_RESET_REASON_OFF_MASK) {
|
||||
flags |= RESET_LOW_POWER_WAKE;
|
||||
}
|
||||
if (reason & NRFX_RESET_REASON_DIF_MASK) {
|
||||
flags |= RESET_DEBUG;
|
||||
}
|
||||
|
||||
#if !NRF_POWER_HAS_RESETREAS
|
||||
if (reason & NRFX_RESET_REASON_CTRLAP_MASK) {
|
||||
flags |= RESET_DEBUG;
|
||||
}
|
||||
if (reason & NRFX_RESET_REASON_DOG0_MASK) {
|
||||
flags |= RESET_WATCHDOG;
|
||||
}
|
||||
if (reason & NRFX_RESET_REASON_DOG1_MASK) {
|
||||
flags |= RESET_WATCHDOG;
|
||||
}
|
||||
if (reason & NRFX_RESETREAS_SREQ_MASK) {
|
||||
flags |= RESET_SOFTWARE;
|
||||
}
|
||||
|
||||
#if NRF_RESET_HAS_NETWORK
|
||||
if (reason & NRFX_RESET_REASON_LSREQ_MASK) {
|
||||
flags |= RESET_SOFTWARE;
|
||||
}
|
||||
if (reason & NRFX_RESET_REASON_LLOCKUP_MASK) {
|
||||
flags |= RESET_CPU_LOCKUP;
|
||||
}
|
||||
if (reason & NRFX_RESET_REASON_LDOG_MASK) {
|
||||
flags |= RESET_WATCHDOG;
|
||||
}
|
||||
if (reason & NRFX_RESET_REASON_LCTRLAP_MASK) {
|
||||
flags |= RESET_DEBUG;
|
||||
}
|
||||
#endif
|
||||
|
||||
#else
|
||||
if (reason & NRFX_RESET_REASON_SREQ_MASK) {
|
||||
flags |= RESET_SOFTWARE;
|
||||
}
|
||||
#endif
|
||||
|
||||
*cause = flags;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int z_impl_hwinfo_clear_reset_cause(void)
|
||||
{
|
||||
uint32_t reason = -1;
|
||||
|
||||
nrfx_reset_reason_clear(reason);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int z_impl_hwinfo_get_supported_reset_cause(uint32_t *supported)
|
||||
{
|
||||
*supported = (RESET_PIN
|
||||
| RESET_WATCHDOG
|
||||
| RESET_SOFTWARE
|
||||
| RESET_CPU_LOCKUP
|
||||
| RESET_LOW_POWER_WAKE
|
||||
| RESET_DEBUG);
|
||||
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
|
|
|
@ -6,6 +6,7 @@
|
|||
|
||||
#include <soc.h>
|
||||
#include <stm32_ll_utils.h>
|
||||
#include <stm32_ll_rcc.h>
|
||||
#include <drivers/hwinfo.h>
|
||||
#include <string.h>
|
||||
#include <sys/byteorder.h>
|
||||
|
@ -30,3 +31,78 @@ ssize_t z_impl_hwinfo_get_device_id(uint8_t *buffer, size_t length)
|
|||
|
||||
return length;
|
||||
}
|
||||
|
||||
int z_impl_hwinfo_get_reset_cause(uint32_t *cause)
|
||||
{
|
||||
uint32_t flags = 0;
|
||||
|
||||
#if defined(RCC_FLAG_SFTRST)
|
||||
if (LL_RCC_IsActiveFlag_SFTRST()) {
|
||||
flags |= RESET_SOFTWARE;
|
||||
}
|
||||
#endif
|
||||
#if defined(RCC_FLAG_PINRST)
|
||||
if (LL_RCC_IsActiveFlag_PINRST()) {
|
||||
flags |= RESET_PIN;
|
||||
}
|
||||
#endif
|
||||
#if defined(RCC_FLAG_IWDGRST)
|
||||
if (LL_RCC_IsActiveFlag_IWDGRST()) {
|
||||
flags |= RESET_WATCHDOG;
|
||||
}
|
||||
#endif
|
||||
#if defined(RCC_FLAG_WWDGRST)
|
||||
if (LL_RCC_IsActiveFlag_WWDGRST()) {
|
||||
flags |= RESET_WATCHDOG;
|
||||
}
|
||||
#endif
|
||||
#if defined(RCC_FLAG_FWRST)
|
||||
if (LL_RCC_IsActiveFlag_FWRST()) {
|
||||
flags |= RESET_SECURITY;
|
||||
}
|
||||
#endif
|
||||
#if defined(RCC_FLAG_BORRST)
|
||||
if (LL_RCC_IsActiveFlag_BORRST()) {
|
||||
flags |= RESET_BROWNOUT;
|
||||
}
|
||||
#endif
|
||||
#if defined(RCC_FLAG_PWRRST)
|
||||
if (LL_RCC_IsActiveFlag_PWRRST()) {
|
||||
flags |= RESET_POR;
|
||||
}
|
||||
#endif
|
||||
#if defined(RCC_FLAG_PORRST)
|
||||
if (LL_RCC_IsActiveFlag_PORRST()) {
|
||||
flags |= RESET_POR;
|
||||
}
|
||||
#endif
|
||||
#if defined(RCC_FLAG_LPWRRST)
|
||||
if (LL_RCC_IsActiveFlag_LPWRRST()) {
|
||||
flags |= RESET_LOW_POWER_WAKE;
|
||||
}
|
||||
#endif
|
||||
|
||||
*cause = flags;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int z_impl_hwinfo_clear_reset_cause(void)
|
||||
{
|
||||
LL_RCC_ClearResetFlags();
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int z_impl_hwinfo_get_supported_reset_cause(uint32_t *supported)
|
||||
{
|
||||
*supported = (RESET_PIN
|
||||
| RESET_WATCHDOG
|
||||
| RESET_SOFTWARE
|
||||
| RESET_SECURITY
|
||||
| RESET_LOW_POWER_WAKE
|
||||
| RESET_POR
|
||||
| RESET_BROWNOUT);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -8,5 +8,20 @@
|
|||
|
||||
ssize_t __weak z_impl_hwinfo_get_device_id(uint8_t *buffer, size_t length)
|
||||
{
|
||||
return -ENOTSUP;
|
||||
return -ENOSYS;
|
||||
}
|
||||
|
||||
int __weak z_impl_hwinfo_get_reset_cause(uint32_t *cause)
|
||||
{
|
||||
return -ENOSYS;
|
||||
}
|
||||
|
||||
int __weak z_impl_hwinfo_clear_reset_cause(void)
|
||||
{
|
||||
return -ENOSYS;
|
||||
}
|
||||
|
||||
int __weak z_impl_hwinfo_get_supported_reset_cause(uint32_t *supported)
|
||||
{
|
||||
return -ENOSYS;
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue