20-FreeRTOS队列API函数

1- xQueueCreate

queue. h
 QueueHandle_t xQueueCreate( UBaseType_t uxQueueLength,
                             UBaseType_t uxItemSize );

创建一个新队列并返回 可引用此队列的句柄。 configSUPPORT_DYNAMIC_ALLOCATION 必须在 FreeRTOSConfig.h 中被设置为 1,或保留未定义状态(此时,它默认 为 1) ,才能使用此 RTOS API 函数。

每个队列需要 RAM 用于保存队列状态和 包含在队列(队列存储区域)中的项目。 如果使用 xQueueCreate() 创建队列,则所需的 RAM 将自动 从 FreeRTOS 堆中分配。 如果使用 xQueueCreateStatic() 创建队列, 则 RAM 由应用程序编写者提供,这会产生更多的参数, 但这样能够在编译时静态分配 RAM 。 请参阅静态分配与 动态分配页面了解详情。

1.1 参数:

1.2 Returns:

如果队列创建成功,则返回所创建队列的句柄 。 如果创建队列所需的内存无法 分配 ,则返回 NULL。

1.3 用法示例:

struct AMessage
{
    char ucMessageID;
    char ucData[ 20 ];
};

void vATask( void *pvParameters )
{
QueueHandle_t xQueue1, xQueue2;

    /* 创建一个能够包含10个无符号长值的队列。 */
    xQueue1 = xQueueCreate( 10, sizeof( unsigned long ) );

    if( xQueue1 == NULL )
    {
        /* Queue was not created and must not be used. */
    }

    /* Create a queue capable of containing 10 pointers to AMessage
    structures.  These are to be queued by pointers as they are
    relatively large structures. */
    xQueue2 = xQueueCreate( 10, sizeof( struct AMessage * ) );

    if( xQueue2 == NULL )
    {
        /* Queue was not created and must not be used. */
    }

    /* ... Rest of task code. */
 }

2 xQueueCreateStatic

queue. h
 QueueHandle_t xQueueCreateStatic(
                             UBaseType_t uxQueueLength,
                             UBaseType_t uxItemSize,
                             uint8_t *pucQueueStorageBuffer,
                             StaticQueue_t *pxQueueBuffer );

创建一个新队列并返回 可以引用该队列的句柄。 configSUPPORT_STATIC_ALLOCATION 必须在 FreeRTOSConfig.h 中设置为 1,该 RTOS API 函数才可用。

每个队列都需要 RAM, 用于保存队列状态和队列中包含的数据项(队列存储区域)。 如果使用 xQueueCreate() 创建队列, 则会自动从 RAM 堆FreeRTOS中分配 。 如果使用 xQueueCreateStatic() 创建队列, 则 RAM 由应用程序编写者提供,这会产生更多的参数, 但这样能够在编译时静态分配 RAM 。 请参阅静态分配与 动态分配页面了解详情。

2.1 参数:

uxQueueLength 队列可同时容纳的最大项目数 。
uxItemSize 存储队列中的每个数据项所需的大小(以字节为单位)。
数据项按副本排队,而不是按引用排队, 因此该值为每个排队项目将被复制的字节数。队列中每个数据项 的大小必须相同。

pucQueueStorageBuffer 如果 uxItemSize 非零,则 pucQueueStorageBuffer 必须 指向一个至少足够大的 uint8_t 数组, 以容纳队列中可以同时存在的最大项数, 即 (uxQueueLength * uxItemSize) 个字节。 如果 uxItemSize 为零,则 pucQueueStorageBuffer 可以为 Null。
pxQueueBuffer 必须指向 StaticQueue_t 类型的变量, 该变量将用于保存队列的数据结构体。

2.2 Returns:

如果队列创建成功, 则返回已创建队列的句柄。 如果 pxQueueBuffer 为 NULL,则返回 NULL。

2.3 用法示例:

/* The queue is to be created to hold a maximum of 10 uint64_t
variables. */
#define QUEUE_LENGTH    10
#define ITEM_SIZE       sizeof( uint64_t )

/* The variable used to hold the queue's data structure. */
static StaticQueue_t xStaticQueue;

/* The array to use as the queue's storage area.  This must be at least
uxQueueLength * uxItemSize bytes. */
uint8_t ucQueueStorageArea[ QUEUE_LENGTH * ITEM_SIZE ];

void vATask( void *pvParameters )
{
QueueHandle_t xQueue;

    /* Create a queue capable of containing 10 uint64_t values. */
    xQueue = xQueueCreateStatic( QUEUE_LENGTH,
                                 ITEM_SIZE,
                                 ucQueueStorageArea,
                                 &xStaticQueue );

    /* pxQueueBuffer was not NULL so xQueue should not be NULL. */
    configASSERT( xQueue );
 }
 

3 uxQueueMessagesWaiting

queue.h
UBaseType_t uxQueueMessagesWaiting( QueueHandle_t xQueue );

返回队列中存储的消息数。

3.1 参数:

xQueue 正在查询的队列的句柄。

3.2 Returns:

队列中可用的消息数。

4-uxQueueMessagesWaitingFromISR

queue.h
UBaseType_t uxQueueMessagesWaitingFromISR( QueueHandle_t xQueue );

可从 ISR 中调用的 uxQueueMessagesWaiting() 的一个版本。 返回 队列中存储的消息数。

4.1参数:

xQueue 正在查询的队列的句柄。

4.2 Returns:

队列中可用的消息数。

5- uxQueueSpacesAvailable

queue.h
UBaseType_t uxQueueSpacesAvailable( QueueHandle_t xQueue );

返回队列中的可用空间数。

5.1 参数:

xQueue 正在查询的队列的句柄。

5.2 Returns:

队列中可用的可用空间数。

6- vQueueDelete

queue.h
void vQueueDelete( QueueHandle_t xQueue );

删除队列 — 释放分配用于存储放置在队列中的项目的所有内存。

6.1参数:

xQueue 要删除的队列的句柄。

7-xQueueReset

queue.h
BaseType_t xQueueReset( QueueHandle_t xQueue );

将队列重置为其原始的空状态。

7.1参数:

xQueue 正在重置的队列的句柄

7.2Returns:

FreeRTOSV7.2.0 xQueueReset() 总是返回 pdPASS。

8-xQueueIsQueueEmptyFromISR

queue.h
BaseType_t xQueueIsQueueEmptyFromISR( const QueueHandle_t xQueue );

查询队列以确定队列是否为空。 此函数只能用于 ISR。

8.1 参数:

xQueue 正在查询的队列的句柄

8.2 Returns:

如果队列不为空,则返回 pdFALSE;如果队列为空,则返回 pdTRUE。

9-xQueueIsQueueFullFromISR

queue.h
BaseType_t xQueueIsQueueFullFromISR( const QueueHandle_t xQueue );

查询队列以确定队列是否已满。 此函数只能用于 ISR。

9.1参数:

xQueue 正在查询的队列的句柄

9.1 Returns:

如果队列未满,则返回 pdFALSE;如果队列已满,则返回 pdTRUE。

10 xQueueSend

queue.h

 BaseType_t xQueueSend(
                            QueueHandle_t xQueue,
                            const void * pvItemToQueue,
                            TickType_t xTicksToWait
                         );

这是一个调用 xQueueGenericSend() 的宏。 它用于 向后兼容 FreeRTOS 的一些版本, 这些版本不包含 xQueueSendToFront() 和 xQueueSendToBack() 宏。 它 等同于 xQueueSendToBack()。

在队列中发布项目。该项目按副本排队,而不是按引用排队。不得从中断服务程序调用此函数。请参阅 xQueueSendFromISR() 以获取 可用于 ISR 的替代方案。

10.1 参数:

xQueue 队列的句柄,数据项将发布到此队列。
pvItemToQueue 指向待入队数据项的指针。创建队列时定义了队列将保留的项的大小,因此固定数量的字节将从 pvItemToQueue 复制到队列存储区域。
xTicksToWait 如果队列已满,则任务应进入阻塞态等待队列上出现可用空间的最大时间。如果队列已满,并且 xTicksToWait 设置为0 ,调用将立即返回。时间在 tick 周期中定义,因此如果需要,应使用常量 portTICK_PERIOD_MS 转换为实时。
如果 INCLUDE_vTaskSuspend 设置为 “1” ,则将阻塞时间指定为 portMAX_DELAY 会导致任务无限期地阻塞(没有超时)。

10.2 Returns:

如果成功发布项目,返回 pdTRUE,否则返回 errQUEUE_FULL。

10.3 用法示例:

struct AMessage
 {
    char ucMessageID;
    char ucData[ 20 ];
 } xMessage;

 unsigned long ulVar = 10UL;

 void vATask( void *pvParameters )
 {
 QueueHandle_t xQueue1, xQueue2;
 struct AMessage *pxMessage;

    /* Create a queue capable of containing 10 unsigned long values. */
    xQueue1 = xQueueCreate( 10, sizeof( unsigned long ) );

    /* Create a queue capable of containing 10 pointers to AMessage structures.
    These should be passed by pointer as they contain a lot of data. */
    xQueue2 = xQueueCreate( 10, sizeof( struct AMessage * ) );


    /* ... */


    if( xQueue1 != 0 )
    {
        /* Send an unsigned long.  Wait for 10 ticks for space to become
        available if necessary. */
        if( xQueueSend( xQueue1,
                       ( void * ) &ulVar,
                       ( TickType_t ) 10 ) != pdPASS )
        {
            /* Failed to post the message, even after 10 ticks. */
        }
    }

    if( xQueue2 != 0 )
    {
        /* Send a pointer to a struct AMessage object.  Don't block if the
        queue is already full. */
        pxMessage = & xMessage;
        xQueueSend( xQueue2, ( void * ) &pxMessage, ( TickType_t ) 0 );
    }

	/* ... Rest of task code. */
 }
 

11-xQueueSendFromISR

queue.h

 BaseType_t xQueueSendFromISR
           (
               QueueHandle_t xQueue,
               const void *pvItemToQueue,
               BaseType_t *pxHigherPriorityTaskWoken
           );

这是用于调用 xQueueGenericSendFromISR() 的宏。 加入此宏可 向后兼容不包括 xQueueSendToBackFromISR() 和 xQueueSendToFrontFromISR() 宏的 FreeRTOS 版本 。

将项目发布到队列尾部。在中断服务程序中使用此函数是安全的。

数据项通过复制而非引用入队,因此最好只将较小的项放入队列, 特别是从 ISR 调用时。在大多数情况下,最好存储一个指向正在排队的数据项的指针。

11.1 参数:

xQueue 队列的句柄,数据项将发布到此队列。
pvItemToQueue 指向待入队数据项的指针。创建队列时定义了队列将保留的项的大小,因此固定数量的字节将从 pvItemToQueue 复制到队列存储区域。
pxHigherPriorityTaskWoken 如果发送到队列导致任务解除阻塞,且解除阻塞的任务的优先级高于当前运行的任务,则xQueueSendFromISR() 会将 *pxHigherPriorityTaskWoken 设置为 pdTRUE。 如果 xQueueSendFromISR() 将此值设置为 pdTRUE,则应在中断退出前请求上下文切换。
从 FreeRTOS V7.3.0 开始,pxHigherPriorityTaskWoken 是一个可选参数,可设置为 NULL。

11.2 Returns:

如果将数据成功发送至队列,则返回 pdTRUE,否则返回 errQUEUE_FULL。
缓冲 IO(每次调用 ISR 可以获取多个值)的用法示例:

void vBufferISR( void )
{
char cIn;
BaseType_t xHigherPriorityTaskWoken;

    /* We have not woken a task at the start of the ISR. */
    xHigherPriorityTaskWoken = pdFALSE;

    /* Loop until the buffer is empty. */
    do
    {
        /* Obtain a byte from the buffer. */
        cIn = portINPUT_BYTE( RX_REGISTER_ADDRESS );

        /* Post the byte. */
        xQueueSendFromISR( xRxQueue, &cIn, &xHigherPriorityTaskWoken );

    } while( portINPUT_BYTE( BUFFER_COUNT ) );

    /* Now the buffer is empty we can switch context if necessary. */
    if( xHigherPriorityTaskWoken )
    {
        /* Actual macro used here is port specific. */
        taskYIELD_FROM_ISR ();
    }
}

12- xQueueSendToBack

queue.h

 BaseType_t xQueueSendToBack(
                                   QueueHandle_t xQueue,
                                   const void * pvItemToQueue,
                                   TickType_t xTicksToWait
                               );

这是一个调用 xQueueGenericSend() 的宏。 它等同于 xQueueSend()。

从队列尾部入队一个数据项。 数据项通过复制 而非引用入队。 不得从中断服务程序 。 请参阅 xQueueSendToBackFromISR (),获取可在 ISR 中使用的 替代方案。

12.1 参数:

xQueue 队列的句柄,数据项将发布到此队列。
pvItemToQueue 指向待入队数据项的指针。创建队列时定义了队列将保留的项的大小,因此固定数量的字节将从 pvItemToQueue 复制到队列存储区域。
xTicksToWait 如果队列已满,则任务应进入阻塞态等待队列上出现可用空间的最大时间。如果设置为 0,调用将立即返回。时间以滴答周期为单位定义,因此如果需要,应使用常量 portTICK_PERIOD_MS 转换为实时。
如果 INCLUDE_vTaskSuspend设置为 “1”,则将阻塞时间指定为 portMAX_DELAY 会导致任务无限期地阻塞(没有超时)。

12.2Returns:

如果成功发布项目,返回 pdTRUE,否则返回 errQUEUE_FULL。

12.3用法示例:

struct AMessage
{
    char ucMessageID;
    char ucData[ 20 ];
} xMessage;

unsigned long ulVar = 10UL;

void vATask( void *pvParameters )
{
QueueHandle_t xQueue1, xQueue2;
struct AMessage *pxMessage;

    /* Create a queue capable of containing 10 unsigned long values. */
    xQueue1 = xQueueCreate( 10, sizeof( unsigned long ) );

    /* Create a queue capable of containing 10 pointers to AMessage
    structures.  These should be passed by pointer as they contain a lot of
    data. */
    xQueue2 = xQueueCreate( 10, sizeof( struct AMessage * ) );

    /* ... */

    if( xQueue1 != 0 )
    {
        /* Send an unsigned long.  Wait for 10 ticks for space to become
        available if necessary. */
        if( xQueueSendToBack( xQueue1,
                             ( void * ) &ulVar,
                             ( TickType_t ) 10 ) != pdPASS )
        {
            /* Failed to post the message, even after 10 ticks. */
        }
    }

    if( xQueue2 != 0 )
    {
        /* Send a pointer to a struct AMessage object.  Don't block if the
        queue is already full. */
        pxMessage = & xMessage;
        xQueueSendToBack( xQueue2, ( void * ) &pxMessage, ( TickType_t ) 0 );
    }

	/* ... Rest of task code. */
}

13-xQueueSendToBackFromISR

queue.h

 BaseType_t xQueueSendToBackFromISR
                    (
                        QueueHandle_t xQueue,
                        const void *pvItemToQueue,
                        BaseType_t *pxHigherPriorityTaskWoken
                    );

此宏用于调用 xQueueGenericSendFromISR()。

从队列尾部入队一个数据项。可在中断服务程序中使用此函数。

数据项通过复制而非引用入队,因此最好只发送较小的项,尤其是从 ISR 调用时。

13.1 参数:

xQueue 队列的句柄,数据项将发布到此队列。
pvItemToQueue 指向待入队数据项的指针。创建队列时定义了队列将保留的项的大小,因此固定数量的字节将从 pvItemToQueue 复制到队列存储区域。
pxHigherPriorityTaskWoken 如果发送到队列导致某个任务解除阻塞,并且解除阻塞的任务的优先级高于当前运行的任务,则 xQueueSendTobackFromISR() 会将 *pxHigherPriorityTaskWoken 设置为 pdTRUE。 如果 xQueueSendTobackFromISR() 将此值设置为 pdTRUE,则应在退出中断之前请求上下文切换。
从 FreeRTOSV7.3.0 开始,pxHigherPriorityTaskWoken 是一个可选参数,可设置为 NULL。

13.2 Returns:

若成功发送至队列,则返回 pdPASS,否则返回 errQUEUE_FULL。

13.3 用法示例:

void vBufferISR( void )
{
char cIn;
BaseType_t xHigherPriorityTaskWoken;

    /* We have not woken a task at the start of the ISR. */
    xHigherPriorityTaskWoken = pdFALSE;

    /* Loop until the buffer is empty. */
    do
    {
        /* Obtain a byte from the buffer. */
        cIn = portINPUT_BYTE( RX_REGISTER_ADDRESS );

        /* Post the byte. */
        xQueueSendToBackFromISR( xRxQueue, &cIn, &xHigherPriorityTaskWoken );

    } while( portINPUT_BYTE( BUFFER_COUNT ) );

    /* Now the buffer is empty we can switch context if necessary. */
    if( xHigherPriorityTaskWoken )
    {
        /* Actual macro used here is port specific. */
        taskYIELD_FROM_ISR ();
    }
}

14 xQueueSendToFront

queue.h

 BaseType_t xQueueSendToFront( QueueHandle_t xQueue,
                               const void * pvItemToQueue,
                               TickType_t xTicksToWait );

此宏用于调用 xQueueGenericSend()。

从队列头部入队一个数据项。 数据项通过复制 而非引用入队。 不得从中断服务程序 调用此函数。 请参阅 xQueueSendToFrontFromISR() 了解 可在 ISR 中使用的替代方法。

14.1参数:

xQueue 队列的句柄,数据项将发布到此队列。
pvItemToQueue 指向待入队数据项的指针。创建队列时定义了队列将保留的项的大小,因此固定数量的字节将从 pvItemToQueue 复制到队列存储区域。
xTicksToWait 如果队列已满,则任务应进入阻塞态等待队列上出现可用空间的最大时间。如果设置为 0,调用将立即返回。时间以滴答周期为单位定义,因此如果需要,应使用常量 portTICK_PERIOD_MS 转换为实时。
如果 INCLUDE_vTaskSuspend设置为 “1”,则将阻塞时间指定为 portMAX_DELAY 会导致任务无限期地阻塞(没有超时)。

14.2 Returns:

如果成功发布项目,返回 pdTRUE,否则返回 errQUEUE_FULL。

14.3 用法示例:

struct AMessage
{
    char ucMessageID;
    char ucData[ 20 ];
} xMessage;

unsigned long ulVar = 10UL;

void vATask( void *pvParameters )
{
QueueHandle_t xQueue1, xQueue2;
struct AMessage *pxMessage;

    /* Create a queue capable of containing 10 unsigned long values. */
    xQueue1 = xQueueCreate( 10, sizeof( unsigned long ) );

    /* Create a queue capable of containing 10 pointers to AMessage
    structures.  These should be passed by pointer as they contain a lot of
    data. */
    xQueue2 = xQueueCreate( 10, sizeof( struct AMessage * ) );

    /* ... */

    if( xQueue1 != 0 )
    {
        /* Send an unsigned long.  Wait for 10 ticks for space to become
        available if necessary. */
        if( xQueueSendToFront( xQueue1,
                              ( void * ) &ulVar,
                              ( TickType_t ) 10 ) != pdPASS )
        {
            /* Failed to post the message, even after 10 ticks. */
        }
    }

    if( xQueue2 != 0 )
    {
        /* Send a pointer to a struct AMessage object.  Don't block if the
        queue is already full. */
        pxMessage = & xMessage;
        xQueueSendToFront( xQueue2, ( void * ) &pxMessage, ( TickType_t ) 0 );
    }

	/* ... Rest of task code. */

15-xQueueSendToFrontFromISR

queue.h

 BaseType_t xQueueSendToFrontFromISR
                 (
                     QueueHandle_t xQueue,
                     const void *pvItemToQueue,
                     BaseType_t *pxHigherPriorityTaskWoken
                 );

这是用于调用 xQueueGenericSendFromISR() 的宏。

从队列头部入队一个数据项。可在中断服务程序中使用此函数。

数据项通过复制而非引用入队,因此最好只发送较小的项,或者发送指向该项的指针。

15.1 参数:

xQueue 队列的句柄,数据项将发布到此队列。
pvItemToQueue 指向待入队数据项的指针。创建队列时定义了队列将保留的项的大小,因此固定数量的字节将从 pvItemToQueue 复制到队列存储区域。
pxHigherPriorityTaskWoken 如果发送到队列导致某个任务解除阻塞,且被解除阻塞的任务的优先级高于当前运行的任务,则 xQueueSendToFrontFromISR() 会将 *pxHigherPriorityTaskWoken 设置为 pdTRUE。 如果 xQueueSendToFrontFromISR() 将此值设置为 pdTRUE,则应在中断退出前请求上下文切换。
从 FreeRTOS V7.3.0 开始,pxHigherPriorityTaskWoken 是一个可选参数,可设置为 NULL。

15.2 Returns:

若数据成功发送至队列,则返回 pdPass,否则返回 errQUEUE_FULL。

15.3 用法示例:

void vBufferISR( void )
{
char cIn;
BaseType_t xHigherPriorityTaskWoken;

    /* We have not woken a task at the start of the ISR. */
    xHigherPriorityTaskWoken = pdFALSE;

    /* Obtain a byte from the buffer. */
    cIn = portINPUT_BYTE( RX_REGISTER_ADDRESS );

    if( cIn == EMERGENCY_MESSAGE )
    {
        /* Post the byte to the front of the queue. */
        xQueueSendToFrontFromISR( xRxQueue, &cIn, &xHigherPriorityTaskWoken );
    }
    else
    {
        /* Post the byte to the back of the queue. */
        xQueueSendToBackFromISR( xRxQueue, &cIn, &xHigherPriorityTaskWoken );
    }

    /* Did sending to the queue unblock a higher priority task? */
    if( xHigherPriorityTaskWoken )
    {
        /* Actual macro used here is port specific. */
        taskYIELD_FROM_ISR ();
    }
}

16-xQueueReceive

queue. h

 BaseType_t xQueueReceive(
                               QueueHandle_t xQueue,
                               void *pvBuffer,
                               TickType_t xTicksToWait
                            );

这是一个调用xQueueGenericReceive()函数的宏。

从队列中接收一个项目。该项目是通过复制接收的,因此必须提供足够大小的缓冲区。复制到缓冲区的字节数是在创建队列时定义的。

此函数不能在中断服务例程中使用。

16.1 参数:

xQueue 要从其中接收项的队列句柄。
pvBuffer 指向接收项将被复制到的缓冲区的指针。
xTicksToWait 如果在调用时队列为空,则任务应该阻塞等待项接收的最大时间。将xTicksToWait设置为0将导致该函数在队列为空时立即返回。时间是以tick周期定义的,因此如果需要,应该使用常量portTICK_PERIOD_MS来转换为实时时间。

如果INCLUDE_vTaskSuspend设置为’1’,那么指定块时间为portMAX_DELAY将导致任务无限期地阻塞(没有超时)。

16.2 Returns:

如果成功从队列接收到项,则返回pdTRUE,否则返回pdFALSE。

16.3 用例:

/* Define a variable of type struct AMMessage.  The examples below demonstrate
how to pass the whole variable through the queue, and as the structure is
moderately large, also how to pass a reference to the variable through a queue. */
struct AMessage
{
   char ucMessageID;
   char ucData[ 20 ];
} xMessage;

/* Queue used to send and receive complete struct AMessage structures. */
QueueHandle_t xStructQueue = NULL;

/* Queue used to send and receive pointers to struct AMessage structures. */
QueueHandle_t xPointerQueue = NULL;


void vCreateQueues( void )
{
   xMessage.ucMessageID = 0xab;
   memset( &( xMessage.ucData ), 0x12, 20 );

   /* Create the queue used to send complete struct AMessage structures.  This can
   also be created after the schedule starts, but care must be task to ensure
   nothing uses the queue until after it has been created. */
   xStructQueue = xQueueCreate(
                         /* The number of items the queue can hold. */
                         10,
                         /* Size of each item is big enough to hold the
                         whole structure. */
                         sizeof( xMessage ) );

   /* Create the queue used to send pointers to struct AMessage structures. */
   xPointerQueue = xQueueCreate(
                         /* The number of items the queue can hold. */
                         10,
                         /* Size of each item is big enough to hold only a
                         pointer. */
                         sizeof( &xMessage ) );

   if( ( xStructQueue == NULL ) || ( xPointerQueue == NULL ) )
   {
      /* One or more queues were not created successfully as there was not enough
      heap memory available.  Handle the error here.  Queues can also be created
      statically. */
   }
}

/* Task that writes to the queues. */
void vATask( void *pvParameters )
{
struct AMessage *pxPointerToxMessage;

   /* Send the entire structure to the queue created to hold 10 structures. */
   xQueueSend( /* The handle of the queue. */
               xStructQueue,
               /* The address of the xMessage variable.  sizeof( struct AMessage )
               bytes are copied from here into the queue. */
               ( void * ) &xMessage,
               /* Block time of 0 says don't block if the queue is already full.
               Check the value returned by xQueueSend() to know if the message
               was sent to the queue successfully. */
               ( TickType_t ) 0 );

   /* Store the address of the xMessage variable in a pointer variable. */
   pxPointerToxMessage = &xMessage

   /* Send the address of xMessage to the queue created to hold 10    pointers. */
   xQueueSend( /* The handle of the queue. */
               xPointerQueue,
               /* The address of the variable that holds the address of xMessage.
               sizeof( &xMessage ) bytes are copied from here into the queue. As the
               variable holds the address of xMessage it is the address of xMessage
               that is copied into the queue. */
               ( void * ) &pxPointerToxMessage,
               ( TickType_t ) 0 );

   /* ... Rest of task code goes here. */
}

/* Task that reads from the queues. */
void vADifferentTask( void *pvParameters )
{
struct AMessage xRxedStructure, *pxRxedPointer;

   if( xStructQueue != NULL )
   {
      /* Receive a message from the created queue to hold complex struct AMessage
      structure.  Block for 10 ticks if a message is not immediately available.
      The value is read into a struct AMessage variable, so after calling
      xQueueReceive() xRxedStructure will hold a copy of xMessage. */
      if( xQueueReceive( xStructQueue,
                         &( xRxedStructure ),
                         ( TickType_t ) 10 ) == pdPASS )
      {
         /* xRxedStructure now contains a copy of xMessage. */
      }
   }

   if( xPointerQueue != NULL )
   {
      /* Receive a message from the created queue to hold pointers.  Block for 10
      ticks if a message is not immediately available.  The value is read into a
      pointer variable, and as the value received is the address of the xMessage
      variable, after this call pxRxedPointer will point to xMessage. */
      if( xQueueReceive( xPointerQueue,
                         &( pxRxedPointer ),
                         ( TickType_t ) 10 ) == pdPASS )
      {
         /* *pxRxedPointer now points to xMessage. */
      }
   }

   /* ... Rest of task code goes here. */
}

17 xQueueReceiveFromISR

queue. h

 BaseType_t xQueueReceiveFromISR
                (
                    QueueHandle_t xQueue,
                    void *pvBuffer,
                    BaseType_t *pxHigherPriorityTaskWoken
                );

从队列中接收项目。从中断服务程序内使用此函数是安全的。

17.1参数:

xQueue 要从中接收项目的队列的句柄。
pvBuffer 指向缓冲区的指针,接收到的项目将被复制到这个缓冲区。
pxHigherPriorityTaskWoken 任务可被阻塞,以等待队列可用空间。如果 xQueueReceiveFromISR 使得此类任务阻塞解除,*pxHigherPriorityTaskWoken 将设置为 pdTRUE,否则 *pxHigherPriorityTaskWoken 将保持不变。
从 FreeRTOSV7.3.0 开始,pxHigherPriorityTaskWoken 是一个可选参数,可设置为 NULL。

17.2 Returns:

如果从队列成功接收到项目,返回 pdTRUE,否则返回 pdFALSE。

17.3 示例用法:

QueueHandle_t xQueue;

/* Function to create a queue and post some values. */
void vAFunction( void *pvParameters )
{
char cValueToPost;
const TickType_t xTicksToWait = ( TickType_t )0xff;

    /* Create a queue capable of containing 10 characters. */
    xQueue = xQueueCreate( 10, sizeof( char ) );
    if( xQueue == 0 )
    {
        /* Failed to create the queue. */
    }

    /* ... */

    /* Post some characters that will be used within an ISR.  If the queue
    is full then this task will block for xTicksToWait ticks. */
    cValueToPost = 'a';
    xQueueSend( xQueue, ( void * ) &cValueToPost, xTicksToWait );
    cValueToPost = 'b';
    xQueueSend( xQueue, ( void * ) &cValueToPost, xTicksToWait );

    /* ... keep posting characters ... this task may block when the queue
    becomes full. */

    cValueToPost = 'c';
    xQueueSend( xQueue, ( void * ) &cValueToPost, xTicksToWait );
}

/* ISR that outputs all the characters received on the queue. */
void vISR_Routine( void )
{
BaseType_t xTaskWokenByReceive = pdFALSE;
char cRxedChar;

    while( xQueueReceiveFromISR( xQueue,
                                ( void * ) &cRxedChar,
                                &xTaskWokenByReceive) )
    {
        /* A character was received.  Output the character now. */
        vOutputCharacter( cRxedChar );

        /* If removing the character from the queue woke the task that was
        posting onto the queue xTaskWokenByReceive will have been set to
        pdTRUE.  No matter how many times this loop iterates only one
        task will be woken. */
    }

    if( xTaskWokenByReceive != pdFALSE )
    {
        /* We should switch context so the ISR returns to a different task.
        NOTE:  How this is done depends on the port you are using.  Check
        the documentation and examples for your port. */
        taskYIELD ();
    }
}

18 xQueueOverwrite

queue.h

 BaseType_t xQueueOverwrite(
                                 QueueHandle_t xQueue,
                                 const void * pvItemToQueue
                              );
 

这是用于调用 xQueueGenericSend() 函数的宏。

即使队列已满的情况下也将写入队列的 xQueueSendToBack() 版本, 同时覆盖队列中已经 存在的数据。

xQueueOverwrite() 旨在用于长度为 1 的队列, 这意味着队列要么为空,要么为满。

不得从中断服务程序 (ISR) 调用此函数。 请参阅 xQueueOverwriteFromISR(),了解可在 ISR 中使用的替代函数。

18.1参数:

xQueue 接收发送数据的队列的句柄。
pvItemToQueue 指向待入队数据项的指针。队列 队列可容纳的项数在 创建队列时定义,这些项 将从 pvItemToQueue 复制到队列存储区域。

18.2 Returns:

xQueueOverwrite() 是用于调用 xQueueGenericSend() 的宏, 因此与 xQueueSendToFront() 具有相同的返回值。 不过,由于 xQueueOverwrite() 将写入队列(即使队列已满), pdPASS 是唯一可以返回的值。

18.3 用法示例:

 void vFunction( void *pvParameters )
 {
 QueueHandle_t xQueue;
 unsigned long ulVarToSend, ulValReceived;

    /* Create a queue to hold one unsigned long value.  It is strongly
    recommended *not* to use xQueueOverwrite() on queues that can
    contain more than one value, and doing so will trigger an assertion
    if configASSERT() is defined. */
    xQueue = xQueueCreate( 1, sizeof( unsigned long ) );

    /* Write the value 10 to the queue using xQueueOverwrite(). */
    ulVarToSend = 10;
    xQueueOverwrite( xQueue, &ulVarToSend );

    /* Peeking the queue should now return 10, but leave the value 10 in
    the queue.  A block time of zero is used as it is known that the
    queue holds a value. */
    ulValReceived = 0;
    xQueuePeek( xQueue, &ulValReceived, 0 );

    if( ulValReceived != 10 )
    {
        /* Error, unless another task removed the value. */
    }

    /* The queue is still full.  Use xQueueOverwrite() to overwrite the
    value held in the queue with 100. */
    ulVarToSend = 100;
    xQueueOverwrite( xQueue, &ulVarToSend );

    /* This time read from the queue, leaving the queue empty once more.
    A block time of 0 is used again. */
    xQueueReceive( xQueue, &ulValReceived, 0 );

    /* The value read should be the last value written, even though the
    queue was already full when the value was written. */
    if( ulValReceived != 100 )
    {
        /* Error unless another task is using the same queue. */
    }

    /* ... */
}

19 xQueueOverwriteFromISR

queue.h

 BaseType_t xQueueOverwrite
                   (
                      QueueHandle_t xQueue,
                      const void * pvItemToQueue
                      BaseType_t *pxHigherPriorityTaskWoken
                    );

这是用于调用 xQueueGenericSendFromISR() 函数的宏。

可以用于 ISR 的 xQueueOverwrite() 版本 。 xQueueOverwriteFromISR() 与 xQueueSendToBackFromISR() 相似, 但即使队列已满,前者也会写入队列,覆盖队列中已经 存在的数据。

xQueueOverwriteFromISR() 旨在用于长度为 1 的队列, 这意味着队列要么为空,要么为满。

19.1参数:

xQueue 接收发送数据的队列的句柄。
pvItemToQueue 指向待入队数据项的指针。队列 队列可容纳的项数在 创建队列时定义,这些项 将从 pvItemToQueue 复制到队列存储区域。
pxHigherPriorityTaskWoken 如果发送通知到队列导致某个任务解除阻塞, 且被解除阻塞的任务的优先级高于当前运行的任务, 则 xQueueOverwriteFromISR() 将把 *pxHigherPriorityTaskWoken 设置 为 pdTRUE。 如果 xQueueOverwriteFromISR() 将此值设置为 pdTRUE, 则应在中断退出之前请求上下文切换 。

19.2Returns:

xQueueOverwriteFromISR() 是调用 xQueueGenericSendFromISR() 的宏, 因此与 xQueueSendToFrontFromISR() 具有 相同的返回值。 不过,由于 xQueueOverwriteFromISR() 将写入队列(即使队列已满), pdPASS 是唯一可以返回的值。

19.3 用法示例:

QueueHandle_t xQueue;

void vFunction( void *pvParameters )
{
    /* Create a queue to hold one unsigned long value.  It is strongly
    recommended not to use xQueueOverwriteFromISR() on queues that can
    contain more than one value, and doing so will trigger an assertion
    if configASSERT() is defined. */
    xQueue = xQueueCreate( 1, sizeof( unsigned long ) );
}

void vAnInterruptHandler( void )
{
/* xHigherPriorityTaskWoken must be set to pdFALSE before it is used. */
BaseType_t xHigherPriorityTaskWoken = pdFALSE;
unsigned long ulVarToSend, ulValReceived;

    /* Write the value 10 to the queue using xQueueOverwriteFromISR(). */
    ulVarToSend = 10;
    xQueueOverwriteFromISR( xQueue, &ulVarToSend, &xHigherPriorityTaskWoken );

    /* The queue is full, but calling xQueueOverwriteFromISR() again will still
    pass because the value held in the queue will be overwritten with the
    new value. */
    ulVarToSend = 100;
    xQueueOverwriteFromISR( xQueue, &ulVarToSend, &xHigherPriorityTaskWoken );

    /* Reading from the queue will now return 100. */

    /* ... */

    if( xHigherPrioritytaskWoken == pdTRUE )
    {
        /* Writing to the queue caused a task to unblock and the unblocked task
        has a priority higher than or equal to the priority of the currently
        executing task (the task this interrupt interrupted).  Perform a
        context switch so this interrupt returns directly to the unblocked
        task. */
        portYIELD_FROM_ISR(); /* or portEND_SWITCHING_ISR() depending on the
        port.*/
    }
}

20-xQueuePeek

queue.h

 BaseType_t xQueuePeek(
                             QueueHandle_t xQueue,
                             void *pvBuffer,
                             TickType_t xTicksToWait
                         );

这是一个调用 xQueueGenericReceive() 函数的宏。

从队列中接收项目,而无须从队列中删除该项目。 项目由副本接收,因此必须提供适当大小的缓冲区 。 队列创建时,复制到缓冲区中的字节数已定义 。

成功接收的项目仍在队列中,因此将由下一次调用再次返回 或 xQueueReceive () 调用。

中断服务例程中不得使用此宏。

20.1 参数:

xQueue 要从中接收项目的队列的句柄。
pvBuffer 指针,指向将复制收到的项目的缓冲区。 它必须至少足够大,才能容纳创建队列时定义的队列项的大小。
xTicksToWait 如果在调用时队列为空,则任务应阻塞等待项目接收的最长时间。 时间已在滴答周期中定义,因此如果需要,应使用常量 portTICK_PERIOD_MS 来将其转换为实时。
如果 INCLUDE_vTaskSuspend设置为 “1”,则将阻塞时间指定为 portMAX_DELAY 会导致任务无限期地阻塞(没有超时)。

20.2 Returns:

如果从队列中成功接收(窥视)项目,则返回 pdTRUE,否则返回 pdFALSE。

20.3 用法示例:

 struct AMessage
 {
    char ucMessageID;
    char ucData[ 20 ];
 } xMessage;

 QueueHandle_t xQueue;

 // Task to create a queue and post a value.
 void vATask( void *pvParameters )
 {
 struct AMessage *pxMessage;

    // Create a queue capable of containing 10 pointers to AMessage structures.
    // These should be passed by pointer as they contain a lot of data.
    xQueue = xQueueCreate( 10, sizeof( struct AMessage * ) );
    if( xQueue == 0 )
    {
        // Failed to create the queue.
    }

    // ...

    // Send a pointer to a struct AMessage object.  Don't block if the
    // queue is already full.
    pxMessage = & xMessage;
    xQueueSend( xQueue, ( void * ) &pxMessage, ( TickType_t ) 0 );

    // ... Rest of task code.
 }

 // Task to peek the data from the queue.
 void vADifferentTask( void *pvParameters )
 {
 struct AMessage *pxRxedMessage;

    if( xQueue != 0 )
    {
        // Peek a message on the created queue.  Block for 10 ticks if a
        // message is not immediately available.
        if( xQueuePeek( xQueue, &( pxRxedMessage ), ( TickType_t ) 10 ) )
        {
            // pcRxedMessage now points to the struct AMessage variable posted
            // by vATask, but the item still remains on the queue.
        }
    }

    // ... Rest of task code.
 }

21 xQueuePeekFromISR

queue.h
 BaseType_t xQueuePeekFromISR(
                                 QueueHandle_t xQueue,
                                 void *pvBuffer,
                                );

xQueuePeek() 的版本,可以从 中断服务程序 (ISR) 内部分配。

从队列中接收项目,而无须从队列中删除该项目。 项目由副本接收,因此必须提供适当大小的缓冲区 。 队列创建时,复制到缓冲区中的字节数已定义 。

成功接收的项目仍在队列中,因此将由下个调用再次返回 或由任何队列接收函数调用的返回。

21.1参数:

xQueue 要从中接收项目的队列的句柄。
pvBuffer 指向复制接收项目缓冲区的指针 。 这必须至少足够大,以容纳队列创建时定义队列项的大小 。

21.2 Returns:

如果从队列中成功接收(窥视)项目,则返回 pdTRUE, 否则返回 pdFALSE。

22 vQueueAddToRegistry

queue.h

 void vQueueAddToRegistry(
                             QueueHandle_t xQueue,
                             char *pcQueueName,
                         );

为队列指定名称,并将队列添加到注册表。

22.1 参数:

xQueue 添加到注册表的队列句柄。
pcQueueName 指定的队列名称。 此为文本字符串,仅为便于调试之用。队列注册表仅存储指向该字符串的指针,因此该字符串必须具有持久性(全局变量,或最好是在 ROM/Flash 中),而不是在堆栈上定义。
队列注册表有两项用途,都与 RTOS 内核感知调试相关:
可以关联文本名称和队列,便于在调试 GUI 中识别队列。
包含调试器定位每个已注册队列和信号量所需的信息。
除非使用 RTOS 内核感知调试器,否则队列注册表没有任何用途。
configQUEUE_REGISTRY_SIZE 定义了可以注册的队列和信号量的最大数量。 仅需注册那些要使用 RTOS 内核感知调试器查看的队列和信号量。

22.1 示例:

void vAFunction( void )
{
QueueHandle_t xQueue;

    /* Create a queue big enough to hold 10 chars. */
    xQueue = xQueueCreate( 10, sizeof( char ) );

    /* We want this queue to be viewable in a RTOS kernel aware debugger,
    so register it. */
    vQueueAddToRegistry( xQueue, "AMeaningfulName" );
}

23 vQueueUnregisterQueue

queue.h

 void vQueueUnregisterQueue( 
                             QueueHandle_t xQueue, 
                           );

从队列注册表中删除队列。

23.1参数:

xQueue 从注册表中删除的队列句柄。
队列注册表有两个目的,都与 RTOS 内核感知调试相关:
可以关联文本名称和队列,便于在调试 GUI 中识别队列。
包含调试器定位每个已注册队列和信号量所需的信息。
除非使用 RTOS 内核感知调试器,否则队列注册表没有任何用途。
configQUEUE_REGISTRY_SIZE 定义了可以注册的队列和信号量的最大数量。 仅需注册那些要使用 RTOS 内核感知调试器查看的队列和信号量。

23.2 示例:

void vAFunction( void )
{
QueueHandle_t xQueue;

    /* Create a queue big enough to hold 10 chars. */
    xQueue = xQueueCreate( 10, sizeof( char ) );

    /* We want this queue to be viewable in a RTOS kernel aware debugger, 
    so register it. */
    vQueueAddToRegistry( xQueue, "AMeaningfulName" );


    /* The queue gets used here. */


    /* At some later time, the queue is going to be deleted, first 
    remove it from the registry. */
    vQueueUnregisterQueue( xQueue );
    vQueueDelete( xQueue );
}
 

24 pcQueueGetName

queue.h
const char *pcQueueGetName( QueueHandle_t xQueue )

从队列的句柄中查找队列名称。

队列只有添加到队列注册表时才有名称。

24.1参数:

xQueue 正在查询的队列的句柄。

24.2 返回:

如果 xQueue 引用的队列在队列注册表中, 则返回队列的文本名称,否则返回 NULL。

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

南山府嵌入式

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值