社群有新朋友好奇:“AirUI界面这么流畅,应用也很丰富,跑起来会不会特别吃内存?”
要回答这个问题,得先搞懂 LuatOS 是怎么为代码安排“住所”的。一言以蔽之,在资源受限的嵌入式环境中,精巧的内存分配策略往往比单纯的代码优化更能决定系统性能的上限。


上一篇文章我们聊了 RAM 的基础知识和 Lua 虚拟机的内存模型,今天我们就深入系统层面,看看 LuatOS 如何对有限的物理内存进行逻辑划分,为你的应用高效“分房”。
模组内存总体规划
LuatOS 将物理内存划分为不同功能的逻辑区域,就像把一套房子规划成客厅、卧室和书房。不同的模组其 RAM 大小和分配策略也各不相同。
内存版“三室一厅”
我们以拥有 8MB RAM 的 Air780EHM 模组为例。

根据实际测试,其内存分配情况如下:

具体的内存区域划分可以用下表清晰地展示:

- Lua 内存:4MB,占比50%。这是 Lua 脚本运行的“主战场”,用于存储变量、函数、表等。
- 系统内存(sys):3MB,占比37.5%。这块区域用于内核堆、任务栈、中断栈以及各类驱动的缓冲区。
- 保留/隐藏区域:约1MB,占比12.5%。
这里约 1MB 的“隐藏”内存,主要分配给了通信协议栈缓存、音频处理缓冲区、Wi-Fi 缓冲区(如适用)、安全引擎缓存和 DMA 描述符等系统底层核心组件。这种分配方式清晰地体现了 LuatOS 的设计理念——优先保障系统核心功能的稳定运行,在此基础之上,再将剩余的资源尽可能多地分配给 Lua 虚拟机,以支持更复杂的应用逻辑。
Air780EHM 模组的 PSRAM 说明
1. 物理内存构成
Air780EHM 使用的是 EC718HM 系列芯片,该芯片配备了物理 PSRAM。
2. 内存区域映射
- sys 内存:实际上位于 PSRAM 上。从用户角度看,
sys 内存区域和 psram 内存区域在 Air780EHM 上是完全相同的物理内存,只是逻辑统计的视角不同。
- Lua 内存:同样实际位于 PSRAM 上,但它是独立划分出来的一块区域。
3. 内存分配关系
简单来说,Air780EHM 的 8MB 物理内存全部位于 PSRAM 上。用户视角看到的 sys、lua、保留区域,是 LuatOS 在逻辑上进行的划分,物理上它们都位于这片 PSRAM 之中。
内存查询接口
在 LuatOS 中,rtos.meminfo() 是最核心的内存查询接口,用于获取不同类型内存的实时使用情况。
函数原型:rtos.meminfo(type)
功能:获取 LuatOS 指定类型的内存信息。
参数说明:
type:可选参数,字符串类型。
- 可取值为
"lua"(查询 Lua 虚拟机内存)、"sys"(查询系统内存)、"psram"(查询 PSRAM 内存)。
- 默认值为
"lua"。
返回值:返回三个数值,分别是总内存大小、已使用内存大小、历史峰值内存大小(单位:字节)。
使用示例:
下面的代码展示了如何查询三种不同类型的内存信息:

-- rtos.meminfo() 接口使用示例
-- 1. 查询 Lua 虚拟机内存(默认)
local total_lua, used_lua, max_used_lua = rtos.meminfo("lua")
log.info("Lua Memory:",
"Total:", total_lua / 1024, "KB",
"Used:", used_lua / 1024, "KB",
"Peak:", max_used_lua / 1024, "KB")
-- 2. 查询系统内存
local total_sys, used_sys, max_used_sys = rtos.meminfo("sys")
log.info("System Memory:",
"Total:", total_sys / 1024, "KB",
"Used:", used_sys / 1024, "KB",
"Peak:", max_used_sys / 1024, "KB")
-- 3. 查询 PSRAM 内存(如果支持)
local total_psram, used_psram, max_used_psram = rtos.meminfo("psram")
if total_psram and total_psram > 0 then
log.info("PSRAM Memory:",
"Total:", total_psram / 1024, "KB",
"Used:", used_psram / 1024, "KB",
"Peak:", max_used_psram / 1024, "KB")
end
内存区域与物理内存关系
不同的芯片平台、不同的固件编译配置下,内存的分配和使用方式存在显著差异。理解这一点,关键在于分清物理内存和逻辑内存。

物理内存和逻辑内存的区分
1. 物理内存类型
我们用大写的 SRAM/PSRAM 来代表物理内存。
- SRAM:静态随机存取存储器。访问速度快,但容量通常较小。在芯片中一定存在,但不一定会全部开放给用户层的 Lua 脚本使用。
- PSRAM:外接的伪静态随机存取存储器。访问速度相对较慢,但容量可以做得更大。它不一定存在于所有模组上,即使存在,也可能需要特定配置才能启用。
简单从硬件角度看:SRAM 更快但容量小,PSRAM 稍慢但容量大。
2. 逻辑内存类型(用户可见)
sys、psram、lua 是 LuatOS 暴露给用户的、逻辑上的内存分配布局,方便开发者理解和监控。
- 虚拟机内存(“lua”):Lua 虚拟机使用的内存区域,包括脚本中的变量、函数、表、字符串等。
- 系统内存(“sys”):系统级内存区域,用于 FreeRTOS 任务栈、驱动缓冲区、内核堆等。
- psram内存(“psram”):专门管理的 PSRAM 区域,通常用于图片缓存、音频数据等大容量临时存储。
不同平台的差异
逻辑内存与物理内存的对应关系,因平台和编译配置的不同而各异。下表清晰地列出了主流平台的差异:

例如,在 Air780EPM/Air780EHM/Air8000 系列上,lua、sys、psram 区域都位于物理 PSRAM 上(sys 和 psram 统计的是同一块内存)。而在 Air780EPV 上,lua 区域可能在 SRAM 也可能在 PSRAM(取决于编译配置),sys 区域则在 SRAM 上。
以上就是 LuatOS 内存分配机制的核心内容。现在再回头看开头的疑问:“AirUI 这么流畅,会不会很吃内存?” 答案已经清晰——只要内存分得巧,系统流畅性与内存占用从来不是非此即彼的矛盾。LuatOS 通过精细的逻辑划分,在保障系统核心稳定的前提下,为上层应用提供了充裕且可控的内存空间。

理解内存布局是高效开发的第一步。后续我们将深入 Lua 垃圾回收(GC)的工作原理,并针对 Zbuff、UART、MQTT 等常用功能进行内存使用分析,手把手教你排查和优化内存问题。欢迎在云栈社区持续关注相关技术讨论。