LiteOS-M内存特性-非连续性内存

举报
zhushy 发表于 2021/08/30 15:16:42 2021/08/30
【摘要】 一些芯片片内RAM大小无法满足要求,需要使用片外物理内存进行扩充。对于这样的多段非连续性内存,需要内存管理模块统一管理,应用使用内存接口时不需要关注内存分配属于哪块物理内存。OpenHarmony LiteOS-M内核支持多段非连续性内存区域,把多个非连续性内存逻辑上合一,用户不感知底层的多段非连续性内存区域。多段非连续性内存如下图所示:  OpenHarmony LiteOS-M内核内存模...

一些芯片片内RAM大小无法满足要求,需要使用片外物理内存进行扩充。对于这样的多段非连续性内存,需要内存管理模块统一管理,应用使用内存接口时不需要关注内存分配属于哪块物理内存。OpenHarmony LiteOS-M内核支持多段非连续性内存区域,把多个非连续性内存逻辑上合一,用户不感知底层的多段非连续性内存区域。多段非连续性内存如下图所示:

 

 

OpenHarmony LiteOS-M内核内存模块在支持非连续性内存时,把不连续的内存区域作为空闲内存结点插入到空闲内存节点链表,把不同内存区域间的不连续部分标记为虚拟的已使用内存节点,从逻辑上把多个非连续性内存区域实现为一个统一的内存池。下面通过示意图说明下多段非连续性内存的运行机制:

LiteOS-M内存特性-非连续性内存-鸿蒙HarmonyOS技术社区

  1. 把多段非连续性内存区域的第一块内存区域通过调用LOS_MemInit接口进行初始化。
  2. 获取下一个内存区域的开始地址和长度,计算该内存区域和上一块内存区域的间隔大小gapSize。
  3. 把内存区域间隔部分视为虚拟的已使用节点,使用上一个内存区域的尾节点,设置其大小为gapSize+ OS_MEM_NODE_HEAD_SIZE。
  4. 把当前内存区域划分为一个空闲内存节点和一个尾节点,把空闲内存节点插入到空闲链表,并设置各个节点的前后链接关系。
  5. 如果有更多的非连续内存区域,重复上述步骤2-4。

当没有开启宏LOSCFG_MEM_MUL_REGIONS或者宏设置为0时,不支持多段非连续性内存区域,相关代码不使能。当宏 LOSCFG_MEM_MUL_REGIONS=1时,支持多段非连续性内存区域,相关代码使能。开发步骤如下:

开发者根据使用的多段内存区域实际情况,配置多段非连续性内存区域。
调用接口UINT32 LOS_MemRegionsAdd(VOID *pool, const LosMemRegion * const memRegions, UINT32 memRegionCount)实现多段非连续性内存逻辑上合并为一个统一的内存池。
按统一的内存池,正常调用内存接口实现业务操作。
对于多段非连续性内存区域,可以在链接脚本中进行配置。下面的示例配置片段仅用于演示:

 . = ALIGN(4);
  .memRegion1 :
  {
    __memory1_start = .; 
    . = . + 0x10000;  /* memory region length */
    __memory1_end = .;
  } >RAM
......
 . = ALIGN(4);
  .memRegion2 :
  {
    __memory2_start = .;
    . = . + 0x1000; /* memory region length */
    __memory2_end = .;
  } >RAM
  

在开发者应该代码中,可以调用接口UINT32 LOS_MemRegionsAdd(VOID *pool, const LosMemRegion * const memRegions, UINT32 memRegionCount)实现多段非连续性内存逻辑上合并为一个统一的内存池。示例代码如下: 

#include "los_memory.h"

#if (LOSCFG_MEM_MUL_REGIONS == 1)
    extern CHAR __memory1_start;
    extern CHAR __memory2_start;

    // 使用LosMemRegion数组配置多段非连续性内存区域
    LosMemRegion memRegions[] =
    {
        { (UINT8 *)&__memory1_start, 0x10000 },
        { (UINT8 *)&__memory2_start, 0x1000 }
    };

    ......

    // 逻辑上合并多段内存区域为一个统一的内存池
    ret = LOS_MemRegionsAdd(NULL, memRegions, sizeof(memRegions) / sizeof(memRegions[0]));
    if (ret != LOS_OK) {
        return ret;
    }
#endif

【版权声明】本文为华为云社区用户原创内容,转载时必须标注文章的来源(华为云社区)、文章链接、文章作者等基本信息, 否则作者和本社区有权追究责任。如果您发现本社区中有涉嫌抄袭的内容,欢迎发送邮件进行举报,并提供相关证据,一经查实,本社区将立刻删除涉嫌侵权内容,举报邮箱: cloudbbs@huaweicloud.com
  • 点赞
  • 收藏
  • 关注作者

评论(0

0/1000
抱歉,系统识别当前为高风险访问,暂不支持该操作

全部回复

上滑加载中

设置昵称

在此一键设置昵称,即可参与社区互动!

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。