Program Size: Code=189906 RO-data=31078 RW-data=636 ZI-data=58604一、先明确核心规则
Keil 编译输出的Program Size中,每个字段的单位是字节(Byte),计算核心是区分「Flash 占用」和「RAM 占用」,这是嵌入式中最关键的两个维度:
| 字段 | 含义 | 存储介质 | 计算公式(核心) |
|---|---|---|---|
| Code | 可执行代码段 | Flash | 独立计算(仅占 Flash) |
| RO-data | 只读数据段(常量) | Flash | 独立计算(仅占 Flash) |
| RW-data | 初始化非 0 的全局变量 | Flash→RAM | 占 Flash(存储初始值)+ 占 RAM(运行时) |
| ZI-data | 未初始化 / 初始化为 0 的变量 | RAM | 仅占 RAM(运行时) |
二、分步计算(以你的数据为例)
你的数据:Code=189906、RO-data=31078、RW-data=636、ZI-data=58604
1. 计算 Flash 总占用(程序烧录到 Flash 的大小)
Flash 需要存储「代码 + 只读常量 + RW-data 的初始值」,公式:
Flash占用 = Code + RO-data + RW-data代入数值:
Flash占用 = 189906 + 31078 + 636 = 221620 字节换算成更易读的单位(1KB=1024Byte):
221620 ÷ 1024 ≈ 216.43 KB✅ 结论:程序烧录后占用 Flash 约 216.43KB,远小于 STM32F407VET6 的 512KB Flash,无溢出风险。
2. 计算 RAM 总占用(程序运行时占用的内存)
RAM 需要存储「RW-data 的运行时值 + ZI-data 的零初始化数据」,公式:
RAM占用 = RW-data + ZI-data代入数值:
RAM占用 = 636 + 58604 = 59240 字节换算单位:
59240 ÷ 1024 ≈ 57.85 KB✅ 结论:程序运行时占用 RAM 约 57.85KB,远小于 STM32F407VET6 的 192KB RAM,剩余 RAM 可用于 LVGL 缓存、业务数据等。
3. 额外验证(可选)
- RO-data 换算:31078 ÷ 1024 ≈ 30.35 KB(只读常量占用 Flash);
- Code 换算:189906 ÷ 1024 ≈ 185.46 KB(纯代码占用 Flash);
三、关键补充(避免误解)
- 单位陷阱:Keil 输出的数值是「字节」,不是 KB!新手容易直接把 189906 当成 189KB,实际是 189906÷1024≈185.46KB;
- RW-data 的双重占用:RW-data 既占 Flash(存储初始值,比如
int a=10;的 10 存在 Flash),又占 RAM(运行时 a 的数值存在 RAM),所以计算 Flash 时要加,计算 RAM 时也要加; - ZI-data 不占 Flash:ZI-data 是 “零初始化数据”,程序启动时由系统自动清零,无需在 Flash 中存储初始值,仅占 RAM;
- 实际可用 RAM:计算出的 57.85KB 是「静态占用」,LVGL 的动态缓存(如显示缓冲区)、栈(Stack)、堆(Heap)会额外占用 RAM,需确保总和 < 192KB。
四、快速换算工具(懒人版)
可以用以下公式快速估算:
Flash(KB) = (Code + RO-data + RW-data) / 1024 RAM(KB) = (RW-data + ZI-data) / 1024代入你的数据:
- Flash = (189906+31078+636)/1024 = 221620/1024 ≈ 216.43 KB
- RAM = (636+58604)/1024 = 59240/1024 ≈ 57.85 KB
总结:你的程序在 Flash 和 RAM 上的占用都远低于 STM32F407VET6 的硬件上限,资源充足,无需担心溢出问题。
结合你提供的Program Size: Code=189906 RO-data=31078 RW-data=636 ZI-data=58604,下面不仅给出精确计算过程,还会明确每个字段对应的存储区域(Flash/RAM)、数据类型和读写属性,彻底讲清 “每个数值存在哪里、为什么、怎么算”。
一、核心前提(先记牢)
| 字段 | 单位 | 核心存储区域(烧录 / 运行) | 数据类型 | 读写属性 |
|---|---|---|---|---|
| Code | 字节 | 仅 Flash(烧录 + 永久存储) | 可执行指令(函数、逻辑) | 只读 |
| RO-data | 字节 | 仅 Flash(烧录 + 永久存储) | 只读常量(字符串、const 变量) | 只读 |
| RW-data | 字节 | Flash(存初始值)+ RAM(运行时) | 初始化非 0 的全局 / 静态变量 | 读写 |
| ZI-data | 字节 | 仅 RAM(仅运行时占用) | 未初始化 / 初始化为 0 的全局 / 静态变量 | 读写 |
二、分步计算(含存储区域说明)
1. 第一步:计算「Flash 总占用」(程序烧录到芯片 Flash 的大小)
Flash 是 STM32 的 “只读存储区”,断电不丢失,用于存放烧录时需要固化的所有数据(代码、常量、RW-data 的初始值)。公式:Flash总占用 = Code + RO-data + RW-data代入你的数值:
Flash总占用 = 189906 + 31078 + 636 = 221620 字节 换算成KB(1KB=1024字节):221620 ÷ 1024 ≈ 216.43 KB- 各部分在 Flash 中的占比:
- Code:189906 字节(≈185.46 KB)→ Flash 中存
main()、lv_task_handler()等函数的机器指令; - RO-data:31078 字节(≈30.35 KB)→ Flash 中存
const char str[] = "LVGL测试"、#define MAX_VAL 100等只读常量; - RW-data:636 字节(≈0.62 KB)→ Flash 中存
int num = 10;(非 0 初始化)的初始值10(运行时会复制到 RAM)。
- Code:189906 字节(≈185.46 KB)→ Flash 中存
2. 第二步:计算「RAM 总占用」(程序运行时占用的内存大小)
RAM 是 STM32 的 “读写存储区”,断电丢失,用于存放运行时可修改的数据(RW-data 的实时值、ZI-data 的零初始化数据)。公式:RAM总占用 = RW-data + ZI-data代入你的数值:
RAM总占用 = 636 + 58604 = 59240 字节 换算成KB:59240 ÷ 1024 ≈ 57.85 KB- 各部分在 RAM 中的占比:
- RW-data:636 字节 → RAM 中存
int num = 10;运行时的实时值(比如程序中修改为 20,RAM 中就存 20); - ZI-data:58604 字节(≈57.23 KB)→ RAM 中存
static uint32_t cnt;(未初始化)、int flag = 0;(初始化为 0),程序启动时系统会自动将这部分区域清零。
- RW-data:636 字节 → RAM 中存
3. 第三步:验证资源是否充足(STM32F407VET6)
- Flash 总容量:512 KB → 216.43 KB < 512 KB(剩余≈295.57 KB,可存更多代码 / 图片 / 字体);
- RAM 总容量:192 KB → 57.85 KB < 192 KB(剩余≈134.15 KB,可用于 LVGL 显示缓存、栈 / 堆、业务数据)。
三、关键补充(避免误解)
ZI-data 为什么不占 Flash?ZI-data 是 “零初始化数据”,程序启动时 STM32 的启动文件(
startup_stm32f407xx.s)会自动把这部分 RAM 区域清零,无需在 Flash 中存储初始值(存 “0” 没有意义),所以仅占用 RAM、不占 Flash。RW-data 的 “双重占用” 怎么理解?比如定义
int a = 10;:- 烧录时:
10这个初始值存在 Flash(占 RW-data 的 1 份空间); - 运行时:CPU 把 Flash 中的
10复制到 RAM,后续修改a=20只改 RAM 中的值,Flash 中的初始值不变。
- 烧录时:
栈(Stack)/ 堆(Heap)没算进去?你看到的
ZI-data仅包含 “全局 / 静态变量”,程序运行时的栈(函数局部变量、函数调用)、堆(malloc动态分配)会额外占用 RAM,但 Keil 的Program Size不会统计这部分(属于运行时动态占用)。比如你给 LVGL 分配的显示缓存lv_color_t buf[480*10](约 9.6 KB),属于堆 / 全局变量,会算进 ZI-data/RW-data;而函数内的局部变量int tmp;属于栈,不会体现在当前数值中。
四、总结(一句话记全)
| 计算目标 | 公式 | 数值(字节) | 数值(KB) | 存储区域 |
|---|---|---|---|---|
| Flash 总占用 | Code + RO-data + RW-data | 221620 | ≈216.43 | 仅 Flash |
| RAM 总占用 | RW-data + ZI-data | 59240 | ≈57.85 | 仅 RAM |
| 纯代码占用 | Code | 189906 | ≈185.46 | 仅 Flash |
| 只读常量占用 | RO-data | 31078 | ≈30.35 | 仅 Flash |
你的程序资源占用非常健康,Flash 和 RAM 都有大量剩余,后续可以放心添加 LVGL 的复杂界面、更多字体 / 图片,或扩展业务逻辑。