20-FreeRTOS队列API函数

news2024/11/30 0:42:36

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。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/152499.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

ShardingSphere分库分表schema名称导致NPE问题排查记录

前段时间把 ShardingSphere 升级到了 5.1.1 版本,奈何官方版本升级太快跟不上速度,这不最近又发现了一个 BUG。 问题现象 数据库做了分库分表,在需要查询多表数据进行 merge 的时候发生了一个 NPE 的异常。 Caused by: java.lang.NullPoin…

【数据结构】前缀树/字典树

目录1.概述2.代码实现3.应用本文参考: LeetCode 208.实现 Trie (前缀树) 1.概述 前缀树又称字典树、Trie 树、单词查找树,是一棵有根树,同时也是一种哈希树的变种,其每个节点包含以下字段: 指向子节点的指针数组 chi…

pytorch 分布式调试debug torch.distributed.launch

文章目录一. pytorch 分布式调试debug torch.distributed.launch 三种方式1. 方式1:ipdb调试(建议)命令行使用pdb未解决:2. 方式2:使用pycharm进行分布式调试(侵入式代码)3. 方式3:使…

HRNet源码阅读笔记(5),庞大的PoseHighResolutionNet模块-transition1

在stage1的最后,分支了。就是所谓的transition1,详见下面的第13行。def forward(self, x):x self.conv1(x)x self.bn1(x)x self.relu(x)x self.conv2(x)x self.bn2(x)x self.relu(x)x self.layer1(x)x_list []for i in range(self.stage2_cfg[NU…

【前端之旅】Webpack模块打包工具

一名软件工程专业学生的前端之旅,记录自己对三件套(HTML、CSS、JavaScript)、Jquery、Ajax、Axios、Bootstrap、Node.js、Vue、小程序开发(Uniapp)以及各种UI组件库、前端框架的学习。 【前端之旅】Web基础与开发工具 【前端之旅】手把手教你安装VS Code并附上超实用插件…

【图的存储】

更好的阅读体验\color{red}{更好的阅读体验}更好的阅读体验 文章目录1. 邻接矩阵2. 边集数组3. 邻接表4. 链式邻接表5. 链式前向星总结1. 邻接矩阵 思想: 利用二维数组 g[N][N] 存储所有的点到点的权值。其中 N 为点的数量,g[i][j] 表示点 i 到点 j 的权…

【C++】容器适配器

文章目录一. 什么是适配器?什么是容器适配器?二.理解容器适配器stack的模拟实现queue的模拟实现一. 什么是适配器?什么是容器适配器? 适配器是一种设计模式(设计模式是一套被反复使用的,多数人知晓的,经过分类编目的,代码设计…

CAD未协调的新图层怎么处理?

在打开CAD图纸时,系统提示图形存在为协调的新图层是什么意思?所谓未协调图层,是指上次打印或者保存之类命令后新增的图层,大部分情况下增加新的外部参照时会把所有外部参照中的图层标记为未协调图层。CAD未协调的新图层怎么处理&a…

2023年底,我要通过这5点,实现博客访问量500W

说实话,这真的是一个非常高远的flag,因为我目前只有35W,但根据我2个月前还是12W的访问量,我觉得我还是可以拼一把的,在这里我想向大家分享一下我的计划,如何达成2023年底,博客访问量达到500W的K…

期刊会议排名、信息检索网站推荐、IEEE Latex模板下载(更新中...)

一.拿到一个期刊或论文,不知道他的影响因子、分区类型等等信息,可以使用以下几个网站搜索一下。二.一些会议期刊搜索1.国外The Latest Information Technology Conference and Journal List - Conference Partner(信息技术最新国际会议和期刊…

Java程序员必知四种负载均衡算法

前言 一般来说,我们在设计系统的时候,为了系统的高扩展性,会尽可能的创建无状态的系统,这样我们就可以采用集群的方式部署,最终很方便的根据需要动态增减服务器数量。但是,要使系统具有更好的可扩展性&…

直观理解--马氏距离

首先我们很了解欧氏距离了,就是用来计算欧式空间(就是我们常见的坐标系)中两个点的距离的。 比如点 x(x1,…,xn)x (x_1,…,x_n)x(x1​,…,xn​) 和 y(y1,…,yn)y (y_1,…,y_n)y(y1​,…,yn​) 的欧氏距离为: d(x,y)(x1−y1)2(x2…

依靠小游戏带动产品增收,app运营这样做

大家都玩过小游戏吧?从小时候的4399游戏平台到现在的微信小游戏,尤其是风靡一时的“跳一跳”和“羊了个羊”都曾上榜热搜,让人印象深刻。在当下小游戏爆火社交平台的不断出现的背景下,小游戏的发展劲头更是强盛。 小游戏的吸引力在…

Memblaze发布大容量企业级SSD:支持32T最大容量,性能更强!

2023年1月10日 —— 今天,北京忆恒创源科技股份有限公司(Memblaze)正式发布 PBlaze6 6930 系列 PCIe 4.0 企业级 NVMe SSD。PBlaze6 6930 面向企业高性能业务应用开发,有着 1600K/680K IOPS 的 4K 随机读/写性能,具备更…

Mysql常见面试题

Mysql常见面试题汇总①⭐事务的基本特性和隔离级别⭐ACID靠什么保证⭐什么是MVCC⭐mysql的主从同步原理简述MyISAM和InnoDB的区别简述mysql中索引类型以及对数据库的性能影响⭐索引的基本原理Mysql聚簇索引和非聚簇索引的区别⭐B树和B树的区别,为什么Mysql使用B树My…

第04讲:Docker部署MySQL8

MySQL 的 Docker 镜像在 dockerhub 上的地址:https://hub.docker.com//mysql 当前(2021-04-02)的 latest 和 8.0.23 是同一个镜像 。另外,5.7 版本和 5.7.33 是同一个镜像 第1步:安装mysql 查询中央仓库 docker se…

Kestrel封装在WindowService中(.net5,.net6,.net7三个版本的介绍)

Kestrel封装在WindowServer中背景关于WindowsServer开发服务.NET5版本建项目添加Controller添加引用修改Startup.cs修改Program.cs配置Kestrel监听发布程序通过命令行创建服务关于SC命令启动服务查看效果测试效果.NET6错误1解决办法:错误2运行效果如下图.NET7版本&a…

千锋教育嵌入式物联网教程之系统编程篇学习-01

目录 课程视频链接 笔记目的 什么是系统编程 如何操作内核的系统调用 系统调用的分类​编辑 系统调用的返回值 系统调用IO函数 文件描述符 文件IO文件描述符与标准IO的文件指针对应关系 Man手册使用 open函数 函数调用失败打印错误 close函数 测试一个进程最多能产生多少个…

如何准备pmp考试?

一、考前五准备 1.知识准备:读透教材,仔细回顾知识点,明确知识框架,模考题考前正确率达到95%。 2.精神准备:明确目标,有信心,不要焦虑。 3.精力准备:科学安排考前的复习和休息时间…

【nvivo11plus教程】03_查询+自动编码

注:nvivo11也可以使用自动编码的。我是在第一次使用自动编码的时候,它弹出来一个界面让我下载安装包,但是网速特别慢,需要5、6个小时,然后我电脑开了一个晚上,第二天早上显示下载失败,但是可以使…