FreeRTOS学习笔记-MessageBuffer

概述

MessageBuffer与StreamBuffer使用基本相同,但有以下2点区别:

  • MessageBuffer一次只能接收1条Message,StreamBuffer则根据长度接收
  • MessageBuffer在接收缓冲区<1条消息大小时,不会接收,而StreamBuffer则会将数据截断接收

关键函数

#include "freertos/message_buffer.h"

//创建Message_buffer
MessageBufferHandle_t xMessageBufferCreate( size_t xBufferSizeBytes);//buffer 大小
			
//发送Message_buffer
size_t xMessageBufferSend( 
			MessageBufferHandle_t xMessageBuffer,//buffer 句柄
			const void *pvTxData, //发送数据指针
			size_t xDataLengthBytes,//从pvTxData拷贝到Message_buffer的数据量,同时会向buffer写入消息长度,占sizeof(size_t)==4Byte
			TickType_t xTicksToWait );//若Message_buffer空间不够则需要等待的时间
//返回值: 正常返回 xDataLengthBytes 否则返回0,表示buffer空间不足

//从Message_buffer中接收数据
size_t xMessageBufferReceive( 
			MessageBufferHandle_t xMessageBuffer,//buffer 句柄
			void *pvRxData,//接收数据指针
			size_t xBufferLengthBytes,//设置可以接收消息的最大长度,如果太小不能容纳一条消息,则该消息将不被接收,并返回0。
			TickType_t xTicksToWait );//若Message_buffer为空则需要等待的时间

课程示例

StreamBuffer 接收

#include <stdio.h>
#include "sdkconfig.h"
#include "freertos/FreeRTOS.h"
#include "freertos/task.h"
#include "esp_system.h"
#include "esp_spi_flash.h"

#include "string.h"
#include "freertos/stream_buffer.h"

StreamBufferHandle_t sbuffer1;

void mytask1(void *pvParameter)
{
    size_t send_size;
    size_t send_len;
    char send_str[50];
    for (int i = 0; i < 3; i++)
    {
        send_len = sprintf(send_str, "Hello World NO%d \n", i);
        send_size = xStreamBufferSend(
            sbuffer1,         // buffer 句柄
            (void *)send_str, //发送数据指针
            send_len,         //从pvTxData拷贝到stream_buffer的数据量
            portMAX_DELAY);   //若stream_buffer空间不够则需要等待的时间
        printf("task1 send len=%d , size = %d \n", send_len, send_size);
    }
    vTaskDelete(NULL);
}

void mytask2(void *pvParameter)
{
    size_t rx_size;
    char rx_str[50];
    vTaskDelay(pdMS_TO_TICKS(2000));
    while (1)
    {
        memset(rx_str, 0, sizeof(rx_str)); //三个参数分别为:数据指针、初始化值、初始化大小
        rx_size = xStreamBufferReceive(
            sbuffer1,       // buffer 句柄
            (void *)rx_str, //接收数据指针
            sizeof(rx_str), //接收的字节数 
            portMAX_DELAY); //若stream_buffer为空则需要等待的时间
        printf("task2 rx size = %d , rx str = %s\n", rx_size, rx_str);
        vTaskDelay(pdMS_TO_TICKS(1000));
    }
}

void app_main(void)
{
    sbuffer1 = xStreamBufferCreate(1000, 40);
    if (sbuffer1 != NULL)
    {
        xTaskCreate(mytask1, "mytask1", 1024 * 5, NULL, 1, NULL);
        xTaskCreate(mytask2, "mytask2", 1024 * 5, NULL, 1, NULL);
    }
}

效果

task1 send len=17 , size = 17
task1 send len=17 , size = 17
task1 send len=17 , size = 17
task2 rx size = 50 , rx str = Hello World NO0
Hello World NO1
Hello World NO2 �?
task2 rx size = 1 , rx str =

修改任务2接收代码,接收数量为10,让一次接收内容小于1次发送内容,效果如下:

task1 send len=17 , size = 17
task1 send len=17 , size = 17
task1 send len=17 , size = 17
task2 rx size = 10 , rx str = Hello Worl
task2 rx size = 10 , rx str = d NO0
Hel
task2 rx size = 10 , rx str = lo World N
task2 rx size = 10 , rx str = O1
Hello
task2 rx size = 10 , rx str = World NO2
task2 rx size = 1 , rx str =

接收内容被截断接收。

MessageBuffer 接收

#include <stdio.h>
#include "sdkconfig.h"
#include "freertos/FreeRTOS.h"
#include "freertos/task.h"
#include "esp_system.h"
#include "esp_spi_flash.h"

#include "string.h"
#include "freertos/message_buffer.h"

MessageBufferHandle_t sbuffer1;

void mytask1(void *pvParameter)
{
    size_t send_size;
    size_t send_len;
    char send_str[50];
    for (int i = 0; i < 3; i++)
    {
        send_len = sprintf(send_str, "Hello World NO%d \n", i);
        send_size = xMessageBufferSend(
            sbuffer1,         // buffer 句柄
            (void *)send_str, //发送数据指针
            send_len,         //从pvTxData拷贝到Message_buffer的数据量
            portMAX_DELAY);   //若Message_buffer空间不够则需要等待的时间
        printf("task1 send len=%d , size = %d \n", send_len, send_size);
    }
    vTaskDelete(NULL);
}

void mytask2(void *pvParameter)
{
    size_t rx_size;
    char rx_str[50];
    vTaskDelay(pdMS_TO_TICKS(2000));
    while (1)
    {
        memset(rx_str, 0, sizeof(rx_str)); //三个参数分别为:数据指针、初始化值、初始化大小
        rx_size = xMessageBufferReceive(
            sbuffer1,       // buffer 句柄
            (void *)rx_str, //接收数据指针
            sizeof(rx_str), //接收的字节数
            portMAX_DELAY); //若Message_buffer为空则需要等待的时间
        printf("task2 rx size = %d , rx str = %s\n", rx_size, rx_str);
        vTaskDelay(pdMS_TO_TICKS(1000));
    }
}

void app_main(void)
{
    sbuffer1 = xMessageBufferCreate(1000);
    if (sbuffer1 != NULL)
    {
        xTaskCreate(mytask1, "mytask1", 1024 * 5, NULL, 1, NULL);
        xTaskCreate(mytask2, "mytask2", 1024 * 5, NULL, 1, NULL);
    }
}

效果:

task1 send len=17 , size = 17 
task1 send len=17 , size = 17
task1 send len=17 , size = 17
task2 rx size = 17 , rx str = Hello World NO0

task2 rx size = 17 , rx str = Hello World NO1

task2 rx size = 17 , rx str = Hello World NO2

同样修改任务2接收代码,接收数量为10,让一次接收内容小于1次发送内容,效果如下:

task1 send len=17 , size = 17
task1 send len=17 , size = 17
task1 send len=17 , size = 17
task2 rx size = 0 , rx str =
task2 rx size = 0 , rx str =
task2 rx size = 0 , rx str =
task2 rx size = 0 , rx str =
task2 rx size = 0 , rx str =
task2 rx size = 0 , rx str =
task2 rx size = 0 , rx str =
task2 rx size = 0 , rx str =

任务2一直不能接收到数据,但消息一直存在于buffer中。

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值