I’m trying to understand how queues work. I have been looking at the code and I see the structure of the queue contains the pointers pcHead, pcWriteTo, and pcReadFrom in addition to a few others.
The queue is created as follows:
and then it moves the pointer pucQueueStorage to the next Queue_t, but why so? aren’t we supposed to have one queue that contains defined number of structs?
so I initialized the buffer of the struct and after calling xQueueSendToBackFromISR(), looks like the contents of the buffer are copied into pcWriteTo, and upon reading off of it into a local struct, I see the buffer gets initialized.
My question is: how does buffer get initialized even though the reference of msg is being passed in?
If each structure is 20 bytes long, and you want to send the whole structure to the queue, then each space in the queue needs to be 20 bytes long. Then the structure is simply copied into the queue storage area when you send to the queue and out of the queue storage area when you read from the queue. This is “queue by copy” - but as described on the link above, you can also queue by reference, in which case you just queue a pointer to the structure. Then each space in the queue should be four bytes (assuming pointers on your MCU are four bytes, as would be the case on an ARM Cortex-M), and you copy a pointer to the structure into and out of the queue instead of copying the entire structure.
Queuing the structures themselves is easier from the application writers point of view as the sender can write over the structure immediately after sending to the queue. Queuing pointers to the structures uses less RAM and is moderately faster, but harder from the application writers point of view as you have to keep track of who ‘owns’ the memory being pointed to.
Queue_t is metadata about the queue which in addition to other items, contains the following two items:
int8_t *pcHead; /*< Points to the beginning of the queue storage area. */
int8_t *pcWriteTo; /*< Points to the free next place in the storage area. */
The memory is allocated both for Queue_t and the Queue items. First, Queue_t is placed followed by Queue items. The following lines initialize the pcHead and pcWriteTo members of Queue_t for a new queue:
The Queue_t is the ‘control’ part of the Queue, it holds the pointers into the data area, and other information needed by the scheduler and other parts to make everything work. It has the same structure for all Queue. After it is the ‘data’ section, where the data that is put on the queue is stored.