首页 > 系统相关 >LWIP 的动态内存管理

LWIP 的动态内存管理

时间:2022-12-08 17:38:43浏览次数:35  
标签:LWIP 管理 MEM memp 动态内存 MEMPOOL 内存


LWIP 的动态内存管理机制

文件mem.h mem.c memp.c memp.h学习

LWIP 的动态内存管理机制可以有三种:

C 运行时库自带的内存分配策略(MEM_LIBC_MALLOC);
动态内存堆(HEAP)分配策略;

动态内存池(POOL(MEM_USE_POOLS))分配策略。

 

动态内存堆分配策略和

通过自定义头文件lwipopt.h (原opt.h)中的宏定义 MEM_LIBC_MALLOC 来实现的,当它被定义为 1 时则使用标准 C运行时库自带的内存分配策略,而为 0时则使用 LWIP 自身的动态内存堆分配策略。一般情况下,我们选择使用

 

动态内存堆分配

其原理就是在一个事先定义好大小的内存块中进行管理,其内存分配的策略是采用最快合适(First Fit)方式,只要找到一个比所请求的内存大的空闲块,就从中切割出合适的块,并把剩余的部分返回到动态内存堆中。在分配的内存块前大约有12字节会存放内存分配器管理用的私有数据,该数据区不能被用户程序修改,否则导致致命问题。

内存释放的过程是相反的过程,但分配器会查看该节点前后相邻的内存块是否空闲,如果空闲则合并成一个大的内存空闲块。采用这种分配策略,其优点就是内存浪费小,比较简单,适合用于小内存的管理,其缺点就是如果频繁的动态分配和释放,可能会造成严重的内存碎片,如果在碎片情况严重的话,可能会导致内存分配不成功。

 

动态内存池分配

动态内存池(POOL)分配策略实现简单,内存的分配、释放效率高,可以有效防止内存碎片的产生。不过,他的缺点是会浪费部分内存。

用户需要在头文件 lwipopt.h (原opt.h)中定义宏 MEM_USE_POOLS和 MEM_USE_CUSTOM_POOLS 为

同时还要开辟一些额外的缓冲池区,创建文件lwippools.h 如下:

LWIP_MALLOC_MEMPOOL_START
LWIP_MALLOC_MEMPOOL(20, 256)
LWIP_MALLOC_MEMPOOL(10, 512)
LWIP_MALLOC_MEMPOOL(5, 1512)
LWIP_MALLOC_MEMPOOL_END

见 mem.c 文件头源码注释部分说明,内存池管理会根据以上的宏自动在内存中静态定义一个大片内存用于内存池。在内存分配申请的时候,自动根据所
请 求 的 大 小 , 选 择 最 适 合 他 长 度 的 池 里 面 去 申 请 , 如 果 启 用 宏MEM_USE_POOLS_TRY_BIGGER_POOL,那么,如果上述的最适合长度的池中没有空间可以用了,分配器将从更大长度的池中去申请。

 

Memp.c文件的数组定义,很是值得今后应用。

const u16_t memp_sizes[MEMP_MAX] = {

#define LWIP_MEMPOOL(name,num,size,desc)  LWIP_MEM_ALIGN_SIZE(size),

#include "lwip/memp_std.h"

};

上面的代码定义了缓冲池所使用的内存缓冲区,问题的关键就在于头文件memp_std.h,它里面的东西可以被简化为诸多条LWIP_MEMPOOL(name,num,size,desc)。又由于用了define关键字将LWIP_MEMPOOL (name,num,size,desc)定义为+((num) * (MEMP_SIZE + MEMP_ALIGN_SIZE(size))),所以,memp_std.h被编译后就为一条一条的+(),+(),+(),+()….

const u16_t memp_sizes[MEMP_MAX] = {

LWIP_MEM_ALIGN_SIZE(sizeof(struct raw_pcb)),

LWIP_MEM_ALIGN_SIZE(sizeof(struct udp_pcb)),

LWIP_MEM_ALIGN_SIZE(sizeof(struct tcp_pcb)),

LWIP_MEM_ALIGN_SIZE(sizeof(struct tcp_pcb_listen)),

...

};

 

数组要比实际需要的大MEM_ALIGNMENT – 1,作者考虑的是编译器的字对齐问题。详细说明可见《嵌入式网络那些事-LwIP协议深度剖析与实战演练》,朱老大说的很是明白。

协议栈还建立了一些与缓冲池管理的全局变量:

memp_num:这个静态数组用于保存各种类型缓冲池的成员数目

memp_sizes:这个静态数组用于保存各种类型缓冲池的结构大小

memp_tab:这个指针数组用于指向各种类型缓冲池当前空闲节点

实现函数:

memp_init():内存池的初始化,主要是为每种内存池建立链表memp_tab,其链表是逆序的,此外,如果有统计功能使能的话,也把记录了各种内存池的数目。

memp_malloc():如果相应的memp_tab链表还有空闲的节点,则从中切出一个节点返回,否则返回空。

memp_free():把释放的节点添加到相应的链表memp_tab头上。

 

《嵌入式网络那些事-LwIP协议深度剖析与实战演练》,这本书,值得拥有!

 

 

 

 

 

 



标签:LWIP,管理,MEM,memp,动态内存,MEMPOOL,内存
From: https://blog.51cto.com/u_6958388/5922942

相关文章

  • LWIP 的ethernetif.c 学习
     《嵌入式网络那些事-LwIP协议深度剖析与实战演练》学习 ethernetif.c netif.c 在 LWIP中,是通过一个叫做结构体:structnetif{structnetif*next;//指向下一个......
  • freertos 内存管理
    每当任务,队列或是信号量被创建时,内核需要进行动态内存分配。当内核请求内存时,其调用pvPortMalloc()而不是直接调用malloc();当释放内存时,调用vPortF......
  • 多厂商设备高效自动配置与管理
    ​ 随着企业向云迁移、5G落地、物联网设备激增、网络爆炸、网络流量变得海量复杂,企业经常会遇到网络拥塞和服务质量低等一系列问题,加强网络管理和改善网络的运行己成为当......
  • [附源码]Python计算机毕业设计Django汽车租赁管理系统
    OverridetheentrypointofanimageIntroducedinGitLabandGitLabRunner9.4.Readmoreaboutthe extendedconfigurationoptions.Beforeexplainingtheav......
  • Windows平台下Vim安装插件(采用内置的包管理器)
    需要提前说明的一些事情本人电脑环境为Windows11,vim采用包管理器scoop下载安装,版本为9.0。在尝试为vim安装插件过程中,参考了知乎上的一篇文章如何安装VIM插件,其中提到在V......
  • Spring:资源管理
    java标准资源管理职责说明面向资源文件系统、artifact(jar、war、ear文件)以及远程资源(HTTP、FTP等)API整合ClassLoader#getResource、java.io.File、java.ne......
  • python 包管理
    python官方的第三方库的仓库:​​https://pypi.org/​​ pip是python的包管理工具pip--version#查看当前版本 安装pipinstall-Upip#升级pippipinstall包名==1.0.4......
  • 如何为管理者设计 360 评估调查题目?
    宣布360评估通常会使管理人员不稳定。同事、下属、管理层甚至客户和供应商通过预先制定的问卷来反馈。360评估可以采用多种形式:从50到300多个问题,例如使用开放式或......
  • 保障房管理系统,高端住宅长租化趋势显现
    版权声明:本文章由“厦门多米克信息技术有限公司”编辑组汇编而成,未经授权和许可,任何个人或媒体不得对本网站的文章及其他信息资料予以复制、转载、抄袭、改编。厦门多米克......
  • [附源码]Python计算机毕业设计Django疫情防控管理系统
    OverridetheentrypointofanimageIntroducedinGitLabandGitLabRunner9.4.Readmoreaboutthe extendedconfigurationoptions.Beforeexplainingtheav......