自学内容网 自学内容网

rk2118--RT-Thread 消息队列

1、概述

什么是 RT-Thread 消息队列
RT-Thread 消息队列是一种用于在任务或中断服务例程(ISR)之间传递消息的机制。它允许一个任务或ISR发送数据到消息队列中,而另一个任务可以从消息队列中接收这些数据。消息队列提供了一种异步通信的方式,使得任务之间可以解耦,提高系统的灵活性和可扩展性。

2. RT-Thread 消息队列的工作原理

RT-Thread 消息队列基于先进先出(FIFO)的原则工作。发送者将消息发送到队列的尾部,而接收者从队列的头部获取消息。如果队列为空,接收者可以选择等待直到有消息可用,或者立即返回一个错误表示没有消息可接收。同样,如果队列已满,发送者可以选择等待直到有空闲空间,或者立即返回一个错误表示无法发送消息。

3. 在 RT-Thread 中创建和使用消息队列的步骤

3.1 创建消息队列

在 RT-Thread 中,你可以使用 rt_mq_create 函数来创建一个消息队列。这个函数需要指定队列的名称、消息池的大小、每个消息的大小以及队列的最大长度。

rt_mq_t msg_mq = rt_mq_create("player", 1024, 32, 10);

在这个例子中,我们创建了一个名为 "msg_mq " 的消息队列,消息池大小为 1024 字节,每个消息的大小为 32 字节,队列的最大长度为 10。

3.2 发送消息

使用 rt_mq_send 函数可以向消息队列中发送消息。这个函数需要指定消息队列的句柄、要发送的消息以及消息的长度。

char msg[] = "Hello RT-Thread!";
rt_mq_send(mq, msg, sizeof(msg));

3.3 接收消息

使用 rt_mq_recv 函数可以从消息队列中接收消息。这个函数需要指定消息队列的句柄、用于存储接收到的消息的缓冲区以及缓冲区的长度。此外,还可以指定一个超时时间,如果在指定的时间内没有接收到消息,函数将返回错误。

ret = rt_mq_recv(g_app_info.main_mq, (void *)&rcv_msg, sizeof(struct app_msg), RT_WAITING_FOREVER);
if (ret == RT_EOK)
{
        RC_LOGI("rcv_msg.value = %d",rcv_msg.value);
         if (rcv_msg.value >= 0) {
         }
}

4. 使用 RT-Thread 消息队列时需要注意的事项

‌内存管理‌:消息队列会占用一定的内存空间,包括消息池和队列控制结构。因此,在创建消息队列时,需要确保有足够的内存可用。
‌线程同步‌:消息队列提供了一种线程同步的机制。在发送和接收消息时,RT-Thread 会自动处理线程之间的同步问题,但开发者仍然需要注意避免死锁和优先级反转等问题。
‌错误处理‌:在发送和接收消息时,需要检查函数的返回值以确保操作成功。如果操作失败,需要根据错误码进行相应的处理。

5. RT-Thread 消息队列的示例代码

以下是一个完整的示例代码,展示了如何在 RT-Thread 中创建、发送和接收消息队列:

#include <rtthread.h>

#define MSG_POOL_SZ    1024
#define MSG_SIZE       32
#define MSG_QUEUE_LEN  10

static void msg_producer(void *parameter)
{
    rt_mq_t mq = (rt_mq_t)parameter;
    char msg[MSG_SIZE];
    int i = 0;

    while (1)
    {
        snprintf(msg, MSG_SIZE, "Message %d", i++);
        rt_mq_send(mq, msg, MSG_SIZE);
        rt_thread_mdelay(1000); // 1 second delay
    }
}

static void msg_consumer(void *parameter)
{
    rt_mq_t mq = (rt_mq_t)parameter;
    char buffer[MSG_SIZE];
    rt_size_t len;

    while (1)
    {
        len = rt_mq_recv(mq, buffer, MSG_SIZE, RT_WAITING_FOREVER);
        if (len > 0)
        {
            rt_kprintf("Receive Message: %s
", buffer);
        }
    }
}

int main(void)
{
    rt_mq_t mq;
    rt_thread_t producer_tid, consumer_tid;

    // Create Message Queue
    mq = rt_mq_create("mq_test", MSG_POOL_SZ, MSG_SIZE, MSG_QUEUE_LEN);
    if (mq == RT_NULL)
    {
        rt_kprintf("Create Message Queue Failed!
");
        return -1;
    }

    // Create Producer Thread
    producer_tid = rt_thread_create("producer",
                                    msg_producer, (void *)mq,
                                    1024, 10, 10);
    if (producer_tid != RT_NULL)
        rt_thread_startup(producer_tid);

    // Create Consumer Thread
    consumer_tid = rt_thread_create("consumer",
                                    msg_consumer, (void *)mq,
                                    1024, 10, 10);
    if (consumer_tid != RT_NULL)
        rt_thread_startup(consumer_tid);

    return 0;
}

在这个示例中,我们创建了两个线程:一个生产者线程和一个消费者线程。生产者线程每隔一秒向消息队列中发送一条消息,而消费者线程则不断从消息队列中接收消息并打印出来


原文地址:https://blog.csdn.net/qq_36367373/article/details/144213983

免责声明:本站文章内容转载自网络资源,如本站内容侵犯了原著者的合法权益,可联系本站删除。更多内容请关注自学内容网(zxcms.com)!