1 LED驱动流程图分析
这里主要分析led_on和led_blink流程。
1.1 led_on流程图分析
1.2 led_blink流程图分析
2 代码实现
代码使用HAL库开发,并且配置freertos。HAL配置太简单了,没啥需要注意的就不记录了。
drv_led.h:
#ifndef __DRV_LED_H
#define __DRV_LED_H
void led_init(void);
void led_on(uint32_t time_sec);
void led_off(void);
void led_blink(uint32_t period,uint32_t time_sec);
#endif
drv_led.c:
#include <stdbool.h>
#include <string.h>
#include "main.h"
#include "FreeRTOS.h"
#include "timers.h"
#define LED_OFF() HAL_GPIO_WritePin(LED_GPIO_Port,LED_Pin,GPIO_PIN_SET)
#define LED_ON() HAL_GPIO_WritePin(LED_GPIO_Port,LED_Pin,GPIO_PIN_RESET)
#define LED_TOGGLE() HAL_GPIO_TogglePin(LED_GPIO_Port,LED_Pin)
typedef enum{
LED_STATE_OFF,
LED_STATE_ON,
LED_STATE_BLINK,
}led_state_e;
static bool is_inited=false;
static TimerHandle_t timer_led;
static uint8_t state;
struct led_control_t
{
uint32_t time_on;
uint32_t time_blink;
uint32_t period_blink;
uint32_t cnt_time_on;
uint32_t cnt_time_blink;
uint32_t cnt_period_blink;
}ledctl;
void led_timer_callback( TimerHandle_t xTimer )
{
switch (state)
{
case LED_STATE_ON:
ledctl.cnt_time_on++;
if(ledctl.cnt_time_on>=ledctl.time_on)
{
LED_OFF();
ledctl.cnt_time_on=0;
xTimerStop(timer_led,1000);
}
break;
case LED_STATE_BLINK:
ledctl.cnt_time_blink++;
ledctl.cnt_period_blink++;
if(ledctl.cnt_time_blink>=ledctl.time_blink)
{
LED_OFF();
ledctl.cnt_time_blink=0;
xTimerStop(timer_led,1000);
break;
}
if(ledctl.cnt_period_blink>=ledctl.period_blink)
{
ledctl.cnt_period_blink=0;
LED_TOGGLE();
}
break;
default:
break;
}
}
void led_init(void)
{
state=LED_STATE_OFF;
memset(&ledctl,0,sizeof(ledctl));
timer_led=xTimerCreate("timer_led",100,pdTRUE,NULL,led_timer_callback);
LED_OFF();
is_inited=true;
}
void led_on(uint32_t time_sec)
{
if(!is_inited)return ;
xTimerStop(timer_led,1000);
ledctl.time_on=time_sec*10;
ledctl.cnt_time_on=0;
LED_ON();
state=LED_STATE_ON;
xTimerStart(timer_led,1000);
}
void led_off(void)
{
if(!is_inited)return ;
xTimerStop(timer_led,1000);
LED_OFF();
state=LED_STATE_OFF;
ledctl.cnt_time_on=0;
ledctl.cnt_time_blink=0;
ledctl.cnt_period_blink=0;
}
void led_blink(uint32_t period,uint32_t time_sec)
{
if(!is_inited)return ;
xTimerStop(timer_led,1000);
ledctl.time_blink=time_sec*10;
ledctl.period_blink=period;
ledctl.cnt_time_blink=0;
ledctl.cnt_period_blink=0;
LED_ON();
state=LED_STATE_BLINK;
xTimerStart(timer_led,1000);
}