网站维护需要关闭网站么,网页版qq农场,ps做字幕模板下载网站有哪些,网页设计茶叶网站建设参考教程#xff1a;【正点原子】手把手教你学FreeRTOS实时系统_哔哩哔哩_bilibili
一、事件标志组简介
1、概述
#xff08;1#xff09;事件标志位是一个“位”#xff0c;用来表示事件是否发生。
#xff08;2#xff09;事件标志组是一组事件标志位的集合#x…参考教程【正点原子】手把手教你学FreeRTOS实时系统_哔哩哔哩_bilibili
一、事件标志组简介
1、概述
1事件标志位是一个“位”用来表示事件是否发生。
2事件标志组是一组事件标志位的集合可以简单的理解事件标志组是一个整数。
3事件标志组的特点
①每一个位与一个事件相关联高8位除外高8位用作存储事件标志组的控制信息。下图所示的是32 位长度的事件标志组 ②每一位事件的含义以及高电平和低电平分别代表什么由用户自己决定。
③任意任务或中断都可以读写这些位。
④可以等待某一位成立或者等待多位同时成立。
4一个事件组就包含了一个EventBits_t数据类型的变量变量类型EventBits_t的定义如下所示它实际上是一个16位或32位无符号的数据类型。
typedef TickType_t EventBits_t;
#if ( configUSE_16_BIT_TICKS 1 )typedef uint16_t TickType_t;
#elsetypedef uint32_t TickType_t;
#endif
#define configUSE_16_BIT_TICKS 0
5事件标志组与队列、信号量的区别 功能 唤醒对象 事件清除 队列、信号量 事件发生时只会唤醒一个任务 是消耗型的资源队列的数据被读走就没了信号量被获取后就减少了 事件标志组 事件发生时会唤醒所有符合条件的任务可以理解为“广播”的作用 被唤醒的任务有两个选择可以让事件保留不动也可以清除事件
2、事件标志组相关API函数介绍
1事件标志组相关API函数概览 函数 描述 xEventGroupCreate() 使用动态方式创建事件标志组 xEventGroupCreateStatic() 使用静态方式创建事件标志组 xEventGroupClearBits() 清零事件标志位 xEventGroupClearBitsFromISR() 在中断中清零事件标志位 xEventGroupSetBits() 设置事件标志位 xEventGroupSetBitsFromISR() 在中断中设置事件标志位 xEventGroupWaitBits() 等待事件标志位 xEventGroupSync() 设置事件标志位并等待另一个事件标志位【A事件完成同时还要等待B事件发生】
2xEventGroupCreate函数
①函数定义
EventGroupHandle_t xEventGroupCreate
(void
)②返回值 返回值 描述 NULL 事件标志组创建失败 其它值 事件标志组创建成功返回其句柄
3xEventGroupClearBits函数
①函数定义
EventBits_t xEventGroupClearBits
(EventGroupHandle_t xEventGroup,const EventBits_t uxBitsToClear
) ②函数参数 形参 描述 xEventGroup 待操作的事件标志组句柄 uxBitsToSet 待清零的事件标志位
③返回值 返回值 描述 整数 清零事件标志位之前事件组中事件标志位的值
4xEventGroupSetBits函数
①函数定义
EventBits_t xEventGroupSetBits
(EventGroupHandle_t xEventGroup,const EventBits_t uxBitsToClear
) ②函数参数 形参 描述 xEventGroup 待操作的事件标志组句柄 uxBitsToSet 待设置的事件标志位
③返回值 返回值 描述 整数 函数返回时事件组中的事件标志位值
5xEventGroupWaitBits函数
①函数定义
EventBits_t xEventGroupWaitBits
(EventGroupHandle_t xEventGroup,const EventBits_t uxBitsToWaitFor,const BaseType_t xClearOnExit,const BaseType_t xWaitForAllBits,TickType_t xTicksToWait
)②函数参数 形参 描述 xEvenrGroup 等待的事件标志组句柄 uxBitsToWaitFor 等待的事件标志位可以用逻辑或等待多个事件标志位 xClearOnExit 成功等待到事件标志位后清除事件组中对应的事件标志位 pdTRUE 清除uxBitsToWaitFor指定位 pdFALSE不清除 xWaitForAllBits 等待 uxBitsToWaitFor 中的所有事件标志位逻辑与 pdTRUE等待的位全部为1 pdFALSE等待的位某个为1 xTicksToWait 等待的阻塞时间
③返回值 返回值 描述 等待的事件标志位值 等待事件标志位成功返回等待到的事件标志位 其它值 等待事件标志位失败返回事件组中的事件标志位
6xEventGroupSync函数
①函数定义
EventBits_t xEventGroupSync
(EventGroupHandle_t xEventGroup,const EventBits_t uxBitsToSet,const EventBits_t uxBitsToWaitFor,TickType_t xTicksToWait
)
②函数参数 形参 描述 xEventGroup 等待事件标志所在事件组 uxBitsToSet 达到同步点后要设置的事件标志 uxBitsToWaitFor 等待的事件标志 xTicksToWait 等待的阻塞时间
③返回值 返回值 描述 等待的事件标志位值 等待事件标志位成功返回等待到的事件标志位 其它值 等待事件标志位失败返回事件组中的事件标志位
二、事件标志组实验
1、原理图与实验目标
1原理图串口外设的接法与列表项的插入和删除实验相同下图未示出 2实验目标
①设计3个任务——start_task、task1、task2
[1]start_task用于创建其它三个任务并创建事件标志组。
[2]task1读取按键按下键值根据不同键值将事件标志组相应事件位置1模拟事件发生按下某个按键对应的标志位置1。
[3]task2同时等待事件标志组中的多个事件位当这些事件位都置1的话就执行相应的处理串口打印信息同时清除标志位。
②预期实验现象
[1]程序下载到板子上后暂时没有任何现象。
[2]按下相关按键串口会输出相应的信息。
2、实验步骤
1将“队列集操作实验”的工程文件夹复制一份在拷贝版中进行实验。
2更改FreeRTOS_experiment.c文件的内容如下所示。
#include FreeRTOS.h
#include task.h
#include LED.h
#include Key.h
#include Serial.h
#include queue.h
#include semphr.h
#include event_groups.h//宏定义
#define START_TASK_STACK_SIZE 128 //start_task任务的堆栈大小
#define START_TASK_PRIO 1 //start_task任务的优先级
#define TASK1_STACK_SIZE 128 //task1任务的堆栈大小
#define TASK1_PRIO 2 //task1任务的优先级
#define TASK2_STACK_SIZE 128 //task2任务的堆栈大小
#define TASK2_PRIO 3 //task2任务的优先级#define EVENTBIT_0 (1 0) //用该宏时表示希望事件标志组的bit0位置为1
#define EVENTBIT_1 (1 1) //用该宏时表示希望事件标志组的bit1位置为1EventGroupHandle_t eventgroup_handle; //定义事件标志组句柄//任务函数声明
void start_task(void);
void task1(void);
void task2(void);//任务句柄
TaskHandle_t start_task_handler; //start_task任务的句柄
TaskHandle_t task1_handler; //task1任务的句柄
TaskHandle_t task2_handler; //task2任务的句柄QueueSetHandle_t queueset_handle;void FreeRTOS_Test(void)
{//创建任务start_taskxTaskCreate((TaskFunction_t)start_task, //指向任务函数的指针start_task, //任务名字START_TASK_STACK_SIZE, //任务堆栈大小单位为字NULL, //传递给任务函数的参数START_TASK_PRIO, //任务优先级(TaskHandle_t *) start_task_handler //任务句柄就是任务的任务控制块);//开启任务调度器vTaskStartScheduler();
}void start_task(void)
{taskENTER_CRITICAL();eventgroup_handle xEventGroupCreate(); //创建事件标志组if(eventgroup_handle ! NULL){Serial_Printf(事件标志组创建成功\r\n);}xTaskCreate((TaskFunction_t) task1,(char *) task1,(configSTACK_DEPTH_TYPE) TASK1_STACK_SIZE,(void *) NULL,(UBaseType_t) TASK1_PRIO,(TaskHandle_t *) task1_handler );xTaskCreate((TaskFunction_t) task2,(char *) task2,(configSTACK_DEPTH_TYPE) TASK2_STACK_SIZE,(void *) NULL,(UBaseType_t) TASK2_PRIO,(TaskHandle_t *) task2_handler );vTaskDelete(NULL);taskEXIT_CRITICAL();
}void task1(void)
{uint8_t key 0;while(1) {key Key_GetNum();if(key 1){//将事件标志组的bit0位置1xEventGroupSetBits(eventgroup_handle, EVENTBIT_0);}else if(key 2){//将事件标志组的bit1位置1xEventGroupSetBits(eventgroup_handle, EVENTBIT_1);}vTaskDelay(10);}
}void task2(void)
{EventBits_t event_bit 0;while(1){event_bit xEventGroupWaitBits(eventgroup_handle, //事件标志组句柄EVENTBIT_0 | EVENTBIT_1, //等待事件标志组的bit0和bit1位均置1pdTRUE, //等待到事件标志位后清除事件标志组的bit0和bit1位pdTRUE, //等待事件标志组的bit0和bit1位都置1,就成立portMAX_DELAY ); //死等Serial_Printf(等待到的事件标志位值为%#x\r\n,event_bit);}
}
3程序完善好后点击“编译”然后将程序下载到开发板上打开串口助手分析信息。
3、程序执行流程
1main函数全流程
①初始化串口模块。
②调用FreeRTOS_Test函数。 2测试函数全流程
①创建任务start_task。
②开启任务调度器。 3多任务调度执行阶段较为简单这里不再赘述。