欢迎友友指正🤗🤗🤗,有输出一起进步~
复习一下rtos理论(自己的感悟结合韦东山老师部分讲解)
概述
队列、信号量是只能唤醒一个任务,而事件组唤醒多任务(不传递数据,传数据通常配合队列、邮箱或全局变量);
常用在:多个条件都满足才启动任务:电源好、传感器就绪、通信连接成功...
事件组是 RTOS 中一种任务间同步与通信机制——其实就是一组二进制事件标志。每个位代表一个事件是否发生。
其中的高8位留给内核使用,只能用其他的位来表示事件
事件组函数
创建:
/* 创建一个事件组,返回它的句柄。 * 此函数内部会分配事件组结构体 * 返回值: 返回句柄,非NULL表示成功 */ EventGroupHandle_t xEventGroupCreate( void ); /* 创建一个事件组,返回它的句柄。 * 此函数无需动态分配内存,所以需要先有一个StaticEventGroup_t结构体,并传入它的指针 * 返回值: 返回句柄,非NULL表示成功 */ EventGroupHandle_t xEventGroupCreateStatic( StaticEventGroup_t * pxEventGroupBuffer );删除:
对于动态创建的事件组,不再需要它们时,可以删除它们以回收内存。
/* * xEventGroup: 事件组句柄,你要删除哪个事件组 */ void vEventGroupDelete( EventGroupHandle_t xEventGroup );
设置事件:
/* 设置事件组中的位 * xEventGroup: 哪个事件组 * uxBitsToSet: 设置哪些位? * 如果uxBitsToSet的bitX, bitY为1, 那么事件组中的bitX, bitY被设置为1 * 可以用来设置多个位,比如 0x15 就表示设置bit4, bit2, bit0 * 返回值: 返回原来的事件值(没什么意义, 因为很可能已经被其他任务修改了) */ EventBits_t xEventGroupSetBits( EventGroupHandle_t xEventGroup, const EventBits_t uxBitsToSet ); /* 设置事件组中的位 * xEventGroup: 哪个事件组 * uxBitsToSet: 设置哪些位? * 如果uxBitsToSet的bitX, bitY为1, 那么事件组中的bitX, bitY被设置为1 * 可以用来设置多个位,比如 0x15 就表示设置bit4, bit2, bit0 * pxHigherPriorityTaskWoken: 有没有导致更高优先级的任务进入就绪态? pdTRUE-有, pdFALSE-没有 * 返回值: pdPASS-成功, pdFALSE-失败 */ BaseType_t xEventGroupSetBitsFromISR( EventGroupHandle_t xEventGroup, const EventBits_t uxBitsToSet, BaseType_t * pxHigherPriorityTaskWoken );
等待事件:
EventBits_t xEventGroupWaitBits( EventGroupHandle_t xEventGroup, const EventBits_t uxBitsToWaitFor, const BaseType_t xClearOnExit, const BaseType_t xWaitForAllBits, TickType_t xTicksToWait );先引入一个概念:unblock condition。一个任务在等待事件发生时,它处于阻塞状态;当期望的时间发生时,这个状态就叫"unblock condition",非阻塞条件,或称为"非阻塞条件成立";当"非阻塞条件成立"后,该任务就可以变为就绪态。
可以使用*xEventGroupWaitBits()等待期望的事件,它发生之后再使用xEventGroupClearBits()*来清除。但是这两个函数之间,有可能被其他任务或中断抢占,它们可能会修改事件组。
可以使用设置xClearOnExit为pdTRUE,使得对事件组的测试、清零都在*xEventGroupWaitBits()*函数内部完成,这是一个原子操作。
同步点:
多个任务都好了后才会开动;
使用xEventGroupSync()函数可以同步多个任务:
- 可以设置某位、某些位,表示自己做了什么事
- 可以等待某位、某些位,表示要等等其他任务
- 期望的时间发生后,xEventGroupSync()才会成功返回。
- xEventGroupSync成功返回后,会清除事件
EventBits_t xEventGroupSync( EventGroupHandle_t xEventGroup, const EventBits_t uxBitsToSet, const EventBits_t uxBitsToWaitFor, TickType_t xTicksToWait );