Files
plant_car/drivers/include/sdrv_etimer.h
2025-11-08 13:26:19 +08:00

450 lines
12 KiB
C

/**
* @file sdrv_etimer.h
* @brief SemiDrive ETIMER driver header file.
*
* @copyright Copyright (c) 2022 Semidrive Semiconductor.
* All rights reserved.
*/
#ifndef INCLUDE_DRV_SDRV_ETIMER_H
#define INCLUDE_DRV_SDRV_ETIMER_H
#include <compiler.h>
#include <types.h>
#include "../source/etimer/sdrv_etimer_lld.h"
#include "sdrv_common.h"
#if (CONFIG_E3 || CONFIG_D3)
#define ETMR_SOURCE_CLK 250
#else
#if ((CONFIG_E3106) || (CONFIG_E3104))
#define ETMR_SOURCE_CLK 150
#else
#define ETMR_SOURCE_CLK 198
#endif
#endif
/* etimer callback */
typedef void (*etimer_callback)(void *arg);
typedef struct sdrv_etimer_controller sdrv_etimer_controller_t;
/**
* @brief etimer work mode
*/
/* etimer work mode*/
typedef enum etimer_work_mode {
/* idle mode */
ETIMER_PWM_IDLE = 0,
/* pwm capture mode */
ETIMER_PWM_CAPTURE = 1,
/* pwm output mode */
ETIMER_PWM_GENERATE = 2,
/* etimer timer function */
ETIMER_TIMER_FUNC = 3,
/* etimer icu function */
ETIMER_ICU_FUNC = 4,
/* other mode : quad filter etc*/
ETIMER_PWM_OTHERS = 5
} etimer_work_mode_t;
/**
* @brief etimer g0 counter mode
*/
/* etimer g0 counter work mode */
typedef enum etimer_g0_mode {
/* g0 idle mode */
G0_IDLE = 0,
/* g0 work for timer func */
G0_FOR_TIMER = 1,
/* g0 work for pwm output */
G0_FOR_PWM_GEN = 2,
} etimer_g0_mode_t;
/**
* @brief etimer work status
*/
/* etimer work status */
typedef enum etimer_chn_status {
/* channel uninit */
ETIMER_CHAN_UNINIT = 0,
/* channel init */
ETIMER_CHAN_INIT = 1,
/* channel running */
ETIMER_CHAN_RUNNING = 2,
/* channel stop */
ETIMER_CHAN_STOP = 3
} etimer_chn_status_t;
/**
* @brief sdrv etimer basic counter num
*/
/* etimer timer : only basic cnt can work for etimer timer function */
typedef enum sdrv_etimer_basic_cnt_id {
ETIMR_BASIC_TMR_G0,
ETIMR_BASIC_TMR_G1,
ETIMR_BASIC_TMR_NUM
} sdrv_etimer_basic_cnt_id_t;
/**
* @brief sdrv etimer tmr config
*/
typedef struct sdrv_etimer_basic_cnt_cfg {
/* etimer timer select */
sdrv_etimer_basic_cnt_id_t tmr_id;
/* etimer timer work mode */
sdrv_etimer_cnt_con_mode_e con_mode;
/* etimer timer clk select */
sdrv_etimer_clk_src_e clk_sel;
/* etimer timer clk frequency */
uint32_t clk_frq;
/* etimer timer clk divider */
uint32_t clk_div;
} sdrv_etimer_basic_cnt_cfg_t;
/**
* @brief sdrv tmr config
*/
typedef struct sdrv_etimer_tmr_cfg {
/* basic timer config */
sdrv_etimer_basic_cnt_cfg_t *cnt_cfg;
/* timer timeout value */
uint32_t time_out;
/* tick cnt per us */
uint32_t cnt_per_ms;
} sdrv_etimer_tmr_cfg_t;
/**
* @brief sdrv etimer ctrl
*/
typedef struct sdrv_etimer_chn {
/* module base addr */
uint32_t base;
/* clk_src and clk_div only take effect for the first time */
sdrv_etimer_clk_src_e clk_src;
uint16_t clk_div;
/* module irq id */
uint32_t irq;
/* irq enable */
/* for pwm capture : irq always enable */
bool int_en;
/* use g0 counter : pwm generate mode only */
bool use_g0_cnt;
/* use center align mode : pwm generate mode only */
bool center_align_mode;
/* whether to support frequency double output in duty 1 (pwm generate mode
* only) */
bool fre_double_flag;
/* channel work mode */
etimer_work_mode_t mode;
/* callback function */
etimer_callback callback;
/* callback function para */
void *arg;
/* etimer channel select */
sdrv_etimer_chn_id_e channel;
/* timer config : etimer timer function only */
sdrv_etimer_tmr_cfg_t config;
/* timer/channel work status */
etimer_chn_status_t crtl_sta;
/* have read flag : pwm capture mode only */
bool cpt_read_flag;
/* is use multicapture function */
bool use_multicpt;
/* The controller this timer belongs to */
sdrv_etimer_controller_t *controller;
} sdrv_etimer_t;
/**
* @brief eTimer hardware contrller
*/
struct sdrv_etimer_controller {
/* module base addr */
uint32_t base;
/* irq init flag */
bool int_init_flag;
/* clk init flag */
bool clk_set_flag;
/* etimer clk src */
sdrv_etimer_clk_src_e etimer_clk_src;
/* etimer clk divider */
uint32_t etimer_clk_div;
/* etimer g0 work mode */
etimer_g0_mode_t g0_mode;
/* g0 period : 4 cmp chan share one period */
uint32_t g0_period;
/* eTimer channels */
/* 0 - 3 : cpt ctrl ptr; 4 - 7 : cmp ctrl ptr */
sdrv_etimer_t *etimer_bank[SDRV_ETIMR_CHN_NR * 2];
/* Counter channels */
sdrv_etimer_t *cnt_bank[ETIMR_BASIC_TMR_NUM];
};
/**
* @brief sdrv etimer pwm_status
*/
typedef struct sdrv_etimer_pwm_state {
/* PWM period in nano seconds. */
uint32_t period;
/* PWM duty cycle in nano seconds. */
/* only duty1 can be used to capture pwm signal */
uint32_t duty1;
/* duty2 only take effect for cmp0_cmp1 out mode */
uint32_t duty2;
} sdrv_etimer_pwm_state_t;
/**
* @brief sdrv etimer cmp mode ctrl
*/
typedef struct etimer_cmp_cfg {
/* pwm out mode select */
sdrv_etimer_cmp_out_e chnl_out_mode;
/* consecutive or oneshot mode */
sdrv_etimer_cmp_con_mode_e con_mode;
/* only single and dual compare mode can work for pwm output */
/* in center align mode, cmp mode must set to dual mode */
sdrv_etimer_cmp_mode_e cmp_mode;
} sdrv_etimer_cmp_cfg_t;
/**
* @brief sdrv etimer multi cmp mode cmp val (ns)
*/
typedef struct etimer_multi_cmp_val {
uint32_t cmp00_val;
uint32_t cmp01_val;
uint32_t cmp10_val;
uint32_t cmp11_val;
} sdrv_etimer_multi_cmp_val_t;
/* common function */
/**
* @brief etimer setup callback funciton
*
* @param[in] etmr: etimer ctrl instance
* @param[in] callback: user callback function
* @return succeed:0 fail:other
*/
uint8_t sdrv_etimer_set_callback(sdrv_etimer_t *etmr, etimer_callback callback,
void *arg);
/* etimer timer function */
/**
* @brief etimer timer init
*
* @param[in] etmr: etimer ctrl instance
* @param[in] cnt_cfg: timer counter config
*/
status_t sdrv_etimer_timer_init(sdrv_etimer_t *etmr,
sdrv_etimer_basic_cnt_cfg_t *cnt_cfg);
/**
* @brief etimer timer start
*
* @param[in] etmr: etimer ctrl instance
* @param[in] time_out: timer timeout value
*/
status_t sdrv_etimer_timer_start(sdrv_etimer_t *etmr, uint32_t time_out);
/**
* @brief etimer timer stop
*
* @param[in] etmr: etimer ctrl instance
*/
status_t sdrv_etimer_timer_stop(sdrv_etimer_t *etmr);
/**
* @brief etimer timer get current time val (us)
*
* @param[in] etmr: etimer ctrl instance
* @return current time val
*/
uint32_t sdrv_etimer_timer_get_current_time(sdrv_etimer_t *etmr);
/* capture function */
/**
* @brief init etimer capture chan.
*
* @param[in] etmr: etimer ctrl instance
*/
status_t sdrv_etimer_capture_init(sdrv_etimer_t *etmr);
/**
* @brief start etimer capture chan.
*
* @param[in] etmr: etimer ctrl instance
*/
status_t sdrv_etimer_capture_start(sdrv_etimer_t *etmr);
/**
* @brief stop etimer capture chan.
*
* @param[in] etmr: etimer ctrl instance
*/
status_t sdrv_etimer_capture_stop(sdrv_etimer_t *etmr);
/**
* @brief etimer capture pwm signal.
*
* @param[in] etmr: etimer ctrl instance
* @param[in] state pwm duty and period
*/
status_t sdrv_etimer_capture_pwm(sdrv_etimer_t *etmr,
sdrv_etimer_pwm_state_t *state);
/* compare funtion */
/**
* @brief etimer pwm set initial putput status.
*
* @param[in] etmr etimer ctrl instance
* @param[in] cmp0_init etimer cmp0 initial out status
* @param[in] cmp1_init etimer cmp1 initial out status
*/
status_t sdrv_etimer_compare_pwm_initial_out_status(sdrv_etimer_t *etmr,
bool cmp0_init, bool cmp1_init);
/**
* @brief etimer pwm state config.
*
* @param[in] etmr: etimer ctrl instance
* @param[in] cmp_cfg etimer cmp common config
* @param[in] state pwm duty and period
*/
status_t sdrv_etimer_compare_pwm_config(sdrv_etimer_t *etmr,
sdrv_etimer_cmp_cfg_t *cmp_cfg,
const sdrv_etimer_pwm_state_t *state);
/**
* @brief etimer pwm config update.
*
* @param[in] etmr etimer ctrl instance
* @param[in] cmp_cfg etimer cmp common config
* @param[in] state pwm duty and period
*/
status_t sdrv_etimer_compare_pwm_config_update(
sdrv_etimer_t *etmr, sdrv_etimer_cmp_cfg_t *cmp_cfg,
const sdrv_etimer_pwm_state_t *state);
/**
* @brief configure etimer pwm output dma enable (dma_en must after pwm config)
*
* @param[in] etmr etimer ctrl instance
* @param[in] wml water mark level (range : 1-15)
*/
status_t sdrv_etimer_compare_pwm_dma_en(sdrv_etimer_t *etmr, uint16_t wml);
/**
* @brief configure multi compare mode.
*
* @param[in] etmr: etimer ctrl instance
* @param[in] multi_cmp etimer multi cmp config
*/
status_t sdrv_etimer_compare_multi_mode(sdrv_etimer_t *etmr,
sdrv_etimer_multi_cmp_val_t *multi_cmp);
/**
* @brief start to generate etimer pwm signal.
*
* @param[in] etmr: etimer ctrl instance
*/
status_t sdrv_etimer_compare_pwm_start(sdrv_etimer_t *etmr);
/**
* @brief stop to generate etimer pwm signal.
*
* @param[in] etmr: etimer ctrl instance
*/
status_t sdrv_etimer_compare_pwm_stop(sdrv_etimer_t *etmr);
/* quad function */
/**
* @brief etimer quad config.
*
* @param[in] etmr: etimer ctrl instance
* @param[in] quad_ctrl etimer quad config
*/
status_t sdrv_etimer_quad_config(sdrv_etimer_t *etmr, quad_ctrl_t *quad_ctrl);
/**
* @brief start etimer quad.
*
* @param[in] etmr: etimer ctrl instance
*/
status_t sdrv_etimer_quad_start(sdrv_etimer_t *etmr);
/**
* @brief stop etimer quad.
*
* @param[in] etmr: etimer ctrl instance
*/
status_t sdrv_etimer_quad_stop(sdrv_etimer_t *etmr);
/**
* @brief get quad dir signal status
*
* @param[in] etmr: etimer ctrl instance
*/
bool sdrv_etimer_quad_dir_up(sdrv_etimer_t *etmr);
/**
* @brief configure etimer filter config
*
* @param[in] etmr: etimer ctrl instance
* @param[in] filter_cfg filter_cfg
*/
status_t sdrv_etimer_filter_config(sdrv_etimer_t *etmr, flt_config_t *filter_cfg);
/* icu function */
/**
* @brief configure etimer icu config
*
* @param[in] etmr etimer ctrl instance
* @param[in] edge_sel capture edge select
*/
status_t sdrv_etimer_icu_config(sdrv_etimer_t *etmr,
sdrv_etimer_cpt_trig_mode_e edge_sel);
/**
* @brief configure etimer icu dma enable (dma_en must after icu config)
*
* @param[in] etmr etimer ctrl instance
* @param[in] wml water mark level (range : 1-15)
*/
status_t sdrv_etimer_icu_dma_en(sdrv_etimer_t *etmr, uint16_t wml);
/**
* @brief start etimer icu chan.
*
* @param[in] etmr etimer ctrl instance
*/
status_t sdrv_etimer_icu_start(sdrv_etimer_t *etmr);
/**
* @brief stop etimer icu chan.
*
* @param[in] etmr etimer ctrl instance
*/
status_t sdrv_etimer_icu_stop(sdrv_etimer_t *etmr);
/**
* @brief stop etimer icu get capture timestamp.
*
* @param[in] etmr etimer ctrl instance
* @return cpt_val : capture val
*/
uint32_t sdrv_etimer_icu_get_cnt_val(sdrv_etimer_t *etmr);
/**
* @brief stop etimer icu get channel level status.
*
* @param[in] etmr etimer ctrl instance
* @return high level : true low level : false
*/
bool sdrv_etimer_icu_get_level(sdrv_etimer_t *etmr);
#endif /* INCLUDE_DRV_SDRV_ETIMER_H */