#include "SN_STOP.h" /* 文件名:SN_STOP.c/.h 作者: SN_FAE_黄泽洪 免责声明:无版权,可随意传播和篡改,该代码仅供开发参考,如需使用请自行验证 本人不担负商业使用上带来的风险。 */ /* 方法一:使用LPTIMER唤醒休眠 //在SN_STOP.c的文件中添加用户的关闭函数和初始函数 //退出休眠后,要重新开启的片上设备函数列表,将函数添加到此列表中 static void OPEN(void){ SN_SYSCLK_set(SYSCLK_48MHZ); //休眠退出后重新初始系统时钟 std_delay_init(); return; } //进入休眠前,要关闭的片上设备函数列表,将函数添加到此列表中 static void CLOSE(void){ //暂时没有 return; } //在main.c文件里面 uint8_t stop = 1; uint8_t k = 0 ; int main(void){ SN_SYSCLK_set(SYSCLK_48MHZ); std_delay_init(); std_delayms(3000); SN_GPIO_PIN_init(GPIOA ,GPIO_PIN_5 , GPIO_MODE_OUTPUT ,GPIO_PULLUP ,GPIO_OUTPUT_OPENDRAIN); SN_GPIO_PIN_toggle(GPIOA, GPIO_PIN_5); SN_LPtim_Rouse( 3000 ); //范围0x0000 - (0xffff-1) 使用lptimer唤醒 while(1){ if(stop){ SN_STOP_EN(); //进入休眠 SN_GPIO_PIN_toggle(GPIOA, GPIO_PIN_5); //退出休眠后翻转io SN_LPtim_ARR(3000+k*100); //修改下一次的休眠时间 } k++; } } 方法二:使用触发唤醒 //在SN_STOP.c的文件中添加用户的关闭函数和初始函数 //退出休眠后,要重新开启的片上设备函数列表,将函数添加到此列表中 static void OPEN(void){ SN_SYSCLK_set(SYSCLK_48MHZ); //休眠退出后重新初始系统时钟 std_delay_init(); return; } //进入休眠前,要关闭的片上设备函数列表,将函数添加到此列表中 static void CLOSE(void){ //暂时没有 return; } //在main.c文件里面 uint8_t stop = 1; uint8_t k = 0 ; void LED(void){ //空的回调函数 return; } int main(void){ SN_SYSCLK_set(SYSCLK_48MHZ); std_delay_init(); std_delayms(3000); SN_GPIO_PIN_init(GPIOA ,GPIO_PIN_5 , GPIO_MODE_OUTPUT ,GPIO_PULLUP ,GPIO_OUTPUT_OPENDRAIN); SN_GPIO_PIN_toggle(GPIOA, GPIO_PIN_5); SN_EXIT_set(GPIOA,GPIO_PIN_1,GPIO_PULLUP,LED,EXTI_TRIGGER_FALLING,NVIC_PRIO_3); //使能IO触发 while(1){ if(stop){ SN_STOP_EN(); //进入休眠 SN_GPIO_PIN_toggle(GPIOA, GPIO_PIN_5); //退出休眠后翻转io SN_LPtim_ARR(3000+k*100); //修改下一次的休眠时间 } k++; } } */ //休眠时间 __IO uint16_t STOP_ARR = 0; //LPTIME标志 __IO uint8_t LPTIME_FLG = 0; /*========================================================================================================== */ /* 用户要将设备关闭和启动的接口放到下面的列表里面 |*/ /*========================================================================================================== */ //进入休眠前,要关闭的片上设备函数列表,将函数添加到此列表中 static void CLOSE(void){ return; } //退出休眠后,要重新开启的片上设备函数列表,将函数添加到此列表中 static void OPEN(void){ SN_SYSCLK_set(SYSCLK_48MHZ); //休眠退出后重新初始系统时钟 std_delay_init(); return; } /*==========================================================================================================*/ /* 函数名称:SN_STOP_IN() 函数功能:进入休眠,M0内核进入休眠 参数:无 返回:无 */ void SN_STOP_EN(void){ //进入休眠前关闭片上外设 CLOSE(); //进入休眠链接CMSIS接口,进入stop模式-------------------------------------------------------------------------in stop std_lptim_interrupt_enable(LPTIM_INTERRUPT_ARRM); std_lptim_enable(); //使能LPTIM if((STOP_ARR>0) && LPTIME_FLG){ std_lptim_set_auto_reload(STOP_ARR);/* 启动LPTIM1计数 */ std_lptim_start_counter(LPTIM_COUNT_SINGLE); //单次 } std_pmu_enter_stop(PMU_MODE, PMU_ENTRY_LOWPOWER_MODE_WFE); //进入stop模式 //----------------------------------------退出休眠继续执行下面的代码------------------------------------------out stop if(LPTIME_FLG){ std_lptim_disable(); } //关闭LPTIM //推出休眠重新开启的片上外设与系统时钟 OPEN(); } /* 函数名称:SN_LPtim_Rouse() 函数功能:使用系统时钟唤醒,初始化一次 参数:唤醒的计数值 (周期和频率,在SN_STOP.h里面的宏定义修改,LPTIM定时器的工作参数) 返回:无 注意:RCL的时钟是32Khz 休眠时间计算公式: (32k/LPTIM_PRESCALER_DIV_x )*CNT = 休眠时间 */ void SN_LPtim_Rouse( uint16_t cnt ){ STOP_ARR = cnt; SN_LPtim_SN_LPtim_EN(); /* 使能RCL时钟并等待时钟稳定 */ std_rcc_rcl_enable(); while(std_rcc_get_rcl_ready() != RCC_CSR2_RCLRDY); /* 选择LPTIM1的时钟源为RCL */ std_rcc_set_lptim1clk_source(RCC_LPTIM1_ASYNC_CLK_SRC_RCL); /* 使能LPTIM1时钟 */ std_rcc_apb1_clk_enable(RCC_PERIPH_CLK_LPTIM1); std_lptim_disable(); //关闭LPTIM /* 设置LPTIM1预分频器 */ std_lptim_set_prescaler(LPTIM_PRESCALER_DIV_x); /* 禁止LPTIM1中断唤醒*/ std_exti_interrupt_disable(EXTI_LINE_LPTIM1); /* 使能LPTIM1事件唤醒 */ std_exti_event_enable(EXTI_LINE_LPTIM1); // NVIC_SetPriority(LPTIM1_IRQn, NVIC_PRIO_0); // NVIC_EnableIRQ(LPTIM1_IRQn); } /* 函数名称:SN_LPtim_ARR 函数功能:更新使用系统时钟唤醒时间 参数:唤醒的计数值 返回:无 注意: */ void SN_LPtim_ARR(uint16_t cnt){ STOP_ARR = cnt; } /* 函数名称:SN_LPtim_Stop 函数功能:停用LPtim唤醒 参数:无 返回:无 注意: */ void SN_LPtim_SN_LPtim_Stop(void){ LPTIME_FLG = 0; //不使用lptime唤醒 std_lptim_disable(); //关闭lptime } /* 函数名称:SN_LPtim_EN 函数功能:重新使用LPtim唤醒 参数:无 返回:无 注意: */ void SN_LPtim_SN_LPtim_EN(void){ LPTIME_FLG = 1; //使用lptime唤醒 }