当前位置:网站首页>[practice] STM32 FreeRTOS migration series tutorial 5:freertos message queue

[practice] STM32 FreeRTOS migration series tutorial 5:freertos message queue

2022-06-21 09:14:00 Huaqing vision it open laboratory

Write it at the front :

This article is 《STM32MP157 Developing a tutorial FreeRTOS Operating system 》 One in a series , The development platform used by the author is Huaqing vision FS-MP1A Development board (STM32MP157 Development board ).stm32mp157 yes ARM Dual core ,2 individual A7 nucleus ,1 individual M4 nucleus ,A7 You can run on the core Linux operating system ,M4 You can run on the core FreeRTOS、RT-Thread And other real-time operating systems ,STM32MP157 Development board, so you can learn Embedded linux, You can also learn. stm32 Single chip microcomputer .

in the light of FS-MP1A Development board , except FreeRTOS Outside the operating system , There are also many other series of tutorials , Include Cortex-A7 Development of article 、Cortex-M4 Development of article 、 Expansion board driver transplantation 、Linux Application development 、Linux System transplantation 、Linux Driving development 、 Hardware design 、 Artificial intelligence machine vision 、Qt Application programming 、Qt Comprehensive project practice, etc . Welcome to your attention , more stm32mp157 Develop tutorials and videos , Technical exchange can be added Q Group 459754978, Thank you for attention .

FS-MP1A Development board Details :https://item.taobao.com/item.htm?id=622457259672

2.FreeRTOS queue

2.1 Introduction to queue

Queues can be used for tasks and tasks 、 Communication between task and interrupt , Between tasks and tasks 、 Transfer data between tasks and interrupts , A limited number of... Can be stored in the queue 、 Fixed size data items .

In general , Queues are first in first out (FIFO) The storage mechanism of , That is to say, the data sent to the queue is extracted first , Of course, you can also use first in and last out (LIFO) Storage buffer ,FreeRTOS Two storage buffer mechanisms are provided in .

The queue does not belong to a specific task , For all tasks, data can be sent to the task , You can also extract data from tasks . Queue function

2.2.1  Create a queue

There are two functions for creating event flag groups , They are as follows :

xQueueCreate(), This function is used to dynamically create queues , The required memory is allocated through dynamic memory management , This function is a macro , When the queue creation function is actually completed xQueueGenericCreate(). The function prototype is as follows :

QueueHandle_t  xQueueCreate(UBaseType_t uxQueueLength,

UBaseType_t uxItemSize)

Parameters :

uxQueueLength:   The queue length of the queue to be created , Here is the number of items in the queue .

uxItemSize:       Each item in the queue ( news ) The length of , The unit is byte .

Return value :

NULL:  Queue creation failed .

Other values : The queue handle returned by the successfully created queue .

xQueueCreate Static(), This function creates a queue for static methods , The required memory is allocated by the user , This function is also a macro , The final call is the function xQueueGenericCreateStatic(). The function prototype is as follows :

QueueHandle_t xQueueCreateStatic(UBaseType_t  uxQueueLength,

                              UBaseType_t  uxItemSize,

                              uint8_t*  pucQueueStorageBuffer,

                              StaticQueue_t*  pxQueueBuffer)

Parameters :

uxQueueLength:      The queue length of the queue to be created , Here is the number of items in the queue .

uxItemSize:          Each item in the queue ( news ) The length of , The unit is byte

pucQueueStorage:      Point to the storage area of the queue item , That is, the message store , This store requires

Assigned by the user . This parameter must point to a uint8_t An array of types . This

The storage area must be greater than or equal to (uxQueueLength * uxItemsSize) byte .

pxQueueBuffer:        This parameter points to a StaticQueue_t Variable of type , Used to save the queue structure .

Return value :

NULL:  Queue creation failed .

Other values : The queue handle returned by the successfully created queue .

2.2.2  Sends a message to the queue

After the queue is created, messages can be sent to it ,FreeRTOS To send messages to the queue API Function has 8 individual , They are as follows :

function xQueueSend()、xQueueSendToBcck() and xQueueSendToFront()

These three functions are used to send messages to the queue , Functions are essentially macros , among xQueueSend() and xQueueSendToBcck() Is to add messages to the back of the queue ,xQueueSendToFront() Is to add a message to the front of the queue , These three functions eventually call the same function :xQueueGenericSend(), Can only be used in task functions , The function prototypes are as follows :

  BaseType_t  xQueueSend( QueueHandle_t xQueue,

const void * pvItemToQueue,

TickType_t xTicksToWait)

  BaseType_t  xQueueSendToBack(QueueHandle_t xQueue,

const void*  pvItemToQueue,

TickType_t  xTicksToWait)

  BaseType_t  xQueueSendToFront(QueueHandle_t  xQueue,

const void *  pvItemToQueue,

TickType_t xTicksToWait)

Parameters :

xQueue:               Handle to the queue , Indicates which queue to send data to , After the queue is created successfully, the

Returns the queue handle for this queue .

pvItemToQueue:        Point to the message to send , When sending, the message will be copied to the queue .

xTicksToWait:          Blocking time , This parameter indicates that when the queue is full, the task enters the blocking state and waits for the queue

Maximum time the column is idle .

Return value :

pdPASS:               Sending message to queue succeeded .

ErrQUEUE_FULL:      The queue is full , Message delivery failed

     function xQueueOverwrite(), This function is also used to send data to the queue , But when the queue is full, the old data will be overwritten , Whether or not this data has been taken away by other tasks or interrupts , This function is also a macro , The final call is also the function xQueueGenericSend(), The function prototype is as follows :

BaseType_t  xQueueOverwrite( QueueHandle_t  xQueue,

const void *  pvItemToQueue)

Parameters :

xQueue:               Handle to the queue , Indicates which queue to send data to , After the queue is created successfully, the

Returns the queue handle for this queue .

pvItemToQueue:        Point to the message to send , When sending, the message will be copied to the queue .

Return value :

pdPASS:    Sending message to queue succeeded , This function will only return pdPASS! Because during the execution of this function

Don't care if the queue is full , When it is full, it overwrites the old data , In short, it will succeed .

function xQueueGenericSend(), All the previous task level queueing functions finally call this function , The function prototype is as follows :

BaseType_t  xQueueGenericSend (QueueHandle_t  xQueue,

const void *   pvItemToQueue,

TickType_t  xTicksToWait,

const BaseType_t  xCopyPosition)

Parameters :

xQueue:               Handle to the queue , Indicates which queue to send data to , After the queue is created successfully, the

Returns the queue handle for this queue .

pvItemToQueue:        Point to the message to send , When sending, the message will be copied to the queue .

xTicksToWait:          Blocking time .

xCopyPosition:         The way to join the team , There are three kinds of

                        queueSEND_TO_BACK:   Back into the team

queueSEND_TO_FRONT: Forward into the team

queueOVERWRITE:       Override team .

Return value :

pdTRUE:               Sending message to queue succeeded .

errQUEUE_FULL:       The queue is full , Message delivery failed

function xQueueSendFromISR()、xQueueSendToBcckFromISR ()、

xQueueSendToFrontFromISR ()

These three functions are used to send messages to the queue in the interrupt service function , These are the interrupt versions of the previous three functions that send messages to the queue , Functions are also macros in nature , Finally, the same function is called xQueueGenericSendFromISR(), The function prototypes are as follows :

BaseType_t xQueueSendFromISR( QueueHandle_t  xQueue,

const void *   pvItemToQueue,

BaseType_t *  pxHigherPriorityTaskWoken)

BaseType_t xQueueSendToBackFromISR(QueueHandle_t xQueue,

const void * pvItemToQueue,

BaseType_t *  pxHigherPriorityTaskWoken)

  BaseType_t xQueueSendToFrontFromISR(QueueHandle_t  xQueue,

const void *  pvItemToQueue,

BaseType_t *  pxHigherPriorityTaskWoken)

Parameters :

xQueue:               Handle to the queue , Indicates which queue to send data to , After the queue is created successfully, the

Returns the queue handle for this queue .

pvItemToQueue:        Point to the message to send , When sending, the message will be copied to the queue .

pxHigherPriorityTaskWoken: Mark whether to switch tasks after exiting this function

Return value :

pdTRUE:               Sending message to queue succeeded .

errQUEUE_FULL:       The queue is full , Message delivery failed

function xQueueOverwriteFromISR(), This function is xQueueOverwrite() Broken version of , This function is also a macro , The final call is also the function xQueueGenericSendFromISR(), The function prototype is as follows :

BaseType_t  xQueueOverwriteFromISR( QueueHandle_t  xQueue,

const void *  pvItemToQueue,

BaseType_t *  pxHigherPriorityTaskWoken)

Parameters :

xQueue:               Handle to the queue , Indicates which queue to send data to , After the queue is created successfully, the

Returns the queue handle for this queue .

pvItemToQueue:        Point to the message to send , When sending, the message will be copied to the queue .

pxHigherPriorityTaskWoken: Mark whether to switch tasks after exiting this function

Return value :

pdTRUE:               Sending message to queue succeeded .

errQUEUE_FULL:       The queue is full , Message delivery failed

function xQueueGenericSendFromISR(), All previous interrupt level queueing functions finally call this function , This function is also a function xQueueGenericSend() Broken version of , The function prototype is as follows :

BaseType_t  xQueueGenericSend FromISR (QueueHandle_t  xQueue,

const void *  pvItemToQueue,

BaseType_t*  pxHigherPriorityTaskWoken,

                                        BaseType_t  xCopyPosition)

Parameters :

xQueue:                 Handle to the queue , Indicates which queue to send data to , After the queue is created successfully

The queue handle of this queue will be returned .

pvItemToQueue:           Point to the message to send , When sending, the message will be copied to the queue .

pxHigherPriorityTaskWoken:        Mark whether to switch tasks after exiting this function .

xCopyPosition:           The way to join the team , There are three kinds of

                        queueSEND_TO_BACK:   Back into the team

queueSEND_TO_FRONT: Forward into the team

queueOVERWRITE:       Override team .

Return value :

pdTRUE:               Sending message to queue succeeded .

errQUEUE_FULL:       The queue is full , Message delivery failed

2.2.3  Read messages from the queue

Corresponding to joining the team , Then there will be a team , Getting out of the queue is getting messages from the queue ,FreeRTOS Out of the queue provided in API The functions are as follows :

xQueueReceive(), This function is used to read a message from the queue in the task , This data will be deleted after reading successfully , This function is a macro , The function that is actually executed is xQueueGenericReceive(), The prototype of this function is as follows :

BaseType_t  xQueueReceive(QueueHandle_t  xQueue,

void *  pvBuffer,

TickType_t  xTicksToWait)

Parameters :

xQueue:         Handle to the queue , Indicate which queue data to read , This message will be returned after the queue is successfully created

Queue handle of the queue .

pvBuffer:        Buffer to hold data , During the process of reading the queue, the read data will be copied to this

Buffer zone .

  xTicksToWait:    Blocking time , This parameter indicates that when the queue is empty, the task enters the blocking state and waits for several times in the queue

According to the maximum time .

Return value :

pdTRUE:        Reading message from queue succeeded .

pdFALSE:       Failed to read message from queue .

    xQueuePeek(), This function is also used to read a message from the queue in the task , However, this data will not be deleted after successful reading , This function is also a macro , The function that is actually executed is xQueueGenericReceive(), The prototype of this function is as follows :

BaseType_t xQueuePeek( QueueHandle_t  xQueue,

void *  pvBuffer,

TickType_t  xTicksToWait)

Parameters :

xQueue:         Handle to the queue , Indicate which queue data to read , This message will be returned after the queue is successfully created

Queue handle of the queue .

pvBuffer:        Buffer to hold data , During the process of reading the queue, the read data will be copied to this

Buffer zone .

  xTicksToWait:    Blocking time , This parameter indicates that when the queue is empty, the task enters the blocking state and waits for several times in the queue

According to the maximum time .

Return value :

pdTRUE:        Reading message from queue succeeded .

pdFALSE:       Failed to read message from queue .

xQueueReceiveFromISR(), This function is xQueueReceive() Broken version of , Used to read messages from the queue in the interrupt service function , The function prototype is as follows :

BaseType_t xQueueReceiveFromISR(QueueHandle_t  xQueue,

void*  pvBuffer,

BaseType_t *  pxTaskWoken)

Parameters :

xQueue:           Handle to the queue , Indicate which queue data to read , After the queue is successfully created, it will return

The queue handle for this queue .

pvBuffer:          Buffer to hold data , During the process of reading the queue, the read data will be copied here

In a buffer .

pxTaskWoken:      Mark whether to switch tasks after exiting this function

Return value :

pdTRUE:   Reading data from queue succeeded .

pdFALSE:   Failed to read data from queue .

xQueuePeekFromISR (), This function is xQueuePeek() Broken version of , After reading the data successfully, this data will not be deleted , The prototype of this function is as follows :

BaseType_t xQueuePeekFromISR( QueueHandle_t  xQueue,

void *  pvBuffer)

Parameters :

xQueue:         Handle to the queue , Indicate which queue data to read , This message will be returned after the queue is successfully created

Queue handle of the queue .

pvBuffer:        Buffer to hold data , During the process of reading the queue, the read data will be copied to this

Buffer zone .

Return value :

pdTRUE:        Reading message from queue succeeded .

pdFALSE:       Failed to read message from queue .

    1. Operation experiment

2.3.1 Experimental design

This design detects three key states through interruption , Read different key values and send them to the queue , Then read the messages in the queue in the task , Make different processing according to different instructions .

May refer to 12.3.2 Chapter to import the existing project , Project storage path 【 Huaqing vision -FS-MP1A Development of information \02- Program source code \ARM Architecture and interface technology \FreeRTOS\6_MP1A-FreeRTOS-Queue】

The tasks and their functions are as follows :

StartTask02():      Read the data in the queue , Do different processing according to the read data .

StartDefaultTask():  Read the key value , And send it to the queue .

2.3.2 Experimental process and analysis

First , Configure... According to the previous chapters CubeMX, Configure... According to the previous section “FREERTOS”, Generate code when finished . stay StartDefaultTask() And StartTask02() Add the following code to .

void StartDefaultTask(void *argument)

{

  /* USER CODE BEGIN 5 */

  /* Infinite loop */

uint8_t err;

  for(;;)

  {

          if((Key_Queue!=NULL)&&(key))   // Message queue Key_Queue Create success , And the button is pressed

          {

              err=xQueueSend(Key_Queue,&key,10);

              if(err==pdPASS)   // Send key value

              {

                  printf("\r data transmission success \n");

              }

             

          }

          vTaskDelay(10);                           // Time delay 10ms, That is to say 10 Individual clock time

  }

  /* USER CODE END 5 */ 

}

void StartTask02(void *argument)

{

  /* USER CODE BEGIN StartTask02 */

  /* Infinite loop */

  for(;;)

  {

  if(Key_Queue!=NULL)

      {

      if(xQueueReceive(Key_Queue,&key,portMAX_DELAY))// The request message Key_Queue

      {     

           switch(key)

           {

               case EVENTBIT_1://

                    LED_1_TOG();

                    break;

               case EVENTBIT_2://

                    LED_2_TOG();

                    break;

               case EVENTBIT_3://

                    LED_3_TOG();

                    break;

            }

           key = 0;

       }

   }

  vTaskDelay(10);      // Time delay 10ms, That is to say 10 Individual clock time

  }

  /* USER CODE END StartTask02 */

}

in addition , First you need to call... In the main function xQueueCreate () Function to create a message queue , Get the successfully created queue handle .

Write the key interrupt callback function as follows

void HAL_GPIO_EXTI_Rising_Callback(uint16_t GPIO_Pin)

{

switch(GPIO_Pin)

{

   case GPIO_PIN_8:

       if(HAL_GPIO_ReadPin(GPIOF,GPIO_PIN_8) == GPIO_PIN_SET) /* read KEY3 PF8 state */

        key = EVENTBIT_3;

       break;

   case GPIO_PIN_7:

   if(HAL_GPIO_ReadPin(GPIOF,GPIO_PIN_7) == GPIO_PIN_SET) /* read KEY2 PF7 state */

   key = EVENTBIT_2;

    break;

   case GPIO_PIN_9:

   if(HAL_GPIO_ReadPin(GPIOF,GPIO_PIN_9) == GPIO_PIN_SET) /* read KEY1 PF9 state */

   key = EVENTBIT_1;

    break;

}

}

  here , When pressed KEY1 Key time ,LED1 Level reversal ; When pressed KEY2 Key time ,LED2 Level reversal ; When pressed KEY3 Key time ,LED3 Level reversal .

Hardware platform : Huaqing vision FS-MP1A Development board (STM32MP157)

原网站

版权声明
本文为[Huaqing vision it open laboratory]所创,转载请带上原文链接,感谢
https://yzsam.com/2022/172/202206210908576281.html