5. 动态内存管理(基于硬件MMU)

AD23N 支持基于硬件MMU实现的动态内存管理,系统通过虚拟内存机制提供了一种更灵活、更安全的内存管理方式。

本章节主要围绕以下几点讲解:


5.1. MMU相关接口

5.1.1. 函数void mem_init(void)

该函数用于初始化MMU,SDK已在main函数调用。

5.1.2. 函数void *malloc(size_t size)

该函数用于申请一块虚拟内存。其中参数::

1、size:申请内存大小,单位为byte
2、返回值:
    地址:申请内存成功。
    空指针:申请内存失败。

5.1.3. 函数void *zalloc(size_t size)

该函数用于申请一块虚拟内存,并且对申请到的内存进行清0。其中参数::

1、size:申请内存大小,单位为byte
2、返回值:
    地址:申请内存成功。
    空指针:申请内存失败。

5.1.4. 函数void free(void *pv)

该函数用于释放申请过的内存。其中参数::

1、pv:申请过的动态内存指针,如果传入的指针已经被释放过,会出现MMU访问异常。

free之后的指针还是会保留之前申请到的值,建议free之后将指针清空。

5.2. 一些旧的内存管理函数说明

5.2.1. 函数void *my_malloc(u32 size, mm_type xType)

对于支持MMU的芯片,该函数内部已拦截为使用mmu的malloc,因此可以当作void *malloc(size_t size)使用,xType参数无效。

5.2.2. void *my_free(void *pv)

对于支持MMU的芯片,函数内部已拦截为使用mmu的free,因此可以当作void free(void *pv)使用。


5.3. MMU在SDK的使用情况

AD23N SDK已经用于解码、编码、音效、文件系统、以及SARADC外设驱动。

因此,AD23N SDK和以往的玩具系列芯片相比,ld文件中overlay的绝大部分的编码、解码、音效所需要的代码段都已去掉。即算法所需要的ram都通过malloc申请。

SDK为了方便排查相关的内存泄露问题,在每个申请内存的地方都添加了申请内存的计数值(仅用于排查内存申请和释放是否成对调用),例如:

"解码内存申请计数“

解码内存申请计数

如果一个文件中需要有多个cnt,可以按以下方式添加

"文件系统内存申请计数“

文件系统内存申请计数


5.4. SDK已有的MMU_debug接口

SDK提供了一个打印函数,通过轮询的方式,讲所有内存申请的计数值打印出来,以此排查内存申请和释放是否成对调用。

如下图添加了一个cnt打印函数(用于打印调用malloc和free的cnt值)到d_malloc_cnt段,只要调用all_malloc_cnt_dump函数就能将段内所有的打印函数轮询一遍。

"文件系统内存申请计数“

文件系统内存申请计数

"malloc_cnt轮询打印函数“

malloc_cnt轮询打印函数


5.5. MMU使用的注意事项

1、MMU申请到的内存不建议用于硬件访问,否则可能会产生一些边界问题。

2、free之后的指针还是会保留之前申请到的值,建议free之后将指针清空。否则再次访问可能会出现异常