Queue Sets vs Event Groups

toll13 wrote on Wednesday, August 12, 2015:

I am using STM32Cube with CMSIS and FreeRTOS.

I need to have a thread that waits for either a signal (binary semaphore), or a message queue (Simultaneously).
I first tried to use CMSIS Signals and osWait, but it seems that they are not actually implemented. For this reason I am changing to using ‘bare’ FreeRTOS.

I see that FreeRTOS supports both Event Groups, and Queue Sets. It seems that Queue Sets are designed specifically for waiting on a queue and signal simultaneously, however, the queue I am using is 100 elements deep, and I am concerned with the overhead of the Queue Sets.

Is this a legitimate concern? If so would an Event Group be a viable alternative?

rtel wrote on Wednesday, August 12, 2015:

It is a legitimate concern if you are short of RAM, and only you know if that is the case.

An event group will most likely be a viable alternative, but again it depends on your application. If there is only one possible receiving task for your binary semaphore, then the binary semaphore can be replaced by a single bit in the event group. Another bit in the event group can then be used to signal that there is something in the queue. Your task will then block on the event group to know which events occur - if the bit that represents the old binary semaphore gets set, then you take whatever action used to be performed after the binary semaphore was given - if the bit that represents something being in the queue you read from the queue.

In the later case, make sure you read all the data from the queue before returning to block on the event group again, as the event group cannot tell you how much data is in the queue, just that something is in the queue.

The disadvantage of this will be if the binary semaphore is given from an interrupt. Setting a bit in an event group from an interrupt is a longer operation than giving a binary semaphore from an interrupt because the event group operation is deferred to the RTOS daemon task, rather than being performed in the interrupt itself. The rataionale being that setting a bit in an event group is not a deterministic operation (you don’t know how many tasks will get unblocked because the bit is set), and the FreeRTOS implementation standard does not permit any non-deterministic operations to be performed from an interrupt or from within a critical section.

Again, if there is only one receiving task, you may also consider using a direct to task notification with the action set to eSetBits. That action can be performed directly within an interrupt, and is much faster too.