287 lines
11 KiB
C
287 lines
11 KiB
C
/**
|
|
* @file sdrv_watchdog.h
|
|
* @brief SemiDrive Watchdog driver header file.
|
|
*
|
|
* @copyright Copyright (c) 2022 Semidrive Semiconductor.
|
|
* All rights reserved.
|
|
*/
|
|
|
|
#ifndef SDRV_WATCHDOG_DRV_H_
|
|
#define SDRV_WATCHDOG_DRV_H_
|
|
|
|
#include <types.h>
|
|
#include <regs_base.h>
|
|
#include "sdrv_common.h"
|
|
|
|
#undef __I
|
|
#undef __O
|
|
#undef __IO
|
|
|
|
|
|
#ifdef __cplusplus
|
|
#define __I volatile /*!< Defines 'read only' permissions */
|
|
#else
|
|
#define __I volatile const /*!< Defines 'read only' permissions */
|
|
#endif
|
|
#define __O volatile /*!< Defines 'write only' permissions */
|
|
#define __IO volatile /*!< Defines 'read / write' permissions */
|
|
|
|
/**
|
|
* @brief watchdog status error code.
|
|
*/
|
|
enum sdrv_watchdog_error
|
|
{
|
|
SDRV_STATUS_TIMEOUT_FAILED = SDRV_ERROR_STATUS(SDRV_STATUS_GROUP_WATCHDOG, 0), /* watchdog status for timeout failed. */
|
|
SDRV_STATUS_DELTA_FAILED = SDRV_ERROR_STATUS(SDRV_STATUS_GROUP_WATCHDOG,1), /* watchdog status for delta failed. */
|
|
SDRV_STATUS_WINDOW_LOW_FAILED= SDRV_ERROR_STATUS(SDRV_STATUS_GROUP_WATCHDOG, 2), /* watchdog status for window_low failed. */
|
|
SDRV_STATUS_INTR_UNCLEARED = SDRV_ERROR_STATUS(SDRV_STATUS_GROUP_WATCHDOG, 3), /* watchdog status for interrupt not cleared. */
|
|
};
|
|
|
|
/**
|
|
* @brief Definition for sdrv watchdog register.
|
|
*/
|
|
typedef struct sdrv_wdt {
|
|
__IO uint32_t ctrl; /**< Global control, offset: 0x0 */
|
|
__IO uint32_t wtc; /**< Terminal count value, offset: 0x4 */
|
|
__IO uint32_t wrc_ctrl; /**< Refresh control, offset: 0x8 */
|
|
__IO uint32_t wrc_val; /**< Refresh window limit, offset: 0xC */
|
|
__IO uint32_t wrc_seq; /**< Refresh sequence delta, offset: 0x10 */
|
|
__IO uint32_t rst_ctl; /**< Reset control, offset: 0x14 */
|
|
__IO uint32_t ext_rst_ctl; /**< External reset control, offset: 0x18 */
|
|
__I uint32_t cnt; /**< Counter, offset: 0x1C */
|
|
__O uint32_t tsw; /**< Timestamp, offset: 0x20 */
|
|
__IO uint32_t intr; /**< Interrupt, offset: 0x24 */
|
|
__IO uint32_t rst_req_mon; /**< Reset request monitor, offset: 0x28 */
|
|
__IO uint32_t dummy_res; /**< Dummy reserved, offset: 0x2C */
|
|
|
|
uint32_t reserved1[4];
|
|
|
|
__IO uint32_t lock; /**< Lock, offset: 0x40 */
|
|
} sdrv_wdt_t;
|
|
|
|
/**
|
|
* @brief Definition for watchdog clock source.
|
|
*/
|
|
typedef enum sdrv_wdt_clock {
|
|
WDT_MAIN_CLOCK = 0U, /**< System 24M clock */
|
|
WDT_BUS_CLOCK, /**< System bus clock */
|
|
WDT_EXT_CLOCK, /**< External clock */
|
|
WDT_TIE_OFF, /**< Tie off */
|
|
WDT_LP_CLOCK, /**< System 32K clock */
|
|
} sdrv_wdt_clock_e;
|
|
|
|
/**
|
|
* @brief Definition for watchdog refresh type.
|
|
*/
|
|
typedef enum sdrv_wdt_refresh {
|
|
WDT_DIRECT_REFRESH = 0U, /**< WDT direct refresh, you must feed dog before timeout. */
|
|
WDT_WINDOW_REFRESH, /**< WDT window based refresh, you must feed dog bewteen time low limit and timeout. */
|
|
WDT_SEQUENCE_REFRESH, /**< WDT sequence based refresh, after you read current counter, you must write it
|
|
to timestamp register before delta time. */
|
|
WDT_DIRECT_SEQUENCE_REFRESH, /**< WDT direct/sequence base refresh combine. */
|
|
WDT_WINDOW_SEQUENCE_REFRESH, /**< WDT window base/sequence base refresh combine. */
|
|
} sdrv_wdt_refresh_e;
|
|
|
|
/**
|
|
* @brief Definition for watchdog interrupt type.
|
|
*/
|
|
typedef enum sdrv_wdt_intr {
|
|
WDT_ILL_WINDOW_REFRESH = 0X1U, /**< WDT illeage window based counter refresh interrupt. */
|
|
WDT_ILL_SEQUENCE_RESRESH = 0X2U, /**< WDT illeage sequential refresh interrupt. */
|
|
WDT_OVERFLOW = 0X4U, /**< WDT timer overflow interrupt. */
|
|
} sdrv_wdt_intr_e;
|
|
|
|
/**
|
|
* @brief Definition for watchdog internal reset config.
|
|
*/
|
|
typedef struct sdrv_wdt_internal_reset {
|
|
bool reset_en; /**< WDT internal system reset request enable. */
|
|
uint8_t reset_mode; /**< WDT reset mode, 0-level, 1-pulse. */
|
|
uint8_t reset_win; /**< WDT pulse mode reset window. */
|
|
uint16_t reset_cnt; /**< WDT reset counter, time between overflow to trigger reset. */
|
|
bool wdt_reset_en; /**< WDT restart after internal system reset enable. */
|
|
} sdrv_wdt_internal_reset_t;
|
|
|
|
/**
|
|
* @brief Definition for watchdog external reset config.
|
|
*/
|
|
typedef struct sdrv_wdt_external_reset {
|
|
bool reset_en; /**< WDT external system reset request enable. */
|
|
uint8_t reset_mode; /**< WDT reset mode, 0-level, 1-pulse. */
|
|
uint8_t reset_pol; /**< WDT reset request polarity, 0-low active, 1-high active. */
|
|
uint8_t reset_win; /**< WDT pulse mode reset window. */
|
|
uint16_t reset_cnt; /**< WDT reset counter, time between overflow to trigger reset. */
|
|
} sdrv_wdt_external_reset_t;
|
|
|
|
/**
|
|
* @brief Definition for watchdog initialize config.
|
|
*/
|
|
typedef struct sdrv_wdt_config {
|
|
sdrv_wdt_clock_e clk_src; /**< WDT clock source. */
|
|
uint16_t pre_divide; /**< Clock pre-divider ratio, 0 ~ 0xFFFF. */
|
|
|
|
uint8_t wdt_en_src; /**< WDT enable control by: 0-Fuse, 1-Software. */
|
|
uint8_t wtc_src; /**< WDT terminal count config by: 0-Fuse, 1-Software. */
|
|
|
|
bool auto_restart; /**< WDT overflow auto restart enable. */
|
|
|
|
sdrv_wdt_refresh_e refresh; /**< WDT refresh mode. */
|
|
uint32_t timeout; /**< WDT timeout value, unit: ms. */
|
|
uint32_t window_low; /**< WDT refresh window low limit, unit: ms. */
|
|
uint32_t seq_delta; /**< WDT refresh sequence delta, unit: ms. */
|
|
|
|
uint32_t intr_bitmap; /**< WDT interrupt enable bitmap. */
|
|
|
|
sdrv_wdt_internal_reset_t int_rst; /**< WDT internal reset. */
|
|
sdrv_wdt_external_reset_t ext_rst; /**< WDT external reset. */
|
|
} sdrv_wdt_config_t;
|
|
|
|
/**
|
|
* @brief Get the default configuration for watchdog.
|
|
*
|
|
* This function get the default configuration for watchdog. When you want initialize,
|
|
* you can call this function first and modify some of them, then call sdrv_wdt_init.
|
|
*
|
|
* @param [in] config WDT config struct.
|
|
* @return SDRV_STATUS_OK represents success, SDRV_STATUS_FAIL represents failed.
|
|
*/
|
|
status_t sdrv_wdt_get_default_config(sdrv_wdt_config_t *config);
|
|
|
|
/**
|
|
* @brief Initialize watchdog with config parameters.
|
|
*
|
|
* This function config watchdog with parameters in sdrv_wdt_config_t.
|
|
*
|
|
* @param [in] base WDT control base.
|
|
* @param [in] config WDT config struct.
|
|
* @return Return SDRV_STATUS_OK or error code.
|
|
*/
|
|
status_t sdrv_wdt_init(sdrv_wdt_t *base, sdrv_wdt_config_t *config);
|
|
|
|
/**
|
|
* @brief De-Initialize watchdog.
|
|
*
|
|
* This function disable watchdog interrupt and clear interrupt status.
|
|
* Disable internal and external reset config.
|
|
*
|
|
* @param [in] base WDT control base.
|
|
* @return SDRV_STATUS_OK represents success, SDRV_STATUS_FAIL represents failed,
|
|
* SDRV_STATUS_INTR_UNCLEARED represents interrupt not cleared.
|
|
*/
|
|
status_t sdrv_wdt_deinit(sdrv_wdt_t *base);
|
|
|
|
/**
|
|
* @brief Enable watchdog.
|
|
*
|
|
* This function enable watchdog timer counter.
|
|
*
|
|
* @param [in] base WDT control base.
|
|
* @return SDRV_STATUS_OK represents success, SDRV_STATUS_FAIL represents failed.
|
|
*/
|
|
status_t sdrv_wdt_enable(sdrv_wdt_t *base);
|
|
|
|
/**
|
|
* @brief Disable watchdog.
|
|
*
|
|
* This function disable watchdog timer counter.
|
|
*
|
|
* @param [in] base WDT control base
|
|
* @return SDRV_STATUS_OK represents success, SDRV_STATUS_FAIL represents failed.
|
|
*/
|
|
status_t sdrv_wdt_disable(sdrv_wdt_t *base);
|
|
|
|
/**
|
|
* @brief Set watchdog timeout value.
|
|
*
|
|
* This function get timeout value in milliseconds and convert to timer counter according
|
|
* to clock source pre-configed.
|
|
*
|
|
* @param [in] base WDT control base.
|
|
* @param [in] timeout unit: ms.
|
|
* @return SDRV_STATUS_OK represents success, SDRV_STATUS_FAIL represents failed,
|
|
* SDRV_STATUS_INVALID_PARAM represents invalid paramemt.
|
|
*/
|
|
status_t sdrv_wdt_set_timeout(sdrv_wdt_t *base, uint32_t timeout);
|
|
|
|
/**
|
|
* @brief Set watchdog time window low limit value.
|
|
*
|
|
* This function get time window low limit value in milliseconds and convert to timer
|
|
* counter according to clock source pre-configed.
|
|
*
|
|
* @param [in] base WDT control base.
|
|
* @param [in] low_limit unit: ms.
|
|
* @return SDRV_STATUS_OK represents success, SDRV_STATUS_FAIL represents failed,
|
|
* SDRV_STATUS_INVALID_PARAM represents invalid paramemt.
|
|
*/
|
|
status_t sdrv_wdt_set_window_low(sdrv_wdt_t *base, uint32_t low_limit);
|
|
|
|
/**
|
|
* @brief Set watchdog sequence delta value.
|
|
*
|
|
* This function get sequence delta value in milliseconds and convert to timer
|
|
* counter according to clock source pre-configed.
|
|
*
|
|
* @param [in] base WDT control base.
|
|
* @param [in] delta unit: ms.
|
|
* @return SDRV_STATUS_OK represents success, SDRV_STATUS_FAIL represents failed,
|
|
* SDRV_STATUS_INVALID_PARAM represents invalid paramemt.
|
|
*/
|
|
status_t sdrv_wdt_set_sequence_delta(sdrv_wdt_t *base, uint32_t delta);
|
|
|
|
/**
|
|
* @brief Feed watchdog.
|
|
*
|
|
* This function trigger watchdog do refresh.
|
|
*
|
|
* @param [in] base WDT control base.
|
|
* @return SDRV_STATUS_OK represents success, SDRV_STATUS_FAIL represents failed.
|
|
*/
|
|
status_t sdrv_wdt_refresh(sdrv_wdt_t *base);
|
|
|
|
/**
|
|
* @brief Read watchdog current counter.
|
|
*
|
|
* This function read watchdog current counter. When you enable sequence refresh, you need call
|
|
* this function first and store read value. Before time delta, use sdrv_wdt_write_timestamp with
|
|
* stored value. Otherwise, illeage sequential refresh interrupt status will set.
|
|
*
|
|
* @param [in] base WDT control base.
|
|
* @return current timer counter.
|
|
*/
|
|
uint32_t sdrv_wdt_read_timestamp(sdrv_wdt_t *base);
|
|
|
|
/**
|
|
* @brief Write watchdog counter to TSW register.
|
|
*
|
|
* This function write counter to TSW register. When config sequence base refresh,
|
|
* read timestamp first, then write read value to TSW before sequence delta.
|
|
*
|
|
* @param [in] base WDT control base.
|
|
* @param [in] timestamp last read wdt conunter.
|
|
* @return SDRV_STATUS_OK represents success, SDRV_STATUS_FAIL represents failed.
|
|
*/
|
|
status_t sdrv_wdt_write_timestamp(sdrv_wdt_t *base, uint32_t timestamp);
|
|
|
|
/**
|
|
* @brief Get watchdog interrupt status of specific type.
|
|
*
|
|
* This function get specific type interrupt status.
|
|
*
|
|
* @param [in] base WDT control base.
|
|
* @param [in] intr interrupt type defined in sdrv_wdt_intr_e.
|
|
* @return true represents status is set, false represents status not set.
|
|
*/
|
|
status_t sdrv_wdt_get_intr_status(sdrv_wdt_t *base, sdrv_wdt_intr_e intr);
|
|
|
|
/**
|
|
* @brief Clear watchdog interrupt status of specific type.
|
|
*
|
|
* @param [in] base WDT control base.
|
|
* @param [in] intr interrupt type defined in sdrv_wdt_intr_e.
|
|
* @return SDRV_STATUS_OK represents success, SDRV_STATUS_FAIL represents failed.
|
|
*/
|
|
status_t sdrv_wdt_clear_intr_status(sdrv_wdt_t *base, sdrv_wdt_intr_e intr);
|
|
|
|
#endif /* SDRV_WATCHDOG_DRV_H_ */
|