/** * @file timer.c * @author chipsea * @brief * @version 0.1 * @date 2020-11-30 * @copyright Copyright (c) 2020, CHIPSEA Co., Ltd. * @note */ #include "sdk_config.h" #include "rom_sym_def.h" #include "timer.h" #include "error.h" #include "clock.h" #include "pwrmgr.h" #include "jump_function.h" AP_TIM_TypeDef* const TimerIndex[FREE_TIMER_NUMBER]= {AP_TIM5,AP_TIM6}; static ap_tm_hdl_t s_ap_callback = NULL; __ATTR_SECTION_SRAM__ static int HalTiemrClearInt(AP_TIM_TypeDef *TIMx) { return TIMx->EOI; } static void HalTimerStopCounter(AP_TIM_TypeDef *TIMx) { TIMx->ControlReg = 0; TIMx->LoadCount = 0; //0x0 TIMx->CurrentCount = 0;//0x4 } static void HalTimerSetLoadTimer(AP_TIM_TypeDef *TIMx, int time) { if(time>0) { TIMx->ControlReg = 0x0; TIMx->ControlReg = 0x2; TIMx->LoadCount = 4*time;// 4MHz system timer, * 4 to convert to 1MHz timer TIMx->ControlReg = 0x3; } else { TIMx->ControlReg = 0x0; } } __ATTR_SECTION_SRAM__ void HalTimer5IRQHandler(void) { if(AP_TIM5->status & 0x1) { HalTiemrClearInt(AP_TIM5); if(s_ap_callback) s_ap_callback(HAL_EVT_TIMER_5); } } __ATTR_SECTION_SRAM__ void HalTimer6IRQHandler(void) { if(AP_TIM6->status & 0x1) { HalTiemrClearInt(AP_TIM6); if(s_ap_callback) s_ap_callback(HAL_EVT_TIMER_6); } } static void HalTimerWakeupHandler(void) { if(s_ap_callback) s_ap_callback(HAL_EVT_WAKEUP); } void HalTimerSleepHandler(void) { if(s_ap_callback) s_ap_callback(HAL_EVT_SLEEP); } int HalTimerMaskInt(UserTimer_e timeId, bool en) { volatile AP_TIM_TypeDef *TIMx; if(timeId != AP_TIMER_ID_5 && timeId != AP_TIMER_ID_6) { return ERR_NOT_SUPPORTED; } TIMx = TimerIndex[timeId-AP_TIMER_ID_5]; if(en) TIMx->ControlReg |= (1 << 2); else TIMx->ControlReg &= ~(1 << 2); return ERR_NONE; } int HalTimerSet(UserTimer_e timeId, uint32_t us) { uint32_t time = us; switch(timeId) { case AP_TIMER_ID_5: JUMP_FUNCTION(V24_IRQ_HANDLER) = (uint32_t)&HalTimer5IRQHandler; NVIC_EnableIRQ((IRQn_Type)TIM5_IRQn); NVIC_SetPriority((IRQn_Type)TIM5_IRQn, IRQ_PRIO_HAL); HalTimerSetLoadTimer(AP_TIM5, time); hal_clk_gate_enable(MOD_TIMER5); break; case AP_TIMER_ID_6: JUMP_FUNCTION(V25_IRQ_HANDLER) = (uint32_t)&HalTimer6IRQHandler; NVIC_EnableIRQ((IRQn_Type)TIM6_IRQn); NVIC_SetPriority((IRQn_Type)TIM6_IRQn, IRQ_PRIO_HAL); HalTimerSetLoadTimer(AP_TIM6, time); hal_clk_gate_enable(MOD_TIMER6); break; default: return ERR_INVALID_PARAM; } return ERR_NONE; } int HalTimerStop(UserTimer_e timeId) { switch(timeId) { case AP_TIMER_ID_5: JUMP_FUNCTION(V24_IRQ_HANDLER) = 0; HalTimerStopCounter(AP_TIM5); NVIC_DisableIRQ((IRQn_Type)TIM5_IRQn); hal_clk_gate_disable(MOD_TIMER5); break; case AP_TIMER_ID_6: JUMP_FUNCTION(V25_IRQ_HANDLER) = 0; HalTimerStopCounter(AP_TIM6); NVIC_DisableIRQ((IRQn_Type)TIM6_IRQn); hal_clk_gate_disable(MOD_TIMER6); break; default: return ERR_INVALID_PARAM; } return ERR_NONE; } int HalTimerInit(ap_tm_hdl_t callback) { s_ap_callback = callback; HalTimerStop(AP_TIMER_ID_5); HalTimerStop(AP_TIMER_ID_6); return hal_pwrmgr_register(MOD_TIMER, HalTimerSleepHandler, HalTimerWakeupHandler); } int HalTimerDeinit(void) { s_ap_callback = NULL; return hal_pwrmgr_unregister(MOD_TIMER); }