1)睡眠模式
2)停止模式
3)待机模式
1、进入睡眠模式:
WFI 指令:__WFI
WFE 指令:__WFE
2、退出睡眠模式:
任何中断或事件都可以唤醒睡眠模式
Tickless低功耗模式的本质是通过调用指令 WFI 实现睡眠模式!
因此,可以在本该空闲任务执行的期间,让MCU 进入相应的低功耗模式;当其他任务准备运行的时候,唤醒MCU退出低功耗模式
1) configUSE_TICKLESS_IDLE 1 使能 0 不使能 2 自己实现低功耗使能
此宏用于使能低功耗 Tickless 模式
2)configEXPECTED_IDLE_TIME_BEFORE_SLEEP
此宏用于定义系统进入相应低功耗模式的最短时长
3)configPRE_SLEEP_PROCESSING(x)
此宏用于定义需要在系统进入低功耗模式前执行的事务,如:进入低功耗前关闭外设时钟,以达到降低功耗的目的。
4)configPOSR_SLEEP_PROCESSING(x)
此宏用于定义需要在系统退出低功耗模式后执行的事务,如:退出低功耗后开启之前关闭的外设时钟,以使系统能够正常运行。
#include "freertos_demo.h"
#include "./SYSTEM/usart/usart.h"
#include "./BSP/LED/led.h"
#include "./BSP/LCD/lcd.h"
#include "./SYSTEM/delay/delay.h"
/*FreeRTOS*********************************************************************************************/
#include "FreeRTOS.h"
#include "task.h"
/*注意要点:
*1.在FreeRTOSConfig.h中设置以下两个宏的值
*configUSE_TICKLESS_IDLE 置为1
*configEXPECTED_IDLE_TIME_BEFORE_SLEEP 置为2(预计低功耗持续时间至少为2秒)
*
*2.在FreeRTOSConfig.h中两个函数宏定义
* configPRE_SLEEP_PROCESSING(x) PRE_SLEEP_PROCESSING() 定义在进入低功耗模式前执行的函数
*configPOST_SLEEP_PROCESSING(x) POST_SLEEP_PROCESSING() 定义在退出低功耗模式后执行的函数
*
*3.在freertos_demo.h与freertos_demo.c 中分别声明和定义void PRE_SLEEP_PROCESSING(void)、 void POST_SLEEP_PROCESSING(void)
*
*4.在在FreeRTOSConfig.h中注意包涵"freertos_demo.h"文件
*/
/*FreeRTOS配置*/
/* START_TASK 任务 配置
* 包括: 任务句柄 任务优先级 堆栈大小 创建任务
*/
#define START_TASK_PRIO 1 /* 任务优先级 */
#define START_STK_SIZE 128 /* 任务堆栈大小 */
TaskHandle_t StartTask_Handler; /* 任务句柄 */
void start_task(void *pvParameters); /* 任务函数 */
/* TASK1 任务 配置
* 包括: 任务句柄 任务优先级 堆栈大小 创建任务
*/
#define TASK1_PRIO 2 /* 任务优先级 */
#define TASK1_STK_SIZE 128 /* 任务堆栈大小 */
TaskHandle_t Task1Task_Handler; /* 任务句柄 */
void task1(void *pvParameters); /* 任务函数 */
/******************************************************************************************************/
/**
* @brief FreeRTOS例程入口函数
* @param 无
* @retval 无
*/
void freertos_demo(void)
{
xTaskCreate((TaskFunction_t )start_task, /* 任务函数 */
(const char* )"start_task", /* 任务名称 */
(uint16_t )START_STK_SIZE, /* 任务堆栈大小 */
(void* )NULL, /* 传入给任务函数的参数 */
(UBaseType_t )START_TASK_PRIO, /* 任务优先级 */
(TaskHandle_t* )&StartTask_Handler); /* 任务句柄 */
vTaskStartScheduler();
}
/**
* @brief start_task
* @param pvParameters : 传入参数(未用到)
* @retval 无
*/
void start_task(void *pvParameters)
{
taskENTER_CRITICAL(); /* 进入临界区 */
/* 创建任务1 */
xTaskCreate((TaskFunction_t )task1,
(const char* )"task1",
(uint16_t )TASK1_STK_SIZE,
(void* )NULL,
(UBaseType_t )TASK1_PRIO,
(TaskHandle_t* )&Task1Task_Handler);
vTaskDelete(StartTask_Handler); /* 删除开始任务 */
taskEXIT_CRITICAL(); /* 退出临界区 */
}
/**
* @brief task1
* @param pvParameters : 传入参数(未用到)
* @retval 无
*/
void task1(void *pvParameters)
{
while(1)
{
LED0(1); /* LED0灭,指示退出低功耗模式 */
delay_ms(3000); /* CPU忙延时,期间不会进入低功耗模式 */
LED0(0); /* LED0亮,指示进入低功耗模式 */
vTaskDelay(3000); /* 阻塞延时,期间会进入低功耗模式 */
}
}
#if(configUSE_TICKLESS_IDLE !=0)
//进入低功耗模式前执行的函数
void PRE_SLEEP_PROCESSING()
{
//关闭部分外设时钟,仅作演示
__HAL_RCC_GPIOA_CLK_DISABLE();
__HAL_RCC_GPIOB_CLK_DISABLE();
__HAL_RCC_GPIOC_CLK_DISABLE();
__HAL_RCC_GPIOD_CLK_DISABLE();
__HAL_RCC_GPIOE_CLK_DISABLE();
__HAL_RCC_GPIOF_CLK_DISABLE();
__HAL_RCC_GPIOG_CLK_DISABLE();
}
//退出低功耗模式前执行的函数
void POST_SLEEP_PROCESSING()
{
//重启部分外设时钟,仅作演示
__HAL_RCC_GPIOA_CLK_ENABLE();
__HAL_RCC_GPIOB_CLK_ENABLE();
__HAL_RCC_GPIOC_CLK_ENABLE();
__HAL_RCC_GPIOD_CLK_ENABLE();
__HAL_RCC_GPIOE_CLK_ENABLE();
__HAL_RCC_GPIOF_CLK_ENABLE();
__HAL_RCC_GPIOG_CLK_ENABLE();
}
#endif
#ifndef __FREERTOS_DEMO_H
#define __FREERTOS_DEMO_H
void freertos_demo(void);
void PRE_SLEEP_PROCESSING(void);
void POST_SLEEP_PROCESSING(void);
#endif
/* 低功耗相关定义 */
#if (configUSE_TICKLESS_IDLE != 0)
#include "freertos_demo.h"
#define configPRE_SLEEP_PROCESSING(x) PRE_SLEEP_PROCESSING() /* 定义在进入低功耗模式前执行的函数 */
#define configPOST_SLEEP_PROCESSING(x) POST_SLEEP_PROCESSING() /* 定义在退出低功耗模式后执行的函数 */
#endif