从零开始学ESP32:(四)ESP32/freeRTOS 实现一个内存池操作

2023-05-16

零开始学ESP32:个人笔记记录:

芯片型号: ESP32
网络环境支持:LWIP
IDF.PY-SDK: ESP-IDF v4.3
芯片功能: freeRTOS系统

声明: 当前内存池参考 Linux / rttthreadOS 两个套系统,自己写成的。

内存池的创建:
头文件:

#include <stdint.h>
内存池主体结构


#define MP_ALIGN_SIZE 4 
#define MP_ALIGN(size, align)               (((size) + (align) - 1) & ~((align) - 1))

typedef struct ST_MEMORY_POOL__ { 
    
    void*     startA_address;    // 起始地址
    size_t    size ;             // 总大小
    size_t    block_size;        // 块大小
    uint8_t*  block_lisk;        // 块链表
    size_t    block_total_count; // 块数量   
    size_t    block_free_count;  // 空闲块数量

}st_memoryPool , *st_mp_t;


/****************************************************************************
 * 函数名称:T_mp_create
 * 输入值:  
 * 输出值:
 * 返回值
 * 其他: 
 * 说明: 内存池的创建
 * */
void* T_mp_create(size_t block_count , size_t  block_size)
{
    uint8_t* block_chr      = NULL;
    register size_t  offset = 0; //寄存器变量

    st_memoryPool* mp = (st_memoryPool * )pvPortMalloc ( sizeof( st_memoryPool ) ); 
    if( mp == NULL )
    {
        return NULL;
    }
    block_size     = MP_ALIGN( block_size ,  MP_ALIGN_SIZE ); //内存4字节对齐
    mp->block_size = block_size;
    mp->size       =  (block_size + sizeof(uint8_t * ) ) * block_count ;

    mp->startA_address = pvPortMalloc(  mp->size  );
    if( !mp->startA_address )
    {
        goto Err_startAdd;
    }

    mp->block_total_count = block_count;
    mp->block_free_count  = block_count;

    block_chr = mp->startA_address ; 
    for(offset = 0 ; offset < mp->block_total_count ; offset ++ )
    {
        *( uint8_t **)( block_chr  + offset *  (block_size + sizeof(uint8_t *)))
        = block_chr + ( offset + 1) * ( block_size + sizeof( uint8_t *) ); 
    }

    *( uint8_t **)( block_chr  + (offset -1) *  (block_size + sizeof(uint8_t *))) = NULL;

    mp->block_lisk = block_chr;

    return mp;

Err_startAdd: vPortFree( mp );
    return NULL;
}

在内存池里面申请内存

/****************************************************************************
 * 函数名称:T_mp_malloc
 * 输入值:  
 * 输出值:
 * 返回值
 * 其他:每次操作内存池分配空间的操作, 需要打断时间 ~= 3400( us ) ( 微秒 )    
 * 说明: 内存池的申请
 * 每次申请必须进行返回,不论当前内存池是否还存在对象
 * 
 * 
 * */
void* T_mp_malloc( st_memoryPool* mp )
{
    uint8_t* block_chr = NULL;
    vTaskSuspendAll();                  //将任务管理器挂起来
    if( mp->block_free_count == 0 ) 
    { 
        xTaskResumeAll();
        return NULL;
    }
    mp->block_free_count --;
    block_chr = mp->block_lisk; 
    assert( block_chr != NULL );
    mp->block_lisk = *(uint8_t **)block_chr;
    *( uint8_t **)block_chr = (uint8_t *)mp;
    xTaskResumeAll();                   //开启任务管理器 
    return ( uint8_t * )( block_chr + sizeof( uint8_t *) );
}

// 释放归还内存块回给内存池里面

/****************************************************************************
 * 函数名称:T_mp_free
 * 输入值:  
 * 输出值:
 * 返回值
 * 其他:  
 * 说明: 内存池的释放
 * */
void T_mp_free( void * block )
{
    uint8_t** block_str = NULL;
    st_memoryPool* mp   = NULL;
    vTaskSuspendAll();  
    block_str      = (uint8_t **)( (uint8_t*) block - (sizeof( uint8_t * )));
    mp             = (st_memoryPool *)*block_str;
    *block_str     = mp->block_lisk;
    mp->block_lisk = ( uint8_t* )block_str; 
    mp->block_free_count ++;
    xTaskResumeAll();                   //开启任务管理器 
}

//释放整个内存块

/****************************************************************************
 * 函数名称:T_mp_free
 * 输入值:  
 * 输出值:
 * 返回值
 * 其他:  
 * 说明: 内存池的释放
 * */
void T_mp_free( void * block )
{
    uint8_t** block_str = NULL;
    st_memoryPool* mp   = NULL;
    vTaskSuspendAll();  
    block_str      = (uint8_t **)( (uint8_t*) block - (sizeof( uint8_t * )));
    mp             = (st_memoryPool *)*block_str;
    *block_str     = mp->block_lisk;
    mp->block_lisk = ( uint8_t* )block_str; 
    mp->block_free_count ++;
    xTaskResumeAll();                   //开启任务管理器 
}

在当前这个版本内存池里面存在尚未解决的问题,在使用时候必须要考虑到:

一、当前任务向内存池申请内存是(T_mp_malloc),没有实现一个超时等待,或者阻塞等待直至有空闲内存块
当前内存池空闲内存为零时, 应该将当前任务挂起并且放到一个任务里面,等待内存到来。

二、在T_mp_malloc 函数里面使用到vTaskSuspendAll()和 xTaskResumeAll(),FREERTOS内存API ,尚未明确会不会
存在一些危险操作和与之相关的问题

三、当多任务都在同时等待当前内存池时候而被第三方任务将整个内存池删除,应该要实现一个操作, 唤醒当前所有等待的任务,并且告
知当前内存池一已经被释放。

要是碰巧看到这边博文的工程师,并且有想法或者是对freeRTOS比较熟系的,希望您路过的时候不设赐教。
当前用上你的想法或者对应的方案,博文也会明确表示当您的身份和对应的贡献。
感谢。

关注微信公众号 一起学习 ( 技术Code城 )

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

从零开始学ESP32:(四)ESP32/freeRTOS 实现一个内存池操作 的相关文章

  • 激光雷达核心技术及行业格局梳理

    点击上方 小白学视觉 xff0c 选择加 34 星标 34 或 置顶 重磅干货 xff0c 第一时间送达 引言 xff1a 车载摄像头是ADAS 的核心传感器 车载摄像头搭载颗数稳步提升 根据 Yole 数据 xff0c 2018 年全球平
  • 2 ROS1通讯编程基础(2)

    2 ROS1通讯编程基础 2 3 配置文件的解读2 3 1 CMakeList txt解读2 3 1 1 find package的配置2 3 1 2 messages services and actions的配置2 3 1 3 动态重配
  • Rviz 使用Arbotix控制机器人运动

    需求 控制机器人模型在 rviz 中做圆周运动 实现流程 安装 Arbotix创建新功能包 xff0c 准备机器人 urdf xacro 文件添加 Arbotix 配置文件编写 launch 文件配置 Arbotix启动 launch 文件
  • VINS问题整理

    VINS的初始化过程 xff1f 首先进行纯视觉SfM xff1a 把滑窗填满 xff0c 然后选择枢纽帧 xff08 和最后一帧有足够的视野重叠保证计算的位姿精度 xff0c 并且和最后一帧有足够的视差保证三角化地图点的精度 xff09
  • 两台ubuntu电脑如何搭建局域网以及通信

    两台ubuntu电脑如何搭建局域网以及通信 功能 xff1a 用自己的电脑代替设备中的电脑进行数据处理 xff0c 以及将最后的结果传给设备电脑 需要做的内容的 xff1a 首先用网线将自己的pc与设备连接起来 1 将自己的笔记本ip地址手
  • PC偏振控制器、锁模激光器技术、AOM声光调制器、相位噪声、锁相环、光耦合器类型

    1 PC 偏振控制器 xff08 1 xff09 什么叫做偏振光 xff1f polarized light 光是一种电磁波 xff0c 电磁波是横波 xff0c 它具有偏振性 xff0c 具有偏振性的光则称为偏振光 具体体现 xff1a
  • 小梅哥——38译码器

    三八译码器 xff0c 即是 3 种输入状态翻译成 8 种输出状态 真值表 代码展示 module decoder 3 8 a b c out input a 输入端口a input b 输入端口b input c 输入端口c output
  • 基本RS触发器(SR锁存器)

    一 前言 SR锁存器 Set Reset Latch 是静态存储单元当中最基本 xff0c 也是电路结构最简单的一种 xff0c 通常由两个或非门或者与非门组成 其中S表示Set xff0c R表示Reset 则S D称为置位端或置1输入端
  • 01-RTOS

    对于裸机而言 xff0c 对于RTOS而言 即 xff1a 对于裸机 xff0c 打游戏意味着不能回消息 回消息意味着不能打游戏 对于RTOS 打游戏和裸机的切换只需要一个时间片节拍 1ms 从宏观来看 就是同时进行的两件事 xff08 但
  • uORB笔记

    不同的类调用同一函数orb subscribe ORB ID vehicle gps position xff0c 来订阅GPS信息是 xff0c 该函数返回的值不同 xff0c 也就是说每个订阅者针对同一主题 xff0c 在调用函数orb
  • STM32 SystemInit()函数学习总结

    拿到程序后如何看系统时钟 xff1f User文件夹 system stm32f4xx程序 xff0c 先找systemcoreclock 系统时钟 xff09 但是这里这么多个系统时钟应该如何选择 点击魔法棒 xff0c 然后点击C C
  • FPGA IP核之PLL四种输出模式的理解

    一 源同步模式 使得进入管脚时的数据和上升沿的相位关系与到达芯片内部第一级寄存器时数据和上升沿的相位关系保持不变 xff08 通过调整内部的布局布线延时做到的 xff0c 用于数据接口 xff0c 特别是高速的情况下 xff09 详细理解
  • FPGA_边沿监测理解

    一 简易频率计设计中为什么一定要获取下降沿 gate a 实际闸门信号 gate a stand 将实际闸门信号打一拍之后的信号 gate a fall s 下降沿标志信号 cnt clk stand Y值 xff0c 即在实际闸门信号下
  • HAL库 STM32 串口通信

    一 实验条件 将STM32的PA9复用为串口1的TX xff0c PA10复用为串口1的RX STM32芯片的输出TX和接收RX与CH340的接收RX和发送TX相连 xff08 收发交叉且PCB上默认没有相连 xff0c 所以需要用P3跳线
  • 全局变量和局部变量

    一 C语言由四种地方可以定义变量 在函数外部定义的是全局变量 xff08 这里的函数包括main函数 xff09 在头文件中定义的是全局变量 在函数或语句块内部定义的是局部变量 函数的参数是该函数的局部变量 全局变量 xff0c 在定义位置
  • 单片机中断

    蓝桥杯单片机之中断 1 中断含义及过程 中断是指CPU在处理A事情时 xff0c 发现B请求CPU立刻去处理 xff08 中断发生 xff09 xff0c 于是CPU去处理B xff08 中断服务 xff09 xff0c 处理完B后又再次回
  • AprilTag的使用、相关问题及解决方法

    使用棋盘格标定相机 安装标定功能包 span class token function sudo span span class token function apt get span span class token function i
  • 对接海康综合安防管理平台经验总结

    前言 xff1a 因业务需要对接海康威视的综合安防管理平台获得下属所管理的摄像头 xff0c 根据摄像头code获得监控视频流信息 1 详情可以浏览海康开放平台 xff0c 在官网上有对应的接入指南以及开放的API接口 前提是本地已部署了海
  • 【环境配置】Visual Studio opencv配置

    需求 在Visual Studio环境中编写C 43 43 代码 xff0c 同时可以调用OpenCV的相关代码 1 安装OpenCV 访问 opencv 官网下载对应平台的库文件 注意 xff1a Visual Studio和OpenCV
  • MySQL常见用法

    文章目录 一 时间类1 1 DATE SUB 函数1 2 NOW CURDATE CURTIME DATE 函数1 3 实战 二 统计类三 字符类3 1 LOCATE 函数3 2 concat 函数3 3 concat ws 函数3 4 g

随机推荐

  • 牢记公式,ardupilot EKF2就是纸老虎(四)!

    版权声明 xff1a 本文为博主原创文章 xff0c 转载请附上博文链接 xff01 四 一睹EKF2芳容 因为篇幅过长 xff0c 写的一些公式会乱码 xff0c 没办法只能把 牢记公式 xff0c ardupilot EKF2就是纸老虎
  • Java Optional使用

    文章目录 Optional一 Optional 简介二 创建 Optional 实例2 1 empty 方法2 2 of 方法2 3 ofNullable 方法 三 Optional的使用3 1 访问 Optional 对象的值3 1 1
  • 正则表达式:基础详解以及在Java中的使用

    文章目录 一 正则表达式1 1 正则表达式中的特殊字符1 2 正则表达式所支持的合法字符1 3 方括号表达式1 4 边界匹配符1 5 三种模式的数量表示符 二 应用2 1 String 类2 2 Pattern 类和 Matcher 类 一
  • Python学习:关键字global和nonlocal的用法说明

    一 global global关键字用来在函数或其他局部作用域中使用全局变量 1 1 如果局部要对全局变量修改 xff0c 而不使用global关键字 count 61 0 def global test count 43 61 1 pri
  • Python:flask框架下前后端的数据交互

    文章目录 前提 一 前端发送数据 xff0c 后端接受数据1 1 路由传参数 数据 1 2 表单提交 二 后端发送数据 xff0c 前端接受数据 前提 后端 xff1a python 的 flask 框架 前端 xff1a html css
  • Python关于None的报错:'NoneType' object is not iterable和cannot unpack non-iterable NoneType object

    文章目录 一 TypeError 39 NoneType 39 object is not iterable xff08 类型错误 xff1a 39 NoneType 39 对象不是可迭代的 xff09 二 TypeError cannot
  • Git:合并分支----git merge命令应用的三种情景

    文章目录 一 git merge 命令应用的三种情景1 1 快进 无冲突 1 2 非 快进 xff0c 修改不同文件 无冲突 1 3 非 快进 xff0c 修改相同文件 有冲突 一 git merge 命令应用的三种情景 1 1 快进 无冲
  • Git:远程分支----git fetch命令的使用

    git fetch 命令的使用 从远程主机克隆 Git 的 clone 命令会为你自动将远程主机命名为 origin xff0c 拉取它的所有数据 xff0c 创建一个指向它的 master 分支的指针 xff0c 并且在本地将其命名为 o
  • Git:移除文件----git rm命令的使用

    文章目录 一 git rm 命令使用1 1 rm 命令1 2 git rm 命令1 3 git rm f 命令1 4 git rm cached 命令 一 git rm 命令使用 Git 本地数据管理 xff0c 大概可以分为三个区 xff
  • 【OpenMv小车】OpenMv追小球的小车之pid调用

    pid py gt gt https github com wagnerc4 flight controller blob master pid py openmv 官网 xff1a http book openmv cc project
  • 【深入理解C++】函数模板作为成员函数

    文章目录 1 普通类的成员函数模板2 类模板的成员函数模板 1 普通类的成员函数模板 不管是普通类还是类模板 xff0c 它们的成员函数都可以是函数模板 xff0c 称为成员函数模板 xff0c 但不可以是虚函数 xff0c 否则编译器报错
  • QGroundControl开发之使用自定义mavlink

    工具 对QGC进行二次开发时 xff0c 常常会遇到想使用自定义mavlink的情况 xff0c 但不像APM那样编译命令会根据xml文件自动生成mavlink协议 QGC似乎不能自动生成mavlink协议 xff08 之前试过似乎不能自动
  • 字符串连接 (c语言)

    题目描述 将给定的字符串连接起来 书中的算法描述如下 xff1a 图 xff1a 字符串连接算法 输入描述 三对字符串 xff0c 每对字符串占一行 xff0c 用空格隔开 每个字符串只包含数字和英文字母大小写且长度不超过100 输出描述
  • STM32—UART中断收发 Day4

    软件 xff1a STM32CubeMX xff0c MDK ARM 硬件 xff1a 蓝桥杯物联网Lora开发板 xff0c 板载芯片STM32L071 一 STM32CubeMX配置 1 先在连接 xff08 Connectivity
  • 虚拟机出现command XXX is available in /bin/ls问题

    问题 xff1a 使用本地的shell命令时候 The command could not be located because 39 usr bin bin 39 is not included in the PATH environme
  • 全志lichee的pack命令

    全志lichee目录打包命令流程 pack 将打包命令传进去build sh脚本里面 查看buildsh里面的脚本命令 其实里面的脚本还是较为简单地的 xff0c 仅仅是作为一个过渡 xff0c 然后就跑进去buildroot script
  • Linux_kernel驱动之GPIO子系统

    前言 xff1a gpio子系统的内容在drivers gpio文件夹下 xff0c 主要文件有 xff1a devres c xff1a devres c是针对gpio api增加的devres机制的支持gpiolib c xff1a g
  • 转载:全志问题解决方法

    版权声明 xff1a 本文为博主原创文章 xff0c 遵循 CC 4 0 BY SA 版权协议 xff0c 转载请附上原文出处链接和本声明 本文链接 xff1a https blog csdn net yanzheng1113 articl
  • 从零开始学ESP32:(二) 开启ESP32WIFI -STA和AP模式共存

    从零开始学ESP32 xff1a 个人笔记记录 xff1a 芯片型号 ESP32 网络环境支持 LWIP IDF PY SDK ESP IDF v4 3 芯片功能 xff1a 支持STA AP网络共存模式 xff1a 工程 xff1a es
  • 从零开始学ESP32:(四)ESP32/freeRTOS 实现一个内存池操作

    零开始学ESP32 xff1a 个人笔记记录 xff1a 芯片型号 ESP32 网络环境支持 LWIP IDF PY SDK ESP IDF v4 3 芯片功能 xff1a freeRTOS系统 声明 xff1a 当前内存池参考 Linux