docs(部署): 删任务栈副本表改指针;纠 CCM/FPU 事实并刷新配图基线
范围:AGENTS.md 一处指针、部署环境要求 §2.2/§3.1/§3.3、RAM 方案 6 处现状 数字、内存配图生成器 + 3 张 SVG、两份报告脚本的行尾与路径修正、新增两份 .map/.htm 数据快照。未改任何 .c/.h(仍跑 @build 复核:0 错误 0 警告)。 部署环境要求.md - §3.3 删"任务栈预算"副本表、改为指针:该表已缺 adcTask/iec104Task/ protectTask,defaultTask/timeSyncTask 两值停在旧数,注释却写"由 gen_task_table.py 同源"——该钩子的校验面只有 README.md / AGENTS.md 两处受管块,抄出来的副本没有门禁、改栈后必漂。指针指向 Src/freertos.c + 两份受管表 + RAM 方案 §2.3/§0.6,并留一条"别再抄"的成因说明。 - §2.2 链接布局补 `RW_CCM 0x10000000`(scatter 给 0x0000FF00 = 65,280 B, 2026-10-11 起承载 FreeRTOS 堆;另有 256 B UNINIT_CCM 尾区),写明 CCM 不可 DMA。原文"SRAM3/CCM 故意未映射"与 STM32F407-Demo.sct 直接矛盾。 - §3.1 MCU 行更正为**单精度 FPU(VFPv4-SP,无硬件双精度)、无 TrustZone** (原写"双精度 FPU / TrustZone"是芯片事实错误,也正是报告 F-6 双精度软 浮点被长期误判的土壤);SRAM 行改为"两块都在用,仅 SRAM3 未映射"。 - §3.3 资源预算表补 CCM 行,并把"主 SRAM 125,104 B / 95.4% / 极度紧张" 更正为 75,264 B / 57.4%(余 55,808 B);红线改标在 CCM(余 7,904 B)。 - 变更记录补 2026-10-22 行(含上一提交里的资源表刷新那一笔)。 AGENTS.md:任务表注里 "RAM使用分析与优化方案.md §1.4" 是**指错小节**——§1.4 确实 存在(该文档 §4「方案」下的阶段 1 子项,讲 lftpd 大局部缓冲静态化),但栈余量 台账在 §2.3(任务栈配置与实测峰值)与 §0.6(静态最坏链与判定),故改指这两处 再加 内存内容分配策略.md §6。根因是该文档里 §1(背景)与 §4 下的 1.1~1.5 同号 撞面,人和 doc-links(自引用放过)都会看错——本会话我上一轮就被它带错过一次。 配图与数据(draw-diagram 流程:改生成器顶部数据 → 重跑 → 逐文本核越界) - 新增 data/ram_report_20261022.md、data/stack_report_20261022.md;后者 运行时水位取自 2026-10-22 真机 [STACK] 心跳(8 任务高水位 + heap free=15,800 / min_ever=8,464),静态侧来自同日 .htm(全局最深链 3,024 B)。 - gen_memory_svg.py:三组图数据从 2026-09-21 / 10-10 快照换成 2026-10-22 实测;任务栈 6 → 9 行,堆总量 48KB → 56KB,判定 6/6 → 9/9 PASS,新增 AboveNormal 配色;Flash 子条改为"窄段不压字 + 下方四列图例";任务栈 画布 440 → 620 高。CCM 段总量按 scatter 用 65,280 B(与台账同口径)。 - 三张 SVG 重生成;用"CJK≈1.0em / 其余≈0.58em + 锚点"逐文本估算边界, 修掉 5 处文字越界/压字(生成器内置 ElementTree 自检亦通过)。 - ram_report.py / stack_report.py 两处工具性修正:write_text 未指定 newline 参数 → Windows 下把 data/ 快照写成 CRLF(与 .gitattributes 及既有快照 不符);stack_report 的 relative_to 在传相对 -i 时抛 ValueError,且会把 本机绝对路径写进入库快照 → 统一走 resolve+relative_to 的相对路径回退。 RAM 方案:6 处"当前状态"随 .map/[STACK] 更正——RW_IRAM1 89,168 → 75,264、 RW_CCM 49,184 → 57,376、FreeRTOS 堆 48KB → 56KB(两处)、CCM 余量 ~16KB → 7,904 B、min_ever 4,848 → 8,464 B、6 任务全过 → 9/9 PASS;S-1 历史句保留。 门禁:pre-commit 对全部改动文件 Passed(doc-links --sections-strict、 task-table、mem-numbers、mem-budget、id-check 增量拦截);字节卫生自查 BOM / CR / U+FFFD / 行尾空格全清。已提交本地,未推送。
This commit is contained in:
@@ -63,7 +63,7 @@
|
||||
| protectTask | 512 | Normal |
|
||||
<!-- TASK_TABLE:END -->
|
||||
|
||||
(实际值以 `Src/freertos.c` 为准,本表由 `scripts/gen_task_table.py` 生成、`task-table` 钩子校验;testTask 仅在启用测试套件时创建。FreeRTOS 堆已迁 CCM,任务栈不占 SRAM;**每次抬栈的实测最坏链与余量台账** → `docs/内存管理/RAM使用分析与优化方案.md` §1.4 与 `docs/内存管理/内存内容分配策略.md` §6)
|
||||
(实际值以 `Src/freertos.c` 为准,本表由 `scripts/gen_task_table.py` 生成、`task-table` 钩子校验;testTask 仅在启用测试套件时创建。FreeRTOS 堆已迁 CCM,任务栈不占 SRAM;**每次抬栈的实测最坏链与余量台账** → `docs/内存管理/RAM使用分析与优化方案.md` §2.3(任务栈配置与实测峰值)与 §0.6(静态最坏链与判定)、`docs/内存管理/内存内容分配策略.md` §6(容量台账))
|
||||
|
||||
## 铁律:源码编辑与编码
|
||||
|
||||
|
||||
+50
-35
@@ -1,4 +1,4 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 880 440" width="880" height="440" style="font-family:Consolas,'Courier New',monospace; font-size:12px; background:#fff">
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 880 620" width="880" height="620" style="font-family:Consolas,'Courier New',monospace; font-size:12px; background:#fff">
|
||||
<defs>
|
||||
<style>
|
||||
.title { font-size:14px; font-weight:bold; }
|
||||
@@ -7,45 +7,60 @@
|
||||
.bar-seg { stroke:#fff; stroke-width:0.5; }
|
||||
</style>
|
||||
</defs>
|
||||
<text x="440.0" y="22" text-anchor="middle" class="title">FreeRTOS 任务栈预算(48KB 堆,2026-09-21 已迁 CCM)</text>
|
||||
<text x="440.0" y="40" text-anchor="middle" class="legend-text" fill="#777">数据: 2026-10-10 @build + 开机/空闲实测(data/stack_report_20261010.md);最坏 = max(静态最坏链, 实测峰值)</text>
|
||||
<text x="440.0" y="22" text-anchor="middle" class="title">FreeRTOS 任务栈预算(9 任务;栈全部从 56KB FreeRTOS 堆分配,堆位于 CCM)</text>
|
||||
<text x="440.0" y="40" text-anchor="middle" class="legend-text" fill="#777">数据: 2026-10-22 @build + 同日真机 [STACK] 水位(data/stack_report_20261022.md);最坏 = max(静态最坏链, 实测峰值);判定线 = 余量 ≥ max(1024B ISR, 配置×30%)</text>
|
||||
<text x="190" y="54" class="legend-text" fill="#555">浅色条 = 分配栈 深色条 = 最坏占用(max(静态最坏, 实测峰值)) 下方文字 = 实测余量/判定</text>
|
||||
<text x="186" y="72" text-anchor="end" dominant-baseline="central" class="label" fill="#333">defaultTask</text>
|
||||
<rect class="bar-seg" x="190" y="64" width="162.5" height="16" fill="#BBDEFB" rx="3"/>
|
||||
<rect x="190" y="64" width="110.1" height="16" fill="#2196F3" rx="3"/>
|
||||
<text x="190" y="91" dominant-baseline="central" class="legend-text" fill="#333">配置 4096B | 实测峰值 2152B | 最坏 2776B | 余量 1320B (32%) <tspan fill="#2E7D32" font-weight="bold">PASS</tspan></text>
|
||||
<rect class="bar-seg" x="190" y="64" width="203.1" height="16" fill="#BBDEFB" rx="3"/>
|
||||
<rect x="190" y="64" width="120.0" height="16" fill="#2196F3" rx="3"/>
|
||||
<text x="190" y="91" dominant-baseline="central" class="legend-text" fill="#333">配置 5120B | 实测峰值 2164B | 最坏 3024B | 余量 2096B (40%) <tspan fill="#2E7D32" font-weight="bold">PASS</tspan></text>
|
||||
<text x="186" y="112" text-anchor="end" dominant-baseline="central" class="label" fill="#333">netTask</text>
|
||||
<rect class="bar-seg" x="190" y="104" width="152.3" height="16" fill="#BBDEFB" rx="3"/>
|
||||
<rect x="190" y="104" width="74.3" height="16" fill="#2196F3" rx="3"/>
|
||||
<text x="190" y="131" dominant-baseline="central" class="legend-text" fill="#333">配置 3840B | 实测峰值 920B | 最坏 1872B | 余量 1968B (51%) <tspan fill="#2E7D32" font-weight="bold">PASS</tspan></text>
|
||||
<rect x="190" y="104" width="75.9" height="16" fill="#2196F3" rx="3"/>
|
||||
<text x="190" y="131" dominant-baseline="central" class="legend-text" fill="#333">配置 3840B | 实测峰值 1116B | 最坏 1912B | 余量 1928B (50%) <tspan fill="#2E7D32" font-weight="bold">PASS</tspan></text>
|
||||
<text x="186" y="152" text-anchor="end" dominant-baseline="central" class="label" fill="#333">ftpTask</text>
|
||||
<rect class="bar-seg" x="190" y="144" width="162.5" height="16" fill="#BBDEFB" rx="3"/>
|
||||
<rect x="190" y="144" width="48.2" height="16" fill="#2196F3" rx="3"/>
|
||||
<text x="190" y="171" dominant-baseline="central" class="legend-text" fill="#333">配置 4096B | 实测峰值 740B | 最坏 1216B | 余量 2880B (70%) <tspan fill="#2E7D32" font-weight="bold">PASS</tspan></text>
|
||||
<text x="186" y="192" text-anchor="end" dominant-baseline="central" class="label" fill="#333">testTask</text>
|
||||
<rect class="bar-seg" x="190" y="184" width="325.0" height="16" fill="#FFE0B2" rx="3"/>
|
||||
<rect x="190" y="184" width="19.7" height="16" fill="#FF9800" rx="3"/>
|
||||
<text x="190" y="211" dominant-baseline="central" class="legend-text" fill="#333">配置 8192B | 实测峰值 496B | 最坏 496B | 余量 7696B (93%) <tspan fill="#2E7D32" font-weight="bold">PASS</tspan></text>
|
||||
<text x="186" y="232" text-anchor="end" dominant-baseline="central" class="label" fill="#333">uiTask</text>
|
||||
<rect class="bar-seg" x="190" y="224" width="650.0" height="16" fill="#FFE0B2" rx="3"/>
|
||||
<rect x="190" y="224" width="159.3" height="16" fill="#FF9800" rx="3"/>
|
||||
<text x="190" y="251" dominant-baseline="central" class="legend-text" fill="#333">配置 16384B | 实测峰值 4016B | 最坏 4016B | 余量 12368B (75%) <tspan fill="#2E7D32" font-weight="bold">PASS</tspan></text>
|
||||
<rect x="190" y="144" width="57.8" height="16" fill="#2196F3" rx="3"/>
|
||||
<text x="190" y="171" dominant-baseline="central" class="legend-text" fill="#333">配置 4096B | 实测峰值 756B | 最坏 1456B | 余量 2640B (64%) <tspan fill="#2E7D32" font-weight="bold">PASS</tspan></text>
|
||||
<text x="186" y="192" text-anchor="end" dominant-baseline="central" class="label" fill="#333">uiTask</text>
|
||||
<rect class="bar-seg" x="190" y="184" width="650.0" height="16" fill="#FFE0B2" rx="3"/>
|
||||
<rect x="190" y="184" width="160.8" height="16" fill="#FF9800" rx="3"/>
|
||||
<text x="190" y="211" dominant-baseline="central" class="legend-text" fill="#333">配置 16384B | 实测峰值 4052B | 最坏 4052B | 余量 12332B (75%) <tspan fill="#2E7D32" font-weight="bold">PASS</tspan></text>
|
||||
<text x="186" y="232" text-anchor="end" dominant-baseline="central" class="label" fill="#333">testTask</text>
|
||||
<rect class="bar-seg" x="190" y="224" width="325.0" height="16" fill="#FFE0B2" rx="3"/>
|
||||
<rect x="190" y="224" width="29.2" height="16" fill="#FF9800" rx="3"/>
|
||||
<text x="190" y="251" dominant-baseline="central" class="legend-text" fill="#333">配置 8192B | 实测峰值 736B | 最坏 736B | 余量 7456B (91%) <tspan fill="#2E7D32" font-weight="bold">PASS</tspan></text>
|
||||
<text x="186" y="272" text-anchor="end" dominant-baseline="central" class="label" fill="#333">timeSyncTask</text>
|
||||
<rect class="bar-seg" x="190" y="264" width="81.2" height="16" fill="#BBDEFB" rx="3"/>
|
||||
<rect x="190" y="264" width="40.6" height="16" fill="#2196F3" rx="3"/>
|
||||
<text x="190" y="291" dominant-baseline="central" class="legend-text" fill="#333">配置 2048B | 实测峰值 616B | 最坏 1024B | 余量 1024B (50%) <tspan fill="#2E7D32" font-weight="bold">PASS</tspan></text>
|
||||
<text x="186" y="314" text-anchor="end" dominant-baseline="central" class="label" fill="#333">idle</text>
|
||||
<rect class="bar-seg" x="190" y="308" width="20.3" height="12" fill="#90A4AE" rx="2"/>
|
||||
<text x="214.3125" y="314" dominant-baseline="central" class="legend-text" fill="#333">512B(未实测)</text>
|
||||
<text x="186" y="336" text-anchor="end" dominant-baseline="central" class="label" fill="#333">timer</text>
|
||||
<rect class="bar-seg" x="190" y="330" width="40.6" height="12" fill="#90A4AE" rx="2"/>
|
||||
<text x="234.625" y="336" dominant-baseline="central" class="legend-text" fill="#333">1024B(未实测)</text>
|
||||
<text x="190" y="360" class="label" fill="#555">堆总量: 49152B (48KB, RW_CCM) 任务栈合计: 38656B (37.8KB) + 内核栈 1536B</text>
|
||||
<text x="190" y="376" class="label" fill="#555">实测: free=8784B / min_ever=4848B(2026-09-21,含 FTP 负载) 判定: 6/6 PASS(余量 ≥ max(1024B, 配置×30%))</text>
|
||||
<rect x="190" y="400" width="10" height="10" fill="#2196F3" rx="2"/>
|
||||
<text x="204" y="408" class="legend-text" fill="#333">Normal 优先级</text>
|
||||
<rect x="320" y="400" width="10" height="10" fill="#FF9800" rx="2"/>
|
||||
<text x="334" y="408" class="legend-text" fill="#333">BelowNormal 优先级</text>
|
||||
<rect x="480" y="400" width="10" height="10" fill="#90A4AE" rx="2"/>
|
||||
<text x="494" y="408" class="legend-text" fill="#333">内核任务栈 (idle/timer)</text>
|
||||
<rect class="bar-seg" x="190" y="264" width="101.6" height="16" fill="#BBDEFB" rx="3"/>
|
||||
<rect x="190" y="264" width="50.1" height="16" fill="#2196F3" rx="3"/>
|
||||
<text x="190" y="291" dominant-baseline="central" class="legend-text" fill="#333">配置 2560B | 实测峰值 616B | 最坏 1264B | 余量 1296B (50%) <tspan fill="#2E7D32" font-weight="bold">PASS</tspan></text>
|
||||
<text x="186" y="312" text-anchor="end" dominant-baseline="central" class="label" fill="#333">adcTask</text>
|
||||
<rect class="bar-seg" x="190" y="304" width="101.6" height="16" fill="#C8E6C9" rx="3"/>
|
||||
<rect x="190" y="304" width="52.4" height="16" fill="#4CAF50" rx="3"/>
|
||||
<text x="190" y="331" dominant-baseline="central" class="legend-text" fill="#333">配置 2560B | 实测峰值 952B | 最坏 1320B | 余量 1240B (48%) <tspan fill="#2E7D32" font-weight="bold">PASS</tspan></text>
|
||||
<text x="186" y="352" text-anchor="end" dominant-baseline="central" class="label" fill="#333">iec104Task</text>
|
||||
<rect class="bar-seg" x="190" y="344" width="101.6" height="16" fill="#BBDEFB" rx="3"/>
|
||||
<rect x="190" y="344" width="57.8" height="16" fill="#2196F3" rx="3"/>
|
||||
<text x="190" y="371" dominant-baseline="central" class="legend-text" fill="#333">配置 2560B | 实测峰值 544B | 最坏 1456B | 余量 1104B (43%) <tspan fill="#2E7D32" font-weight="bold">PASS</tspan></text>
|
||||
<text x="186" y="392" text-anchor="end" dominant-baseline="central" class="label" fill="#333">protectTask</text>
|
||||
<rect class="bar-seg" x="190" y="384" width="81.2" height="16" fill="#BBDEFB" rx="3"/>
|
||||
<rect x="190" y="384" width="34.6" height="16" fill="#2196F3" rx="3"/>
|
||||
<text x="190" y="411" dominant-baseline="central" class="legend-text" fill="#333">配置 2048B | 实测峰值 828B | 最坏 872B | 余量 1176B (57%) <tspan fill="#2E7D32" font-weight="bold">PASS</tspan></text>
|
||||
<text x="186" y="434" text-anchor="end" dominant-baseline="central" class="label" fill="#333">idle</text>
|
||||
<rect class="bar-seg" x="190" y="428" width="20.3" height="12" fill="#90A4AE" rx="2"/>
|
||||
<text x="214.3125" y="434" dominant-baseline="central" class="legend-text" fill="#333">512B(未实测)</text>
|
||||
<text x="186" y="456" text-anchor="end" dominant-baseline="central" class="label" fill="#333">timer</text>
|
||||
<rect class="bar-seg" x="190" y="450" width="40.6" height="12" fill="#90A4AE" rx="2"/>
|
||||
<text x="234.625" y="456" dominant-baseline="central" class="legend-text" fill="#333">1024B(未实测)</text>
|
||||
<text x="190" y="480" class="label" fill="#555">堆总量: 57344B(configTOTAL_HEAP_SIZE=56KB,位于 RW_CCM) 任务栈合计: 47360B(含 testTask 8192B)</text>
|
||||
<text x="190" y="496" class="label" fill="#555">产品构建 8 任务栈 = 39168B + 内核栈 1536B 实测: free=15800B / min_ever=8464B(2026-10-22)</text>
|
||||
<text x="190" y="512" class="label" fill="#555">判定: 9/9 PASS(testTask 无实测,取静态最坏链)</text>
|
||||
<rect x="190" y="536" width="10" height="10" fill="#2196F3" rx="2"/>
|
||||
<text x="204" y="544" class="legend-text" fill="#333">Normal 优先级</text>
|
||||
<rect x="320" y="536" width="10" height="10" fill="#FF9800" rx="2"/>
|
||||
<text x="334" y="544" class="legend-text" fill="#333">BelowNormal 优先级</text>
|
||||
<rect x="490" y="536" width="10" height="10" fill="#4CAF50" rx="2"/>
|
||||
<text x="504" y="544" class="legend-text" fill="#333">AboveNormal 优先级(adcTask)</text>
|
||||
<rect x="710" y="536" width="10" height="10" fill="#90A4AE" rx="2"/>
|
||||
<text x="724" y="544" class="legend-text" fill="#333">内核栈 idle/timer</text>
|
||||
</svg>
|
||||
|
||||
|
Before Width: | Height: | Size: 5.1 KiB After Width: | Height: | Size: 6.9 KiB |
+43
-28
@@ -7,32 +7,47 @@
|
||||
.bar-seg { stroke:#fff; stroke-width:0.5; }
|
||||
</style>
|
||||
</defs>
|
||||
<text x="410.0" y="24" text-anchor="middle" class="title">Flash (1MB) 使用布局 — 2026-09-21 @build</text>
|
||||
<rect class="bar-seg" x="60" y="50" width="165.8" height="40" fill="#2196F3" rx="2"/>
|
||||
<text x="142.9" y="70.0" text-anchor="middle" dominant-baseline="central" class="label" fill="#000">代码段 (Code) 229.5KB</text>
|
||||
<rect class="bar-seg" x="225.8270263671875" y="50" width="9.8" height="40" fill="#4CAF50" rx="2"/>
|
||||
<text x="239.6" y="70.0" text-anchor="start" dominant-baseline="central" class="legend-text" fill="#333">只读数据 (RO) 13.5KB</text>
|
||||
<rect class="bar-seg" x="235.5828857421875" y="50" width="564.0" height="40" fill="#E0E0E0" rx="2"/>
|
||||
<text x="517.6" y="70.0" text-anchor="middle" dominant-baseline="central" class="label" fill="#000">Flash 空闲 780.4KB</text>
|
||||
<text x="60" y="108" class="label" fill="#333">已用: 243.6KB (23.8%) 空闲: 780.4KB (76.2%) 总量: 1024KB</text>
|
||||
<text x="60" y="124" class="label" fill="#555">代码段明细 (229.5KB)</text>
|
||||
<rect class="bar-seg" x="60" y="130" width="308.6" height="24" fill="#4CAF50" rx="2"/>
|
||||
<text x="214.3" y="142.0" text-anchor="middle" dominant-baseline="central" class="label" fill="#000">LVGL 库 95.7KB</text>
|
||||
<rect class="bar-seg" x="368.6272640610105" y="130" width="107.4" height="24" fill="#2196F3" rx="2"/>
|
||||
<text x="422.3" y="142.0" text-anchor="middle" dominant-baseline="central" class="label" fill="#000">应用代码/UI 33.3KB</text>
|
||||
<rect class="bar-seg" x="476.0484475010214" y="130" width="25.7" height="24" fill="#9C27B0" rx="2"/>
|
||||
<text x="505.7" y="142.0" text-anchor="start" dominant-baseline="central" class="legend-text" fill="#333">FatFS 8.0KB</text>
|
||||
<rect class="bar-seg" x="501.7023015116438" y="130" width="15.7" height="24" fill="#FF9800" rx="2"/>
|
||||
<text x="521.4" y="142.0" text-anchor="start" dominant-baseline="central" class="legend-text" fill="#333">dhara / FTL 4.9KB</text>
|
||||
<rect class="bar-seg" x="517.3919038540107" y="130" width="50.4" height="24" fill="#607D8B" rx="2"/>
|
||||
<text x="542.6" y="136.0" text-anchor="middle" dominant-baseline="central" class="label" fill="#000">HAL 驱动</text>
|
||||
<text x="542.6" y="148.0" text-anchor="middle" dominant-baseline="central" class="label" fill="#000">15.6KB</text>
|
||||
<rect class="bar-seg" x="567.7800285986655" y="130" width="31.9" height="24" fill="#00BCD4" rx="2"/>
|
||||
<text x="603.7" y="142.0" text-anchor="start" dominant-baseline="central" class="legend-text" fill="#333">FreeRTOS 内核 9.9KB</text>
|
||||
<rect class="bar-seg" x="599.6883085932182" y="130" width="8.6" height="24" fill="#F44336" rx="2"/>
|
||||
<text x="612.3" y="142.0" text-anchor="start" dominant-baseline="central" class="legend-text" fill="#333">CH395F 网络 2.7KB</text>
|
||||
<rect class="bar-seg" x="608.3109764401472" y="130" width="13.3" height="24" fill="#795548" rx="2"/>
|
||||
<text x="625.6" y="142.0" text-anchor="start" dominant-baseline="central" class="legend-text" fill="#333">C 库 (microlib) 4.1KB</text>
|
||||
<rect class="bar-seg" x="621.6323369195153" y="130" width="178.4" height="24" fill="#E0E0E0" rx="2"/>
|
||||
<text x="710.8" y="142.0" text-anchor="middle" dominant-baseline="central" class="label" fill="#000">其他 (长尾) 55.3KB</text>
|
||||
<text x="410.0" y="24" text-anchor="middle" class="title">Flash (1MB) 使用布局 — 2026-10-22 @build</text>
|
||||
<rect class="bar-seg" x="60" y="50" width="150.5" height="40" fill="#2196F3" rx="2"/>
|
||||
<text x="135.2" y="70.0" text-anchor="middle" dominant-baseline="central" class="label" fill="#000">代码段 (Code) 208.2KB</text>
|
||||
<rect class="bar-seg" x="210.45082092285156" y="50" width="13.1" height="40" fill="#4CAF50" rx="2"/>
|
||||
<text x="227.6" y="70.0" text-anchor="start" dominant-baseline="central" class="legend-text" fill="#333">只读数据 (RO) 18.1KB</text>
|
||||
<rect class="bar-seg" x="223.56307983398438" y="50" width="575.6" height="40" fill="#E0E0E0" rx="2"/>
|
||||
<text x="511.4" y="70.0" text-anchor="middle" dominant-baseline="central" class="label" fill="#000">Flash 空闲 796.5KB</text>
|
||||
<text x="60" y="108" class="label" fill="#333">已用: 227.5KB (22.2%) 空闲: 796.5KB (77.8%) ER_IROM1(Code+RO): 226.3KB (22.1%) 总量: 1MB (= ROM 合计口径)</text>
|
||||
<text x="60" y="124" class="label" fill="#555">Code + RO 分布(ER_IROM1 226.3KB,按 .map 对象归类)</text>
|
||||
<rect class="bar-seg" x="60" y="130" width="280.0" height="24" fill="#4CAF50" rx="2"/>
|
||||
<text x="200.0" y="142.0" text-anchor="middle" dominant-baseline="central" class="label" fill="#000">85.7KB</text>
|
||||
<rect class="bar-seg" x="340.0319284802044" y="130" width="182.0" height="24" fill="#2196F3" rx="2"/>
|
||||
<text x="431.0" y="142.0" text-anchor="middle" dominant-baseline="central" class="label" fill="#000">55.7KB</text>
|
||||
<rect class="bar-seg" x="522.0593869731802" y="130" width="81.9" height="24" fill="#F44336" rx="2"/>
|
||||
<text x="563.0" y="142.0" text-anchor="middle" dominant-baseline="central" class="label" fill="#000">25.1KB</text>
|
||||
<rect class="bar-seg" x="603.9623243933589" y="130" width="57.1" height="24" fill="#607D8B" rx="2"/>
|
||||
<text x="632.5" y="142.0" text-anchor="middle" dominant-baseline="central" class="label" fill="#000">17.5KB</text>
|
||||
<rect class="bar-seg" x="661.0376756066412" y="130" width="34.8" height="24" fill="#FF9800" rx="2"/>
|
||||
<rect class="bar-seg" x="695.8620689655173" y="130" width="34.4" height="24" fill="#00BCD4" rx="2"/>
|
||||
<rect class="bar-seg" x="730.2234993614305" y="130" width="27.0" height="24" fill="#9C27B0" rx="2"/>
|
||||
<rect class="bar-seg" x="757.2605363984676" y="130" width="17.5" height="24" fill="#795548" rx="2"/>
|
||||
<rect class="bar-seg" x="774.7765006385698" y="130" width="1.5" height="24" fill="#B0BEC5" rx="2"/>
|
||||
<rect class="bar-seg" x="776.2707535121331" y="130" width="23.7" height="24" fill="#E0E0E0" rx="2"/>
|
||||
<rect x="60" y="167" width="10" height="10" fill="#4CAF50" rx="2"/>
|
||||
<text x="74" y="176" class="legend-text" fill="#333">LVGL 库 85.7KB</text>
|
||||
<rect x="255" y="167" width="10" height="10" fill="#2196F3" rx="2"/>
|
||||
<text x="269" y="176" class="legend-text" fill="#333">应用代码/UI 55.7KB</text>
|
||||
<rect x="450" y="167" width="10" height="10" fill="#F44336" rx="2"/>
|
||||
<text x="464" y="176" class="legend-text" fill="#333">CH395F+FTP 25.1KB</text>
|
||||
<rect x="645" y="167" width="10" height="10" fill="#607D8B" rx="2"/>
|
||||
<text x="659" y="176" class="legend-text" fill="#333">HAL 驱动 17.5KB</text>
|
||||
<rect x="60" y="183" width="10" height="10" fill="#FF9800" rx="2"/>
|
||||
<text x="74" y="192" class="legend-text" fill="#333">dhara / FTL 10.7KB</text>
|
||||
<rect x="255" y="183" width="10" height="10" fill="#00BCD4" rx="2"/>
|
||||
<text x="269" y="192" class="legend-text" fill="#333">FreeRTOS 内核 10.5KB</text>
|
||||
<rect x="450" y="183" width="10" height="10" fill="#9C27B0" rx="2"/>
|
||||
<text x="464" y="192" class="legend-text" fill="#333">FatFS 8.3KB</text>
|
||||
<rect x="645" y="183" width="10" height="10" fill="#795548" rx="2"/>
|
||||
<text x="659" y="192" class="legend-text" fill="#333">C 库 (microlib) 5.4KB</text>
|
||||
<rect x="60" y="199" width="10" height="10" fill="#B0BEC5" rx="2"/>
|
||||
<text x="74" y="208" class="legend-text" fill="#333">startup 0.5KB</text>
|
||||
<rect x="255" y="199" width="10" height="10" fill="#E0E0E0" rx="2"/>
|
||||
<text x="269" y="208" class="legend-text" fill="#333">其他 (长尾) 7.3KB</text>
|
||||
</svg>
|
||||
|
||||
|
Before Width: | Height: | Size: 3.5 KiB After Width: | Height: | Size: 4.4 KiB |
+36
-35
@@ -7,50 +7,51 @@
|
||||
.bar-seg { stroke:#fff; stroke-width:0.5; }
|
||||
</style>
|
||||
</defs>
|
||||
<text x="410.0" y="24" text-anchor="middle" class="title">SRAM (192KB) 使用布局 — 2026-09-21 @build</text>
|
||||
<text x="410.0" y="24" text-anchor="middle" class="title">SRAM (192KB) 使用布局 — 2026-10-22 @build</text>
|
||||
<text x="60" y="42" class="label" fill="#555">主 SRAM RW_IRAM1 @0x20000000(128KB,DMA 可达)</text>
|
||||
<rect class="bar-seg" x="60" y="50" width="234.1" height="44" fill="#4CAF50" rx="2"/>
|
||||
<text x="177.0" y="72.0" text-anchor="middle" dominant-baseline="central" class="label" fill="#000">LVGL</text>
|
||||
<rect class="bar-seg" x="294.0728759765625" y="50" width="76.4" height="44" fill="#FF9800" rx="2"/>
|
||||
<text x="332.3" y="72.0" text-anchor="middle" dominant-baseline="central" class="label" fill="#000">UI</text>
|
||||
<rect class="bar-seg" x="370.47119140625" y="50" width="49.8" height="44" fill="#9C27B0" rx="2"/>
|
||||
<rect class="bar-seg" x="420.2215576171875" y="50" width="30.1" height="44" fill="#8BC34A" rx="2"/>
|
||||
<rect class="bar-seg" x="450.279541015625" y="50" width="28.3" height="44" fill="#00BCD4" rx="2"/>
|
||||
<rect class="bar-seg" x="478.5986328125" y="50" width="25.1" height="44" fill="#F44336" rx="2"/>
|
||||
<rect class="bar-seg" x="503.6940002441406" y="50" width="7.2" height="44" fill="#607D8B" rx="2"/>
|
||||
<rect class="bar-seg" x="510.9205627441406" y="50" width="5.8" height="44" fill="#795548" rx="2"/>
|
||||
<rect class="bar-seg" x="516.7018127441406" y="50" width="6.5" height="44" fill="#9E9E9E" rx="2"/>
|
||||
<rect class="bar-seg" x="523.22265625" y="50" width="276.8" height="44" fill="#E0E0E0" rx="2"/>
|
||||
<text x="661.6" y="72.0" text-anchor="middle" dominant-baseline="central" class="label" fill="#000">free</text>
|
||||
<text x="60" y="112" class="label" fill="#333">已用: 82048B (62.6%) 空闲: 49024B (37.4%) 总量: 128KB</text>
|
||||
<text x="60" y="136" class="label" fill="#555">CCM RW_CCM @0x10000000(64KB,仅 CPU 可达,DMA 不可达)</text>
|
||||
<rect class="bar-seg" x="60" y="144" width="277.7" height="44" fill="#2196F3" rx="2"/>
|
||||
<text x="198.8" y="166.0" text-anchor="middle" dominant-baseline="central" class="label" fill="#000">heap</text>
|
||||
<rect class="bar-seg" x="337.6806640625" y="144" width="92.3" height="44" fill="#E0E0E0" rx="2"/>
|
||||
<text x="383.8" y="166.0" text-anchor="middle" dominant-baseline="central" class="label" fill="#000">free</text>
|
||||
<text x="60" y="206" class="label" fill="#333">已用: 49184B (75.0%) 空闲: 16352B (25.0%) 总量: 64KB</text>
|
||||
<rect class="bar-seg" x="60" y="50" width="95.3" height="44" fill="#4CAF50" rx="2"/>
|
||||
<text x="107.6" y="72.0" text-anchor="middle" dominant-baseline="central" class="label" fill="#000">LVGL 池 16KB</text>
|
||||
<rect class="bar-seg" x="155.2777099609375" y="50" width="76.5" height="44" fill="#FF9800" rx="2"/>
|
||||
<text x="193.5" y="72.0" text-anchor="middle" dominant-baseline="central" class="label" fill="#000">UI</text>
|
||||
<rect class="bar-seg" x="231.75506591796875" y="50" width="47.7" height="44" fill="#8BC34A" rx="2"/>
|
||||
<text x="255.6" y="72.0" text-anchor="middle" dominant-baseline="central" class="label" fill="#000">lftpd</text>
|
||||
<rect class="bar-seg" x="279.40521240234375" y="50" width="39.7" height="44" fill="#9C27B0" rx="2"/>
|
||||
<rect class="bar-seg" x="319.12872314453125" y="50" width="29.6" height="44" fill="#F44336" rx="2"/>
|
||||
<rect class="bar-seg" x="348.7689208984375" y="50" width="9.7" height="44" fill="#00BCD4" rx="2"/>
|
||||
<rect class="bar-seg" x="358.502197265625" y="50" width="5.8" height="44" fill="#795548" rx="2"/>
|
||||
<rect class="bar-seg" x="364.283447265625" y="50" width="120.2" height="44" fill="#9E9E9E" rx="2"/>
|
||||
<text x="424.4" y="72.0" text-anchor="middle" dominant-baseline="central" class="label" fill="#000">other</text>
|
||||
<rect class="bar-seg" x="484.4476318359375" y="50" width="315.1" height="44" fill="#E0E0E0" rx="2"/>
|
||||
<text x="642.0" y="72.0" text-anchor="middle" dominant-baseline="central" class="label" fill="#000">free</text>
|
||||
<text x="60" y="112" class="label" fill="#333">已用: 75264B (57.4%) 空闲: 55808B (42.6%) 总量: 128KB</text>
|
||||
<text x="60" y="136" class="label" fill="#555">CCM RW_CCM @0x10000000(段 65,280 B;仅 CPU 可达、DMA 不可达 → R2/R3)</text>
|
||||
<rect class="bar-seg" x="60" y="144" width="323.9" height="44" fill="#2196F3" rx="2"/>
|
||||
<text x="222.0" y="166.0" text-anchor="middle" dominant-baseline="central" class="label" fill="#000">FreeRTOS 堆</text>
|
||||
<rect class="bar-seg" x="383.9306640625" y="144" width="44.6" height="44" fill="#E0E0E0" rx="2"/>
|
||||
<text x="406.2" y="166.0" text-anchor="middle" dominant-baseline="central" class="label" fill="#000">free</text>
|
||||
<text x="60" y="206" class="label" fill="#333">已用: 57376B (87.9%) 空闲: 7904B (12.1%) 总量: 63.75KB(+256 B UNINIT_CCM 尾区)——CCM 是当前全局卡点</text>
|
||||
<rect x="60" y="226" width="12" height="12" fill="#4CAF50" rx="2"/>
|
||||
<text x="76" y="236" class="legend-text" fill="#333">主SRAM LVGL: 40.5KB (31.6%)</text>
|
||||
<text x="76" y="236" class="legend-text" fill="#333">主SRAM LVGL 池 16KB: 16.5KB (12.9%)</text>
|
||||
<rect x="60" y="242" width="12" height="12" fill="#FF9800" rx="2"/>
|
||||
<text x="76" y="252" class="legend-text" fill="#333">主SRAM UI: 13.2KB (10.3%)</text>
|
||||
<rect x="60" y="258" width="12" height="12" fill="#9C27B0" rx="2"/>
|
||||
<text x="76" y="268" class="legend-text" fill="#333">主SRAM FTL/BBT: 8.6KB (6.7%)</text>
|
||||
<rect x="60" y="274" width="12" height="12" fill="#8BC34A" rx="2"/>
|
||||
<text x="76" y="284" class="legend-text" fill="#333">主SRAM lftpd: 5.2KB (4.1%)</text>
|
||||
<rect x="60" y="290" width="12" height="12" fill="#00BCD4" rx="2"/>
|
||||
<text x="76" y="300" class="legend-text" fill="#333">主SRAM CMSIS: 4.9KB (3.8%)</text>
|
||||
<rect x="420" y="226" width="12" height="12" fill="#F44336" rx="2"/>
|
||||
<text x="436" y="236" class="legend-text" fill="#333">主SRAM NET: 4.3KB (3.4%)</text>
|
||||
<rect x="60" y="258" width="12" height="12" fill="#8BC34A" rx="2"/>
|
||||
<text x="76" y="268" class="legend-text" fill="#333">主SRAM lftpd: 8.2KB (6.4%)</text>
|
||||
<rect x="60" y="274" width="12" height="12" fill="#9C27B0" rx="2"/>
|
||||
<text x="76" y="284" class="legend-text" fill="#333">主SRAM FTL/BBT: 6.9KB (5.4%)</text>
|
||||
<rect x="60" y="290" width="12" height="12" fill="#F44336" rx="2"/>
|
||||
<text x="76" y="300" class="legend-text" fill="#333">主SRAM NET/CH395F: 5.1KB (4.0%)</text>
|
||||
<rect x="420" y="226" width="12" height="12" fill="#00BCD4" rx="2"/>
|
||||
<text x="436" y="236" class="legend-text" fill="#333">主SRAM CMSIS-RTOS: 1.7KB (1.3%)</text>
|
||||
<rect x="420" y="242" width="12" height="12" fill="#607D8B" rx="2"/>
|
||||
<text x="436" y="252" class="legend-text" fill="#333">主SRAM HAL: 1.2KB (1.0%)</text>
|
||||
<text x="436" y="252" class="legend-text" fill="#333">主SRAM HAL: 0.1KB (0.1%)</text>
|
||||
<rect x="420" y="258" width="12" height="12" fill="#795548" rx="2"/>
|
||||
<text x="436" y="268" class="legend-text" fill="#333">主SRAM C stack: 1.0KB (0.8%)</text>
|
||||
<rect x="420" y="274" width="12" height="12" fill="#9E9E9E" rx="2"/>
|
||||
<text x="436" y="284" class="legend-text" fill="#333">主SRAM other: 1.1KB (0.9%)</text>
|
||||
<text x="436" y="284" class="legend-text" fill="#333">主SRAM other: 20.8KB (16.2%)</text>
|
||||
<rect x="420" y="290" width="12" height="12" fill="#E0E0E0" rx="2"/>
|
||||
<text x="436" y="300" class="legend-text" fill="#333">主SRAM free: 47.9KB (37.4%)</text>
|
||||
<text x="436" y="300" class="legend-text" fill="#333">主SRAM free: 54.5KB (42.6%)</text>
|
||||
<rect x="60" y="322" width="12" height="12" fill="#2196F3" rx="2"/>
|
||||
<text x="76" y="332" class="legend-text" fill="#333">CCM heap: 48.0KB (75.0%)</text>
|
||||
<text x="76" y="332" class="legend-text" fill="#333">CCM FreeRTOS 堆: 56.0KB (87.9%)</text>
|
||||
<rect x="60" y="338" width="12" height="12" fill="#E0E0E0" rx="2"/>
|
||||
<text x="76" y="348" class="legend-text" fill="#333">CCM free: 16.0KB (25.0%)</text>
|
||||
<text x="76" y="348" class="legend-text" fill="#333">CCM free: 7.7KB (12.1%)</text>
|
||||
</svg>
|
||||
|
||||
|
Before Width: | Height: | Size: 4.5 KiB After Width: | Height: | Size: 4.8 KiB |
@@ -18,7 +18,7 @@
|
||||
- F407 另有 **64KB CCM RAM**:**已于 2026-09-21 启用**并把 FreeRTOS 堆迁入(§1.2)
|
||||
- 起步时没有任何运行时测量手段:不知道每个任务实际用了多少栈,改栈全靠拍脑袋
|
||||
|
||||
当前状态(**以 §2.1 受管快照为准**,由 `.map` 自动生成):RW_IRAM1 **89,168 / 131,072 B(68.0%)**、RW_CCM **49,184 / 65,280 B(75.3%)**。✅ **任务栈:2026-10-10 削链后 `defaultTask` 实测峰值 2152B/4096(余 47%)、静态最坏链 2776B(余 32%)**,6 任务全过 `stack_report.py` 判据(曾于 2026-10-04 升至 3664B/4096 ≈ 10%,登记为 S-1,现已销项),详见 §2.3 与"2026-10-10 复测"小节。
|
||||
当前状态(**以 §2.1 受管快照为准**,由 `.map` 自动生成;2026-10-22 `@build`):RW_IRAM1 **75,264 / 131,072 B(57.4%)**、RW_CCM **57,376 / 65,280 B(87.9%)**。✅ **任务栈:`stack_report.py` 9/9 PASS**(2026-10-22 静态最坏链 + 同日真机 `[STACK]` 水位,`defaultTask` 最坏 3024B/5120(余 40%)、`protectTask` 872B/2048(余 57%),见 `data/stack_report_20261022.md`);**卡点已从 SRAM1 移到 CCM**(余 7,904 B)。历史:`defaultTask` 曾于 2026-10-04 达 3664B/4096 ≈10%,登记为 S-1,2026-10-10 削链后销项(详见"2026-10-10 复测"小节)。
|
||||
|
||||
本方案三个目标:
|
||||
|
||||
@@ -121,7 +121,7 @@
|
||||
| idle(内核) | `configMINIMAL_STACK_SIZE=128` | 0.5KB | 空闲 | 未观测(未取句柄) |
|
||||
| timer(内核) | `configTIMER_TASK_STACK_DEPTH=256` | 1KB | 软定时器 | 未观测 |
|
||||
|
||||
> 任务栈全部从 FreeRTOS 堆(48KB,2026-09-21 已迁 CCM)分配。**"配置栈"列以 `Src/freertos.c` 为唯一来源;实测峰值/余量判定以 §0.6 的 `stack_report` 基线为准**(本表数值同步自该基线)。
|
||||
> 任务栈全部从 FreeRTOS 堆(56KB = `configTOTAL_HEAP_SIZE` 57,344 B;2026-09-21 迁 CCM、2026-10-12 扩容)分配。**"配置栈"列以 `Src/freertos.c` 为唯一来源;实测峰值/余量判定以 §0.6 的 `stack_report` 基线为准**(本表数值同步自该基线)。
|
||||
|
||||
### 2.4 动态分配点与隐患
|
||||
|
||||
@@ -135,12 +135,12 @@
|
||||
|---|---|---|
|
||||
| ① LVGL 内存池 40KB 对 1bpp 小屏菜单过大 | 40KB → **16KB ✅ 2026-10-15** | 高(目标 8~16KB;**开机实测 UI 仅用 ~3KB**,见 §2.6.2) |
|
||||
| ② 任务栈"往大了给",无实测依据 | 38,912 B(38 KB 现值,§2.6.1) | 高(§0.6 已有实测:uiTask 3.8/16KB、netTask 0.6/4KB → 阶段 1.3 缩减) |
|
||||
| ③ 64KB CCM 曾完全未利用,缓冲挤在主 SRAM | — | ✅ 2026-09-21 已启用(堆迁入 CCM),CCM 余量 ~16KB |
|
||||
| ③ 64KB CCM 曾完全未利用,缓冲挤在主 SRAM | — | ✅ 2026-09-21 已启用(堆迁入 CCM);2026-10-22 CCM 余量 7,904 B(**全局卡点**)|
|
||||
|
||||
量化补充(来源:2026-09-11 审计快照,口径与方法见 §8.4):
|
||||
|
||||
- 两池(FreeRTOS 48KB + LVGL 40KB)曾占主 SRAM 的 **68%**,是当时"SRAM 几乎耗尽(95.4%,余 5.8KB)"的直接原因;**堆迁 CCM 后该结构性压力已解除**(现 RW_IRAM1 66.4%,见 §2.1)
|
||||
- heap_4 **不合并相邻空闲块** → 长期运行需盯碎片,`min_ever`(现 4,848 B)是硬指标而非 `free`
|
||||
- 两池(FreeRTOS 48KB + LVGL 40KB)曾占主 SRAM 的 **68%**,是当时"SRAM 几乎耗尽(95.4%,余 5.8KB)"的直接原因;**堆迁 CCM 后该结构性压力已解除**(2026-10-22 RW_IRAM1 57.4%,见 §2.1)
|
||||
- heap_4 **不合并相邻空闲块** → 长期运行需盯碎片,`min_ever`(2026-10-22 实测 8,464 B,56KB 池)是硬指标而非 `free`
|
||||
- 未映射资源:SRAM3 64KB(scatter 未映射;clone 芯片可能无此区);CCM 已用
|
||||
- 曾经的三条中风险项:新任务无处安置(已缓解)、堆碎片(仍存)、栈溢出检测缺失 → **已于阶段 0 开启 `configCHECK_FOR_STACK_OVERFLOW=2` 并实测抓到过溢出**(§0.1)
|
||||
|
||||
@@ -148,7 +148,7 @@
|
||||
|
||||
### 2.6 堆 / LVGL 池 / C 库 / Flash 明细
|
||||
|
||||
#### 2.6.1 FreeRTOS 堆(48 KB;2026-09-21 已迁 CCM `RW_CCM`)
|
||||
#### 2.6.1 FreeRTOS 堆(56 KB;2026-09-21 已迁 CCM `RW_CCM`)
|
||||
|
||||
`configTOTAL_HEAP_SIZE = 49,152`(heap_4)。内部构成:
|
||||
|
||||
|
||||
@@ -0,0 +1,245 @@
|
||||
# STM32F4-Base RAM/Flash Usage Report
|
||||
|
||||
> Generated: 2026-10-22 12:06 Map: `STM32F407-Demo.map`
|
||||
|
||||
## 1. Grand Totals (全局总量)
|
||||
|
||||
| Metric | Value |
|
||||
|---|---|
|
||||
| Code (inc. data) | 213,188 B (208.2 KB) |
|
||||
| RO Data | 18,580 B (18.1 KB) |
|
||||
| RW Data (initialized) | 1,184 B (1.16 KB) |
|
||||
| ZI Data (zero-init) | 131,504 B (128.4 KB) |
|
||||
| **Total RO (Code + RO)** | **231,768 B (226.3 KB)** |
|
||||
| **Total RW (RW + ZI) = SRAM used** | **132,688 B (129.58 KB)** |
|
||||
| **Total ROM (Code + RO + RW init)** | **232,952 B (227.5 KB)** |
|
||||
|
||||
## 2. 执行区水位 (Execution Regions)
|
||||
|
||||
| Region | Base | Size | Max | Util% |
|
||||
|---|---|---|---|---|
|
||||
| ER_IROM1 | 0x08000000 | 231,768 B (226.34 KB) | 1,048,576 B (1024 KB) | 22.1% |
|
||||
| RW_CCM | 0x10000000 | 57,376 B (56.03 KB) | 65,280 B (64 KB) | 87.9% |
|
||||
| UNINIT_CCM | 0x1000FF00 | 48 B (0.05 KB) | 256 B (0 KB) | 18.8% |
|
||||
| RW_IRAM1 | 0x20000000 | 75,264 B (73.50 KB) | 131,072 B (128 KB) | 57.4% |
|
||||
|
||||
## 3. RW_IRAM1 逐符号明细(ZI + RW,按大小降序)
|
||||
|
||||
| # | Address | Size (B) | Size (KB) | Type | Section | Object |
|
||||
|---|---|---|---|---|---|---|
|
||||
| 1 | 0x2000ADC8 | 16,384 | 16.00 | Zero | .bss | lv_mem_core_builtin.o |
|
||||
| 2 | 0x20007EB4 | 7,724 | 7.54 | Zero | .bss | lftpd.o |
|
||||
| 3 | 0x200107A4 | 6,746 | 6.59 | Zero | .bss | ui_net_sink.o |
|
||||
| 4 | 0x2000EDC8 | 6,408 | 6.26 | Zero | .bss | ui_port.o |
|
||||
| 5 | 0x2000667C | 6,200 | 6.05 | Zero | .bss | nand_ftl.o |
|
||||
| 6 | 0x20004E18 | 4,152 | 4.05 | Zero | .bss | ch395f.o |
|
||||
| 7 | 0x20002054 | 4,096 | 4.00 | Zero | .bss | console_log.o |
|
||||
| 8 | 0x20001274 | 3,552 | 3.47 | Zero | .bss | sys_log_mcu.o |
|
||||
| 9 | 0x20003640 | 2,724 | 2.66 | Zero | .bss | default_task.o |
|
||||
| 10 | 0x2000A524 | 1,720 | 1.68 | Zero | .bss | cmsis_os2.o |
|
||||
| 11 | 0x2000444C | 1,440 | 1.41 | Zero | .bss | sample_ring.o |
|
||||
| 12 | 0x20009F48 | 1,220 | 1.19 | Zero | .bss | tasks.o |
|
||||
| 13 | 0x20000D74 | 1,104 | 1.08 | Zero | .bss | cfg_file_store_mcu.o |
|
||||
| 14 | 0x20003054 | 1,064 | 1.04 | Zero | .bss | soe_store.o |
|
||||
| 15 | 0x20012200 | 1,024 | 1.00 | Zero | | startup_stm32f407xx.o |
|
||||
| 16 | 0x20005E50 | 800 | 0.78 | Zero | .bss | gd5f2gq5ue.o |
|
||||
| 17 | 0x200040E8 | 712 | 0.70 | Zero | .bss | iec104_serv.o |
|
||||
| 18 | 0x20000AB4 | 704 | 0.69 | Zero | .bss | cfg_file.o |
|
||||
| 19 | 0x200005CC | 560 | 0.55 | Zero | .bss | spi.o |
|
||||
| 20 | 0x20000844 | 552 | 0.54 | Zero | .bss | usart.o |
|
||||
| 21 | 0x20009CE0 | 552 | 0.54 | Zero | .bss | lftpd_io.o |
|
||||
| 22 | 0x2000ABDC | 492 | 0.48 | Zero | .bss | lv_init.o |
|
||||
| 23 | 0x20004C38 | 480 | 0.47 | Zero | .bss | freq.o |
|
||||
| 24 | 0x2000629C | 416 | 0.41 | Zero | .bss | net_socket.o |
|
||||
| 25 | 0x200064DC | 416 | 0.41 | Zero | .bss | net_pending.o |
|
||||
| 26 | 0x200034C0 | 384 | 0.38 | Zero | .bss | task_prof.o |
|
||||
| 27 | 0x20004A8C | 320 | 0.31 | Zero | .bss | prot_set.o |
|
||||
| 28 | 0x2000A40C | 280 | 0.27 | Zero | .bss | timers.o |
|
||||
| 29 | 0x20006190 | 268 | 0.26 | Zero | .bss | rs485.o |
|
||||
| 30 | 0x200011C4 | 176 | 0.17 | Zero | .bss | prot_set_store.o |
|
||||
| 31 | 0x200004C4 | 168 | 0.16 | Zero | .bss | adc.o |
|
||||
| 32 | 0x200002B0 | 160 | 0.16 | Data | .data | lftpd.o |
|
||||
| 33 | 0x200049EC | 160 | 0.16 | Zero | .bss | phasor.o |
|
||||
| 34 | 0x200106D0 | 152 | 0.15 | Zero | .bss | ui_menu_view.o |
|
||||
| 35 | 0x2000643C | 128 | 0.12 | Zero | .bss | net_listener.o |
|
||||
| 36 | 0x20004BCC | 108 | 0.11 | Zero | .bss | prot_elm.o |
|
||||
| 37 | 0x2000056C | 84 | 0.08 | Zero | .bss | i2c.o |
|
||||
| 38 | 0x200043F8 | 84 | 0.08 | Zero | .bss | adc_input.o |
|
||||
| 39 | 0x2000024C | 83 | 0.08 | Data | .data | ftp_cfg.o |
|
||||
| 40 | 0x200007FC | 72 | 0.07 | Zero | .bss | tim.o |
|
||||
| 41 | 0x20000A6C | 72 | 0.07 | Zero | .bss | stm32f4xx_hal_timebase_tim.o |
|
||||
| 42 | 0x2000347C | 68 | 0.07 | Zero | .bss | task_watchdog.o |
|
||||
| 43 | 0x20000480 | 65 | 0.06 | Zero | .bss | freertos.o |
|
||||
| 44 | 0x20009F08 | 64 | 0.06 | Zero | .bss | queue.o |
|
||||
| 45 | 0x20000354 | 60 | 0.06 | Data | .data | tasks.o |
|
||||
| 46 | 0x2000040C | 60 | 0.06 | Data | .data | ui_page_selftest.o |
|
||||
| 47 | 0x20010768 | 60 | 0.06 | Zero | .bss | ui_page_runlog.o |
|
||||
| 48 | 0x20000150 | 48 | 0.05 | Data | .data | adc_health.o |
|
||||
| 49 | 0x200043C8 | 48 | 0.05 | Zero | .bss | iec104_pts.o |
|
||||
| 50 | 0x20000000 | 44 | 0.04 | Data | .data | freertos.o |
|
||||
| 51 | 0x2000009C | 44 | 0.04 | Data | .data | task_watchdog.o |
|
||||
| 52 | 0x20000044 | 36 | 0.04 | Data | .data | sys_log_mcu.o |
|
||||
| 53 | 0x20000228 | 36 | 0.04 | Data | .data | net_cfg.o |
|
||||
| 54 | 0x20000448 | 32 | 0.03 | Data | .data | ui_standby.o |
|
||||
| 55 | 0x20006170 | 32 | 0.03 | Zero | .bss | tpafe5160.o |
|
||||
| 56 | 0x200064BC | 32 | 0.03 | Zero | .bss | net_events.o |
|
||||
| 57 | 0x20000128 | 28 | 0.03 | Data | .data | adc_input.o |
|
||||
| 58 | 0x20000068 | 24 | 0.02 | Data | .data | console_log.o |
|
||||
| 59 | 0x200000E4 | 24 | 0.02 | Data | .data | adc_task.o |
|
||||
| 60 | 0x20000180 | 24 | 0.02 | Data | .data | prot_set.o |
|
||||
| 61 | 0x2000019C | 24 | 0.02 | Data | .data | freq.o |
|
||||
| 62 | 0x200001FC | 24 | 0.02 | Data | .data | net_listener.o |
|
||||
| 63 | 0x200043B0 | 24 | 0.02 | Zero | .bss | protect_task.o |
|
||||
| 64 | 0x20000030 | 20 | 0.02 | Data | .data | cfg_file.o |
|
||||
| 65 | 0x20000080 | 20 | 0.02 | Data | .data | soe_store.o |
|
||||
| 66 | 0x200001D0 | 20 | 0.02 | Data | .data | gd5f2gq5ue.o |
|
||||
| 67 | 0x20000390 | 20 | 0.02 | Data | .data | timers.o |
|
||||
| 68 | 0x20000468 | 20 | 0.02 | Data | .data | ui_net_sink.o |
|
||||
| 69 | 0x200003D0 | 18 | 0.02 | Data | .data | ui_menu.o |
|
||||
| 70 | 0x200000FC | 16 | 0.02 | Data | .data | iec104_serv.o |
|
||||
| 71 | 0x20000118 | 16 | 0.02 | Data | .data | iec104_pts.o |
|
||||
| 72 | 0x20000214 | 16 | 0.02 | Data | .data | net_events.o |
|
||||
| 73 | 0x200002A0 | 16 | 0.02 | Data | .data | nand_ftl.o |
|
||||
| 74 | 0x200003EC | 16 | 0.02 | Data | .data | ui_content_page.o |
|
||||
| 75 | 0x200000D4 | 12 | 0.01 | Data | .data | default_task.o |
|
||||
| 76 | 0x200001B4 | 12 | 0.01 | Data | .data | stm32f4xx_hal.o |
|
||||
| 77 | 0x200001E4 | 12 | 0.01 | Data | .data | tpafe5160.o |
|
||||
| 78 | 0x200001F0 | 12 | 0.01 | Data | .data | net_socket.o |
|
||||
| 79 | 0x200003A8 | 12 | 0.01 | Data | .data | port.o |
|
||||
| 80 | 0x200003C4 | 12 | 0.01 | Data | .data | ui_port.o |
|
||||
| 81 | 0x200003FC | 12 | 0.01 | Data | .data | ui_page_password.o |
|
||||
| 82 | 0x200005C0 | 12 | 0.01 | Zero | .bss | iwdg.o |
|
||||
| 83 | 0x200001C4 | 10 | 0.01 | Data | .data | ch395f.o |
|
||||
| 84 | 0x20000094 | 8 | 0.01 | Data | .data | sys_clock.o |
|
||||
| 85 | 0x200000C8 | 8 | 0.01 | Data | .data | task_prof.o |
|
||||
| 86 | 0x2000010C | 8 | 0.01 | Data | .data | protect_task.o |
|
||||
| 87 | 0x20000144 | 8 | 0.01 | Data | .data | sample_ring.o |
|
||||
| 88 | 0x200003B4 | 8 | 0.01 | Data | .data | ff.o |
|
||||
| 89 | 0x200003BC | 8 | 0.01 | Data | .data | ffsystem.o |
|
||||
| 90 | 0x200003E4 | 8 | 0.01 | Data | .data | ui_menu_view.o |
|
||||
| 91 | 0x2000002C | 4 | 0.00 | Data | .data | app_main.o |
|
||||
| 92 | 0x200000D0 | 4 | 0.00 | Data | .data | vol_lock.o |
|
||||
| 93 | 0x200000E0 | 4 | 0.00 | Data | .data | net_task.o |
|
||||
| 94 | 0x200001C0 | 4 | 0.00 | Data | .data | system_stm32f4xx.o |
|
||||
| 95 | 0x20000224 | 4 | 0.00 | Data | .data | net_pending.o |
|
||||
| 96 | 0x20000350 | 4 | 0.00 | Data | .data | lftpd_io.o |
|
||||
| 97 | 0x200003A4 | 4 | 0.00 | Data | .data | cmsis_os2.o |
|
||||
| 98 | 0x2000047C | 4 | 0.00 | Data | .data | mc_w.l(errno.o) |
|
||||
| 99 | 0x2000014C | 2 | 0.00 | Data | .data | phasor.o |
|
||||
| 100 | 0x20000408 | 2 | 0.00 | Data | .data | ui_page_net_cfg.o |
|
||||
| 101 | 0x20000198 | 1 | 0.00 | Data | .data | prot_elm.o |
|
||||
| | | **75,239** | **73.48** | | | **Total** |
|
||||
|
||||
## 4. Image Component Sizes(RW + ZI > 0,按大小降序)
|
||||
|
||||
| # | Object | Code | RO | RW | ZI | RW+ZI |
|
||||
|---|---|---|---|---|---|---|
|
||||
| 1 | heap_4.o | 512 | 69 | 32 | 57,344 | 57,376 |
|
||||
| 2 | lv_mem_core_builtin.o | 410 | 0 | 0 | 16,384 | 16,384 |
|
||||
| 3 | lftpd.o | 6,108 | 509 | 160 | 7,724 | 7,884 |
|
||||
| 4 | ui_net_sink.o | 1,126 | 67 | 20 | 6,746 | 6,766 |
|
||||
| 5 | ui_port.o | 418 | 0 | 12 | 6,408 | 6,420 |
|
||||
| 6 | nand_ftl.o | 2,352 | 175 | 16 | 6,200 | 6,216 |
|
||||
| 7 | ch395f.o | 3,986 | 603 | 10 | 4,152 | 4,162 |
|
||||
| 8 | console_log.o | 980 | 55 | 24 | 4,096 | 4,120 |
|
||||
| 9 | sys_log_mcu.o | 3,074 | 83 | 36 | 3,552 | 3,588 |
|
||||
| 10 | default_task.o | 2,332 | 280 | 12 | 2,724 | 2,736 |
|
||||
| 11 | cmsis_os2.o | 1,496 | 0 | 4 | 1,720 | 1,724 |
|
||||
| 12 | sample_ring.o | 292 | 0 | 8 | 1,440 | 1,448 |
|
||||
| 13 | tasks.o | 4,342 | 0 | 60 | 1,220 | 1,280 |
|
||||
| 14 | cfg_file_store_mcu.o | 380 | 24 | 0 | 1,104 | 1,104 |
|
||||
| 15 | soe_store.o | 816 | 28 | 20 | 1,064 | 1,084 |
|
||||
| 16 | startup_stm32f407xx.o | 36 | 392 | 0 | 1,024 | 1,024 |
|
||||
| 17 | gd5f2gq5ue.o | 3,930 | 478 | 20 | 800 | 820 |
|
||||
| 18 | iec104_serv.o | 1,188 | 16 | 16 | 712 | 728 |
|
||||
| 19 | cfg_file.o | 5,970 | 810 | 20 | 704 | 724 |
|
||||
| 20 | spi.o | 584 | 0 | 0 | 560 | 560 |
|
||||
| 21 | lftpd_io.o | 1,198 | 0 | 4 | 552 | 556 |
|
||||
| 22 | usart.o | 884 | 0 | 0 | 552 | 552 |
|
||||
| 23 | freq.o | 764 | 8 | 24 | 480 | 504 |
|
||||
| 24 | lv_init.o | 156 | 0 | 0 | 492 | 492 |
|
||||
| 25 | net_socket.o | 4,916 | 443 | 12 | 416 | 428 |
|
||||
| 26 | net_pending.o | 1,400 | 0 | 4 | 416 | 420 |
|
||||
| 27 | task_prof.o | 638 | 185 | 8 | 384 | 392 |
|
||||
| 28 | prot_set.o | 844 | 640 | 24 | 320 | 344 |
|
||||
| 29 | timers.o | 1,232 | 0 | 20 | 280 | 300 |
|
||||
| 30 | rs485.o | 120 | 0 | 0 | 268 | 268 |
|
||||
| 31 | prot_set_store.o | 236 | 74 | 0 | 176 | 176 |
|
||||
| 32 | adc.o | 580 | 0 | 0 | 168 | 168 |
|
||||
| 33 | phasor.o | 420 | 258 | 2 | 160 | 162 |
|
||||
| 34 | task_watchdog.o | 1,110 | 137 | 44 | 116 | 160 |
|
||||
| 35 | ui_menu_view.o | 2,034 | 16 | 8 | 152 | 160 |
|
||||
| 36 | net_listener.o | 948 | 207 | 24 | 128 | 152 |
|
||||
| 37 | adc_input.o | 592 | 27 | 28 | 84 | 112 |
|
||||
| 38 | freertos.o | 712 | 592 | 44 | 65 | 109 |
|
||||
| 39 | prot_elm.o | 708 | 227 | 1 | 108 | 109 |
|
||||
| 40 | i2c.o | 168 | 0 | 0 | 84 | 84 |
|
||||
| 41 | ftp_cfg.o | 152 | 225 | 83 | 0 | 83 |
|
||||
| 42 | stm32f4xx_hal_timebase_tim.o | 152 | 0 | 0 | 72 | 72 |
|
||||
| 43 | tim.o | 168 | 0 | 0 | 72 | 72 |
|
||||
| 44 | iec104_pts.o | 1,082 | 132 | 16 | 48 | 64 |
|
||||
| 45 | queue.o | 2,840 | 0 | 0 | 64 | 64 |
|
||||
| 46 | ui_page_runlog.o | 28 | 105 | 0 | 60 | 60 |
|
||||
| 47 | ui_page_selftest.o | 28 | 109 | 60 | 0 | 60 |
|
||||
| 48 | adc_health.o | 432 | 0 | 48 | 0 | 48 |
|
||||
| 49 | net_events.o | 1,994 | 809 | 16 | 32 | 48 |
|
||||
| 50 | tpafe5160.o | 808 | 67 | 12 | 32 | 44 |
|
||||
| 51 | net_cfg.o | 832 | 103 | 36 | 0 | 36 |
|
||||
| 52 | protect_task.o | 840 | 68 | 8 | 24 | 32 |
|
||||
| 53 | ui_standby.o | 1,208 | 67 | 32 | 0 | 32 |
|
||||
| 54 | (incl. Padding) | 284 | 96 | 16 | 9 | 25 |
|
||||
| 55 | adc_task.o | 1,520 | 234 | 24 | 0 | 24 |
|
||||
| 56 | ui_menu.o | 760 | 137 | 18 | 0 | 18 |
|
||||
| 57 | ui_content_page.o | 1,664 | 81 | 16 | 0 | 16 |
|
||||
| 58 | iwdg.o | 28 | 0 | 0 | 12 | 12 |
|
||||
| 59 | port.o | 762 | 73 | 12 | 0 | 12 |
|
||||
| 60 | stm32f4xx_hal.o | 116 | 0 | 12 | 0 | 12 |
|
||||
| 61 | ui_page_password.o | 686 | 175 | 12 | 0 | 12 |
|
||||
| 62 | ff.o | 7,962 | 282 | 8 | 0 | 8 |
|
||||
| 63 | ffsystem.o | 204 | 20 | 8 | 0 | 8 |
|
||||
| 64 | sys_clock.o | 1,788 | 286 | 8 | 0 | 8 |
|
||||
| 65 | app_main.o | 2,272 | 65 | 4 | 0 | 4 |
|
||||
| 66 | net_task.o | 1,460 | 72 | 4 | 0 | 4 |
|
||||
| 67 | system_stm32f4xx.o | 16 | 24 | 4 | 0 | 4 |
|
||||
| 68 | vol_lock.o | 92 | 0 | 4 | 0 | 4 |
|
||||
| 69 | errno.o | 20 | 0 | 4 | 0 | 4 |
|
||||
| 70 | ui_page_net_cfg.o | 1,004 | 105 | 2 | 0 | 2 |
|
||||
| | **All .o files** | **213,188** | **18,580** | **1,184** | **131,504** | **132,688** |
|
||||
|
||||
## 5. Flash (Code + RO Data) Top-30(按大小降序)
|
||||
|
||||
| # | Object | Code | RO Data | Code+RO |
|
||||
|---|---|---|---|---|
|
||||
| 1 | ff.o | 7,962 | 282 | 8,244 |
|
||||
| 2 | cfg_file.o | 5,970 | 810 | 6,780 |
|
||||
| 3 | lftpd.o | 6,108 | 509 | 6,617 |
|
||||
| 4 | net_socket.o | 4,916 | 443 | 5,359 |
|
||||
| 5 | lv_indev.o | 4,928 | 0 | 4,928 |
|
||||
| 6 | ch395f.o | 3,986 | 603 | 4,589 |
|
||||
| 7 | ui_font_cn_12.o | 0 | 4,545 | 4,545 |
|
||||
| 8 | lv_obj_pos.o | 4,526 | 16 | 4,542 |
|
||||
| 9 | lv_refr.o | 4,486 | 0 | 4,486 |
|
||||
| 10 | gd5f2gq5ue.o | 3,930 | 478 | 4,408 |
|
||||
| 11 | tasks.o | 4,342 | 0 | 4,342 |
|
||||
| 12 | lv_obj_scroll.o | 4,126 | 0 | 4,126 |
|
||||
| 13 | lv_obj_style.o | 4,106 | 0 | 4,106 |
|
||||
| 14 | lv_draw_sw_mask.o | 3,862 | 0 | 3,862 |
|
||||
| 15 | stm32f4xx_hal_spi.o | 3,586 | 0 | 3,586 |
|
||||
| 16 | lv_draw_sw_box_shadow.o | 3,246 | 0 | 3,246 |
|
||||
| 17 | sys_log_mcu.o | 3,074 | 83 | 3,157 |
|
||||
| 18 | lv_indev_scroll.o | 3,068 | 0 | 3,068 |
|
||||
| 19 | lv_obj.o | 2,982 | 43 | 3,025 |
|
||||
| 20 | lv_draw_sw_img.o | 2,960 | 0 | 2,960 |
|
||||
| 21 | queue.o | 2,840 | 0 | 2,840 |
|
||||
| 22 | journal.o | 2,834 | 0 | 2,834 |
|
||||
| 23 | iec104_link.o | 2,824 | 0 | 2,824 |
|
||||
| 24 | net_events.o | 1,994 | 809 | 2,803 |
|
||||
| 25 | default_task.o | 2,332 | 280 | 2,612 |
|
||||
| 26 | nand_ftl.o | 2,352 | 175 | 2,527 |
|
||||
| 27 | app_main.o | 2,272 | 65 | 2,337 |
|
||||
| 28 | printfa.o | 2,312 | 0 | 2,312 |
|
||||
| 29 | stm32f4xx_hal_i2c.o | 2,294 | 0 | 2,294 |
|
||||
| 30 | lv_display.o | 2,284 | 0 | 2,284 |
|
||||
| | **All .o files** | **213,188** | **18,580** | **231,768** |
|
||||
|
||||
> 自洽校验:per-file 213,188/18,580/1,184/131,504 vs Grand Totals 213,188/18,580/1,184/131,504(CodeΔ=+0 / ROΔ=+0 / RWΔ=+0 / ZIΔ=+0;精确一致(含 '('incl. Generated)'-'(incl. Padding)' 台账行))→ **PASS**
|
||||
@@ -0,0 +1,100 @@
|
||||
# Stack budget report
|
||||
|
||||
- Source: `MDK-ARM\STM32F407-Demo\STM32F407-Demo.htm` (Keil static call graph)
|
||||
- Linker run: Thu Oct 22 10:36:17 2026
|
||||
- Global maximum stack usage: **3024 B** (any call tree)
|
||||
- Runtime watermark: 8 task(s) from 串口采集日志 `.dsh\skills\serial-assistant\scripts\state\serial.log`
|
||||
|
||||
Rule: `margin = cfg - max(static_max_depth, runtime_peak)` must be >= max(1024 B ISR, 30% of cfg).
|
||||
|
||||
| Task | Entry | Cfg (B) | Static max (B) | Runtime peak (B) | Worst (B) | Margin (B) | Margin % | Verdict |
|
||||
|---|---|---|---|---|---|---|---|---|
|
||||
| defaultTask | `StartDefaultTask` | 5120 | 3024 | 2164 | 3024 | 2096 | 40% | PASS |
|
||||
| netTask | `StartNetTask` | 3840 | 1912 | 1116 | 1912 | 1928 | 50% | PASS |
|
||||
| ftpTask | `StartFtpTask` | 4096 | 1456 | 756 | 1456 | 2640 | 64% | PASS |
|
||||
| uiTask | `StartUiTask` | 16384 | 1336 | 4052 | 4052 | 12332 | 75% | PASS |
|
||||
| testTask | `start_test_task` | 8192 | 736 | - | 736 | 7456 | 91% | PASS |
|
||||
| timeSyncTask | `time_sync_task` | 2560 | 1264 | 616 | 1264 | 1296 | 50% | PASS |
|
||||
| adcTask | `adc_task_func` | 2560 | 1320 | 952 | 1320 | 1240 | 48% | PASS |
|
||||
| iec104Task | `iec104_serv_task` | 2560 | 1456 | 544 | 1456 | 1104 | 43% | PASS |
|
||||
| protectTask | `protect_task` | 2048 | 872 | 828 | 872 | 1176 | 57% | PASS |
|
||||
|
||||
`Static max` = armlink worst-case call-tree depth; `Runtime peak` = measured high-water mark (boot + whatever workload ran before the sample); `Worst` = max of the two, which is what the verdict is computed from.
|
||||
|
||||
Runtime heap: free=15800 B, min_ever=8464 B
|
||||
|
||||
## Worst call chain per task
|
||||
|
||||
### defaultTask: 3024 B (own frame 0 B)
|
||||
|
||||
```
|
||||
StartDefaultTask -> default_task_func -> storage_bring_up -> net_cfg_load -> cfg_file_load -> s_write_template -> s_write_doc -> cfg_store_write_atomic -> f_rename -> sync_fs -> disk_ioctl -> ftl_flush_cache -> dhara_map_write -> prepare_write -> auto_gc -> dhara_map_gc -> try_recover -> raw_gc -> trace_path -> dhara_journal_read_meta -> dhara_nand_read -> gd5f_read_from_cache -> dbg_console_write_line -> con_append -> dbg_console_drain -> MX_USART1_UART_Init -> HAL_UART_Init -> HAL_UART_MspInit -> Error_Handler -> dbg_console_write_line (Cycle)
|
||||
```
|
||||
|
||||
### netTask: 1912 B (own frame 0 B)
|
||||
|
||||
```
|
||||
StartNetTask -> net_task_func -> net_process_messages -> net_listener_tick -> net_relisten_locked -> ch395f_read_recv_buf -> ch395f_spi_dma_transfer -> ch395f_spi_fault_set -> dbg_console_write_line -> con_append -> dbg_console_drain -> MX_USART1_UART_Init -> HAL_UART_Init -> HAL_UART_MspInit -> Error_Handler -> dbg_console_write_line (Cycle)
|
||||
```
|
||||
|
||||
### ftpTask: 1456 B (own frame 24 B)
|
||||
|
||||
```
|
||||
StartFtpTask -> lftpd_start -> lftpd_inet_listen -> net_bind -> ch395f_open_socket -> ch395f_poll_cmd_status -> ch395f_get_cmd_status -> ch395f_write_cmd -> ch395f_spi_fault_set -> dbg_console_write_line -> con_append -> dbg_console_drain -> MX_USART1_UART_Init -> HAL_UART_Init -> HAL_UART_MspInit -> Error_Handler -> dbg_console_write_line (Cycle)
|
||||
```
|
||||
|
||||
### uiTask: 1336 B (own frame 0 B)
|
||||
|
||||
```
|
||||
StartUiTask -> ui_task_func -> ui_menu_init -> ui_menu_view_init -> lv_obj_create -> lv_obj_class_init_obj -> lv_theme_apply -> lv_obj_remove_style_all -> lv_obj_remove_style -> lv_obj_refresh_style -> refresh_children_style -> refresh_children_style (Cycle)
|
||||
```
|
||||
|
||||
### testTask: 736 B (own frame 224 B)
|
||||
|
||||
```
|
||||
start_test_task -> dbg_console_write_line -> con_append -> dbg_console_drain -> MX_USART1_UART_Init -> HAL_UART_Init -> HAL_UART_MspInit -> Error_Handler -> dbg_console_write_line (Cycle)
|
||||
```
|
||||
|
||||
### timeSyncTask: 1264 B (own frame 152 B)
|
||||
|
||||
```
|
||||
time_sync_task -> time_sync_open_listener -> net_bind -> ch395f_open_socket -> ch395f_poll_cmd_status -> ch395f_get_cmd_status -> ch395f_write_cmd -> ch395f_spi_fault_set -> dbg_console_write_line -> con_append -> dbg_console_drain -> MX_USART1_UART_Init -> HAL_UART_Init -> HAL_UART_MspInit -> Error_Handler -> dbg_console_write_line (Cycle)
|
||||
```
|
||||
|
||||
### adcTask: 1320 B (own frame 312 B)
|
||||
|
||||
```
|
||||
adc_task_func -> adc_health_report -> syslog_post -> dbg_console_write_line -> con_append -> dbg_console_drain -> MX_USART1_UART_Init -> HAL_UART_Init -> HAL_UART_MspInit -> Error_Handler -> dbg_console_write_line (Cycle)
|
||||
```
|
||||
|
||||
### iec104Task: 1456 B (own frame 160 B)
|
||||
|
||||
```
|
||||
iec104_serv_task -> s_serv_poll -> s_service_link -> s_drop_conn -> s_bind_listen -> net_bind -> ch395f_open_socket -> ch395f_poll_cmd_status -> ch395f_get_cmd_status -> ch395f_write_cmd -> ch395f_spi_fault_set -> dbg_console_write_line -> con_append -> dbg_console_drain -> MX_USART1_UART_Init -> HAL_UART_Init -> HAL_UART_MspInit -> Error_Handler -> dbg_console_write_line (Cycle)
|
||||
```
|
||||
|
||||
### protectTask: 872 B (own frame 160 B)
|
||||
|
||||
```
|
||||
protect_task -> s_log_active_edge -> dbg_console_write_line -> con_append -> dbg_console_drain -> MX_USART1_UART_Init -> HAL_UART_Init -> HAL_UART_MspInit -> Error_Handler -> dbg_console_write_line (Cycle)
|
||||
```
|
||||
|
||||
## Frame-size ranking (own frame, top 15)
|
||||
|
||||
| Bytes | Function |
|
||||
|---|---|
|
||||
| 624 | `lv_draw_sw_arc` |
|
||||
| 400 | `draw_line_skew` |
|
||||
| 352 | `lv_draw_sw_triangle` |
|
||||
| 352 | `net_stack_bring_up` |
|
||||
| 328 | `lv_obj_redraw` |
|
||||
| 328 | `view_frame_draw_cb` |
|
||||
| 324 | `s_transform` |
|
||||
| 320 | `wd_stall_evidence` |
|
||||
| 312 | `adc_task_func` |
|
||||
| 312 | `nc_draw_cb` |
|
||||
| 304 | `lv_draw_label_iterate_characters` |
|
||||
| 304 | `lv_draw_sw_box_shadow` |
|
||||
| 304 | `soe_store_drain` |
|
||||
| 304 | `sys_clock_init` |
|
||||
| 296 | `net_relisten_locked` |
|
||||
+20
-19
@@ -117,8 +117,12 @@ Graphviz / Cppcheck 的安装位置差异一律用 `DTU_*` 环境变量表达(
|
||||
|
||||
- 链接器使用**手动 scatter 文件** `MDK-ARM/STM32F407-Demo/STM32F407-Demo.sct`(在仓库,`.uvprojx` 已启用 `useFile=1`):
|
||||
- `ER_IROM1` 0x08000000,1 MB(代码 + 只读数据)
|
||||
- `RW_IRAM1` 0x20000000,**128 KB**(SRAM1 112K + SRAM2 16K 连续;SRAM3/CCM 故意未映射——克隆芯片可能无 SRAM3)
|
||||
- Keil `Options for Target → Target` 页显示的片上内存来自 `.uvprojx` 的 `<Cpu>` 行(IRAM 112 KB / IRAM2 16 KB / IROM 1 MB,同样在仓库)+ Device Pack
|
||||
- `RW_IRAM1` 0x20000000,**128 KB**(SRAM1 112K + SRAM2 16K 连续,**DMA 可达区**:存储/网络/串口 DMA
|
||||
缓冲只能放这里;克隆芯片可能无 SRAM3,换料必须重测)
|
||||
- `RW_CCM` 0x10000000,**64 KB 减 256 B 尾**(2026-10-11 起启用,承载 FreeRTOS 堆与 `.noinit` 崩溃现场;
|
||||
**CCM 不可被 DMA 寻址**——规则 R2/R3 见 `docs/内存管理/内存内容分配策略.md` §4,并有编译期窗口断言 +
|
||||
启动期自检 + 运行时守卫三层强制)
|
||||
- Keil `Options for Target → Target` 页显示的片上内存来自 `.uvprojx` 的 `<Cpu>` 行(IRAM 112 KB / IRAM2 16 KB / IROM 1 MB,同样在仓库)+ Device Pack(**GUI 那几格不含 CCM 段,别据此判断"CCM 没用"**)
|
||||
- ⚠ 新机器**不要在 GUI 里重填 RAM 区**,也**勿改 Target 页**(会回写共享的 `.uvprojx` 影响他人);确需调整内存布局(如日后启用 SRAM3/CCM)时修改 `.sct` 并提交
|
||||
|
||||
### 2.3 PC 侧编译环境(模拟器 + 主机侧单元测试,必需)
|
||||
@@ -476,10 +480,10 @@ $env:DTU_KEIL_UV4 = 'D:\NotExist\UV4.exe' # 仅当前会话,不动用户级
|
||||
|
||||
| 项 | 值 | 说明 |
|
||||
|---|---|---|
|
||||
| MCU | STM32F407ZGTx | Cortex-M4(双精度 FPU / TrustZone),LQFP144 |
|
||||
| MCU | STM32F407ZGTx | Cortex-M4,**单精度** FPU(VFPv4-SP,**无硬件双精度**,`double` 走软件模拟;无 TrustZone),LQFP144 |
|
||||
| 主频 | 168 MHz | HSE 8 MHz → PLL M=4 / N=168 / P=2(`Inc/stm32f4xx_hal_conf.h`) |
|
||||
| Flash | 1 MB(0x08000000) | 片内 |
|
||||
| SRAM | 192 KB(128 KB 主 + 64 KB CCM) | 当前仅用主 SRAM 128 KB;SRAM3/CCM 未映射(§3.3) |
|
||||
| SRAM | 192 KB(128 KB 主 + 64 KB CCM) | **两块都在用**:主 SRAM1 128 KB(DMA 可达)+ CCM(FreeRTOS 堆);SRAM3 仍未映射 → §3.3 |
|
||||
| RTOS | FreeRTOS V10.3.1(CMSIS-RTOS V2) | HAL 时基 TIM7,tick = 1 ms;NVIC 4 位抢占,外设中断优先级 ≥5 |
|
||||
|
||||
### 3.2 外设硬件要求(引脚级)
|
||||
@@ -505,22 +509,18 @@ $env:DTU_KEIL_UV4 = 'D:\NotExist\UV4.exe' # 仅当前会话,不动用户级
|
||||
| CCM(`RW_CCM` 段) | 57,376 B(56.0 KB) | 65,280 B | **87.9%** | **7,904 B** | **当前真正的红线**:加任务 / 抬栈 / 加堆会先在这里撞墙;`mem-budget` 钩子在 92% 拦提交 |
|
||||
|
||||
- LVGL 内存池 16 KB(静态占用,2026-10-15 由 40 KB 收缩);FreeRTOS 堆 56 KB(CCM)
|
||||
- 任务栈预算(words,1 word = 4 B):
|
||||
- **任务栈配置不在本文重复**:唯一事实源是 `Src/freertos.c`(`.ioc` 的 `FREERTOS.Tasks01`),
|
||||
受管表只有两份——根 `README.md` 与 `AGENTS.md` 里由 `scripts/gen_task_table.py --write` 生成的
|
||||
`TASK_TABLE` 块,由 `task-table` 钩子校验;每任务的静态最坏链、实测峰值与余量台账在
|
||||
`docs/内存管理/RAM使用分析与优化方案.md` §2.3(配置与实测峰值)与 §0.6(静态最坏链与判定)。
|
||||
- ⚠ **不要再在本文抄一份任务表**:`task-table` 钩子的校验面只有上面那两份受管块,抄出来的副本
|
||||
没有门禁、改栈后必然漂(2026-10-22 删除本文历史副本时,它已缺 `adcTask` / `iec104Task` /
|
||||
`protectTask` 三个任务,`defaultTask`/`timeSyncTask` 两值也停在旧数)。
|
||||
|
||||
| 任务 | 栈大小 | 优先级 |
|
||||
|---|---|---|
|
||||
| defaultTask | 1024 | Normal |
|
||||
| netTask | 960 | Normal |
|
||||
| ftpTask | 1024 | Normal |
|
||||
| testTask | 2048 | BelowNormal |
|
||||
| uiTask | 4096 | BelowNormal |
|
||||
| timeSyncTask | 512 | Normal |
|
||||
|
||||
> 上表由 `scripts/gen_task_table.py` 同源(唯一来源 `Src/freertos.c` / `.ioc` 的 `FREERTOS.Tasks01`);
|
||||
> 2026-10-10 栈整改**未改任何栈值**,靠削调用链达标(详见 `docs/内存管理/RAM使用分析与优化方案.md`)。
|
||||
|
||||
> 挖潜方向(未实施):SRAM3 64 KB / CCM 64 KB 未映射——详见 `docs/内存管理/`。
|
||||
> 部署侧含义:**不要做任何需要额外 RAM 的固件定制**,新增功能先过内存预算。
|
||||
> 挖潜方向:**SRAM3 64 KB 仍未映射**;CCM 64 KB **已启用**(2026-10-11 起承载 FreeRTOS 堆,见上表
|
||||
> `RW_CCM` 行),配额与台账 → `docs/内存管理/RAM预算台账.md`。
|
||||
> 部署侧含义:**新增需要额外 RAM 的固件定制前必须先过内存预算**——余量集中在 SRAM1,CCM 只剩
|
||||
> 7,904 B,加任务 / 抬栈 / 加堆会先在 CCM 撞墙。
|
||||
|
||||
### 3.4 下载与调试
|
||||
|
||||
@@ -649,6 +649,7 @@ $env:DTU_KEIL_UV4 = 'D:\NotExist\UV4.exe' # 仅当前会话,不动用户级
|
||||
|
||||
| 日期 | 变更 |
|
||||
|---|---|
|
||||
| 2026-10-22 | **§3.2 / §3.3 与 §2.2 内存事实纠偏**:① §3.3 资源预算表由 2026-09-11 快照刷新为 2026-10-22 实测——Flash 231,768 B / 22.1%,主 SRAM1 由"125,104 B / 95.4% / 极度紧张"更正为 **75,264 B / 57.4%(余 55,808 B)**,并**补上 CCM 行**(57,376 B / 87.9%,余 7,904 B)——当前红线在 CCM 而非 SRAM1;② 删除 §3.3 的任务栈副本表(无门禁、已缺 `adcTask`/`iec104Task`/`protectTask`),改指针到 `README.md`/`AGENTS.md` 受管表与 `RAM使用分析与优化方案.md` §2.3/§0.6;③ §2.2 链接布局补 `RW_CCM 0x10000000` 段(2026-10-11 已启用、**不可 DMA**),§3.1 MCU 行更正为**单精度 FPU、无 TrustZone**(原写"双精度 FPU / TrustZone"是芯片事实错误,也正是报告 F-6 双精度软浮点被长期误判的土壤) |
|
||||
| 2026-10-12 | **远程 CI 文档迁出本目录**:`CI配置指南.md` 与 `Gitea_Runner部署指南.md` 合并为 **`docs/CI/远程CI完整指南.md`**(入口 `docs/CI/README.md`),本文三处引用改指新路径与新章节号(§4.1.3 机器级变量、§7 相关文档登记)。原因:远程 CI 只涉及本机一台 runner,不应与"任何机器都要过"的部署核对清单混在一起 |
|
||||
| 2026-10-10 | **删除旧档 NCFG 迁移**(升级/迁移口径变更):旧固件遗留的 `/cfg/netcfg.bin` 不再"首启自动迁移"——旧档若存在则被忽略(不读、不删、不迁移),配置直接回落工厂默认(`/config.ini` `[network]` 段模板)。`net_cfg_legacy.c/h` 与 `cfg_store_legacy_path()` 已移除;携带旧档的设备升级后需经 UI 或 FTP 重新配置网口。§五 现场部署 IP 行同步 |
|
||||
| 2026-10-02 | **模拟器构建修复**(配置引擎重构遗留):`simulator/CMakeLists.txt` 的配置文件引擎引用同步到迁移后位置——包含目录 `App/`→`App/cfg/`(`cfg_file.h`/`cfg_file_store.h`)、源文件 `App/cfg_file.c`→`App/cfg/cfg_file.c`、包含目录 `test/`→`test/board/`(`test_config.h`/`net_latency_test.h`);全量 include 离线核查无其他断链,模拟器全量构建恢复(`--cfgtest` 四场景 PASS,rc=0)。§2.12 验证链 ⑤ 行同步更新 |
|
||||
|
||||
@@ -365,7 +365,9 @@ def main():
|
||||
|
||||
if args.output:
|
||||
pathlib.Path(args.output).parent.mkdir(parents=True, exist_ok=True)
|
||||
pathlib.Path(args.output).write_text(report, encoding="utf-8")
|
||||
# newline="\n":Windows 下 write_text 默认把 \n 翻成 \r\n,会跟 .gitattributes
|
||||
# (* text=auto eol=lf)与 data/ 目录既有快照的行尾不一致(2026-10-22 实测)。
|
||||
pathlib.Path(args.output).write_text(report, encoding="utf-8", newline="\n")
|
||||
print(f"OK: Report written to {args.output}", file=sys.stderr)
|
||||
else:
|
||||
print(report)
|
||||
|
||||
+12
-3
@@ -176,12 +176,20 @@ def main():
|
||||
add = out.append
|
||||
add('# Stack budget report')
|
||||
add('')
|
||||
add(f'- Source: `{html_path.relative_to(REPO_ROOT)}` (Keil static call graph)')
|
||||
# 显示用相对路径:传相对 -i 时 relative_to 会抛 ValueError(2026-10-22 实测踩到),
|
||||
# 且绝不把本机绝对路径写进入库的 data/ 快照。
|
||||
def _disp(pth):
|
||||
try:
|
||||
return pathlib.Path(pth).resolve().relative_to(REPO_ROOT)
|
||||
except (ValueError, OSError):
|
||||
return pathlib.Path(pth).name
|
||||
|
||||
add(f'- Source: `{_disp(html_path)}` (Keil static call graph)')
|
||||
if meta["updated"]:
|
||||
add(f'- Linker run: {meta["updated"]}')
|
||||
add(f'- Global maximum stack usage: **{meta["max_stack"]} B** (any call tree)')
|
||||
if runtime:
|
||||
add(f'- Runtime watermark: {len(runtime)} task(s) from `{args.serial}`')
|
||||
add(f'- Runtime watermark: {len(runtime)} task(s) from 串口采集日志 `{_disp(args.serial)}`')
|
||||
add('')
|
||||
add('Rule: `margin = cfg - max(static_max_depth, runtime_peak)` must be '
|
||||
f'>= max({args.isr_margin} B ISR, {args.min_free_pct}% of cfg).')
|
||||
@@ -252,7 +260,8 @@ def main():
|
||||
|
||||
report = '\n'.join(out)
|
||||
if args.output:
|
||||
pathlib.Path(args.output).write_text(report, encoding='utf-8')
|
||||
# newline="\n":避免 Windows 换行翻译污染 data/ 快照的 LF 行尾(与 .gitattributes 一致)。
|
||||
pathlib.Path(args.output).write_text(report, encoding='utf-8', newline='\n')
|
||||
print(f'written: {args.output}')
|
||||
else:
|
||||
print(report)
|
||||
|
||||
@@ -17,39 +17,41 @@ import sys
|
||||
# Diagram data
|
||||
# ---------------------------------------------------------------------------
|
||||
|
||||
# ── RAM breakdown (2026-09-21 @build, map Grand Totals; data/ram_report_20260921.md) ──
|
||||
# ── RAM breakdown (2026-10-22 @build, map Grand Totals; data/ram_report_20261022.md) ──
|
||||
# Region 1: main SRAM RW_IRAM1 @0x20000000 (128KB = 131,072 B, DMA-reachable)
|
||||
SRAM1_TOTAL = 131072
|
||||
SRAM1_USED = 82048
|
||||
SRAM1_USED = 75264
|
||||
SRAM1_FREE = SRAM1_TOTAL - SRAM1_USED
|
||||
# Region 2: CCM RW_CCM @0x10000000 (64KB = 65,536 B, CPU only, DMA NOT reachable)
|
||||
CCM_TOTAL = 65536
|
||||
CCM_USED = 49184
|
||||
# Region 2: CCM RW_CCM @0x10000000 —— scatter 给的是 0x0000FF00 = 65,280 B(CPU only,
|
||||
# DMA 不可达);另有 0x1000FF00 起 256 B 的 UNINIT_CCM 尾区(.noinit 崩溃现场用 48 B)
|
||||
CCM_TOTAL = 65280
|
||||
CCM_USED = 57376
|
||||
CCM_FREE = CCM_TOTAL - CCM_USED
|
||||
|
||||
RAM1_CATEGORIES = [
|
||||
("LVGL", 41460, "#4CAF50"),
|
||||
("UI", 13532, "#FF9800"),
|
||||
("FTL/BBT", 8812, "#9C27B0"),
|
||||
("lftpd", 5324, "#8BC34A"),
|
||||
("CMSIS", 5016, "#00BCD4"),
|
||||
("NET", 4445, "#F44336"),
|
||||
("HAL", 1280, "#607D8B"),
|
||||
("LVGL 池 16KB", 16876, "#4CAF50"),
|
||||
("UI", 13546, "#FF9800"),
|
||||
("lftpd", 8440, "#8BC34A"),
|
||||
("FTL/BBT", 7036, "#9C27B0"),
|
||||
("NET/CH395F", 5250, "#F44336"),
|
||||
("CMSIS-RTOS", 1724, "#00BCD4"),
|
||||
("HAL", 84, "#607D8B"),
|
||||
("C stack", 1024, "#795548"),
|
||||
("other", 1155, "#9E9E9E"),
|
||||
("free", SRAM1_FREE, "#E0E0E0"),
|
||||
("other", 21284, "#9E9E9E"),
|
||||
("free", SRAM1_FREE, "#E0E0E0"),
|
||||
]
|
||||
RAM2_CATEGORIES = [
|
||||
("heap", 49184, "#2196F3"),
|
||||
("free", CCM_FREE, "#E0E0E0"),
|
||||
("FreeRTOS 堆", CCM_USED, "#2196F3"),
|
||||
("free", CCM_FREE, "#E0E0E0"),
|
||||
]
|
||||
|
||||
# ── Flash breakdown (1MB = 1,048,576 B; 2026-09-21 @build) ──────────────────
|
||||
# ── Flash breakdown (1MB = 1,048,576 B; 2026-10-22 @build) ──────────────────
|
||||
FLASH_TOTAL = 1048576
|
||||
FLASH_CODE = 234976
|
||||
FLASH_RO = 13824
|
||||
FLASH_RW = 632
|
||||
FLASH_USED = FLASH_CODE + FLASH_RO + FLASH_RW
|
||||
FLASH_CODE = 213188
|
||||
FLASH_RO = 18580
|
||||
FLASH_RW = 1184
|
||||
FLASH_USED = FLASH_CODE + FLASH_RO + FLASH_RW # ROM 合计(含 RW 初始化表)
|
||||
FLASH_IROM = FLASH_CODE + FLASH_RO # ER_IROM1 区用量 = 231,768 B(22.1%)
|
||||
FLASH_FREE = FLASH_TOTAL - FLASH_USED
|
||||
|
||||
FLASH_CATEGORIES = [
|
||||
@@ -59,37 +61,42 @@ FLASH_CATEGORIES = [
|
||||
("Flash 空闲", FLASH_FREE, "#E0E0E0"),
|
||||
]
|
||||
|
||||
# Flash code sub-breakdown (2026-09-21; top items from data/ram_report_20260921.md,
|
||||
# long-tail .o objects below the report's top-44 threshold are counted in "其他")
|
||||
# Flash Code+RO 分布(= ER_IROM1 231,768 B;2026-10-22 按 .map 对象表逐对象归类,
|
||||
# 口径同 data/ram_report_20261022.md;"其他"含链接器填充)
|
||||
FLASH_CODE_SUB = [
|
||||
("LVGL 库", 98000, "#4CAF50"),
|
||||
("应用代码/UI", 34110, "#2196F3"),
|
||||
("FatFS", 8146, "#9C27B0"),
|
||||
("dhara / FTL", 4982, "#FF9800"),
|
||||
("HAL 驱动", 16000, "#607D8B"),
|
||||
("FreeRTOS 内核", 10132, "#00BCD4"),
|
||||
("CH395F 网络", 2738, "#F44336"),
|
||||
("C 库 (microlib)", 4230, "#795548"),
|
||||
("其他 (长尾)", 56638, "#E0E0E0"), # remainder
|
||||
("LVGL 库", 87706, "#4CAF50"),
|
||||
("应用代码/UI", 57011, "#2196F3"),
|
||||
("CH395F+FTP", 25652, "#F44336"),
|
||||
("HAL 驱动", 17876, "#607D8B"),
|
||||
("dhara / FTL", 10907, "#FF9800"),
|
||||
("FreeRTOS 内核", 10762, "#00BCD4"),
|
||||
("FatFS", 8468, "#9C27B0"),
|
||||
("C 库 (microlib)", 5486, "#795548"),
|
||||
("startup", 468, "#B0BEC5"),
|
||||
("其他 (长尾)", 7432, "#E0E0E0"), # remainder
|
||||
]
|
||||
|
||||
# ── Task stack budgets (2026-10-10 @build + 开机/空闲实测; data/stack_report_20261010.md) ──
|
||||
# ── Task stack budgets (2026-10-22 @build + 同日真机 [STACK] 实测; data/stack_report_20261022.md) ──
|
||||
# (name, cfg, prio, worst, peak_used, margin, margin_pct, verdict, desc)
|
||||
# worst = max(静态最坏深度, 实测峰值); margin = cfg - worst
|
||||
# 9 行含 testTask(仅测试构建创建、无实测 → 取静态最坏链,峰位列填同值)
|
||||
TASK_STACKS = [
|
||||
("defaultTask", 4096, "Normal", 2776, 2152, 1320, 32, "PASS", "FatFS 挂载/探针 + 配置引擎 + syslog + 栈探针"),
|
||||
("netTask", 3840, "Normal", 1872, 920, 1968, 51, "PASS", "CH395F 轮询、消息处理"),
|
||||
("ftpTask", 4096, "Normal", 1216, 740, 2880, 70, "PASS", "lftpd FTP 服务(大缓冲已静态化)"),
|
||||
("testTask", 8192, "BelowNormal", 496, 496, 7696, 93, "PASS", "测试套件(产品构建不创建,取静态最坏链)"),
|
||||
("uiTask", 16384, "BelowNormal", 4016, 4016, 12368, 75, "PASS", "LVGL UI 主循环"),
|
||||
("timeSyncTask", 2048, "Normal", 1024, 616, 1024, 50, "PASS", "TCP 时间同步(余量正好卡在 ISR 底线)"),
|
||||
("defaultTask", 5120, "Normal", 3024, 2164, 2096, 40, "PASS", "FatFS 挂载/探针 + 配置引擎 + syslog + LED"),
|
||||
("netTask", 3840, "Normal", 1912, 1116, 1928, 50, "PASS", "CH395F 轮询、消息处理"),
|
||||
("ftpTask", 4096, "Normal", 1456, 756, 2640, 64, "PASS", "lftpd FTP 服务(大缓冲已静态化)"),
|
||||
("uiTask", 16384, "BelowNormal", 4052, 4052, 12332, 75, "PASS", "LVGL UI 主循环 + 远程显示推流"),
|
||||
("testTask", 8192, "BelowNormal", 736, 736, 7456, 91, "PASS", "测试套件(产品构建不创建,取静态最坏链)"),
|
||||
("timeSyncTask", 2560, "Normal", 1264, 616, 1296, 50, "PASS", "TCP 时间同步(8888)"),
|
||||
("adcTask", 2560, "AboveNormal", 1320, 952, 1240, 48, "PASS", "1 kHz 节拍消费者(L1 采集,纯取数)"),
|
||||
("iec104Task", 2560, "Normal", 1456, 544, 1104, 43, "PASS", "IEC 60870-5-104 上行(2404)"),
|
||||
("protectTask", 2048, "Normal", 872, 828, 1176, 57, "PASS", "20 ms 保护判据 + 闭锁 + 定值校验和巡检"),
|
||||
]
|
||||
KERNEL_STACKS = [("idle", 512), ("timer", 1024)] # 128/256 words
|
||||
KERNEL_STACKS = [("idle", 512), ("timer", 1024)] # 128/256 words(未实测)
|
||||
|
||||
HEAP_TOTAL = 49152 # configTOTAL_HEAP_SIZE(位于 RW_CCM)
|
||||
HEAP_FREE = 8784 # 2026-09-21 实测(含 FTP 负载)
|
||||
HEAP_MIN_EVER = 4848
|
||||
TOTAL_STACKS = sum(t[1] for t in TASK_STACKS) # 38,656
|
||||
HEAP_TOTAL = 57344 # configTOTAL_HEAP_SIZE 56 KB(位于 RW_CCM;段实占 57,376 B 含元数据)
|
||||
HEAP_FREE = 15800 # 2026-10-22 真机 [STACK](启动 + 网络/FTP/104 就绪后)
|
||||
HEAP_MIN_EVER = 8464
|
||||
TOTAL_STACKS = sum(t[1] for t in TASK_STACKS) # 47,360(含 testTask;产品构建 8 任务 = 39,168)
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
# SVG helpers
|
||||
@@ -171,7 +178,7 @@ def gen_ram_svg():
|
||||
SCALE = (W - 80) / SRAM1_TOTAL # 128KB 占满宽;CCM (64KB) 占半宽
|
||||
|
||||
svg = svg_header(W, H)
|
||||
svg += f'<text x="{W/2}" y="24" text-anchor="middle" class="title">SRAM (192KB) 使用布局 — 2026-09-21 @build</text>\n'
|
||||
svg += f'<text x="{W/2}" y="24" text-anchor="middle" class="title">SRAM (192KB) 使用布局 — 2026-10-22 @build</text>\n'
|
||||
|
||||
# Region 1: 主 SRAM
|
||||
y1 = 50
|
||||
@@ -191,7 +198,7 @@ def gen_ram_svg():
|
||||
|
||||
# Region 2: CCM
|
||||
y2 = y1 + BAR_H + 50
|
||||
svg += f'<text x="{BAR_X}" y="{y2-8}" class="label" fill="#555">CCM RW_CCM @0x10000000(64KB,仅 CPU 可达,DMA 不可达)</text>\n'
|
||||
svg += f'<text x="{BAR_X}" y="{y2-8}" class="label" fill="#555">CCM RW_CCM @0x10000000(段 65,280 B;仅 CPU 可达、DMA 不可达 → R2/R3)</text>\n'
|
||||
x = BAR_X
|
||||
for label, size, color in RAM2_CATEGORIES:
|
||||
w = size * SCALE
|
||||
@@ -203,7 +210,7 @@ def gen_ram_svg():
|
||||
svg += f'<text x="{BAR_X}" y="{y2+BAR_H+18}" class="label" fill="#333">'
|
||||
svg += f'已用: {CCM_USED}B ({CCM_USED/CCM_TOTAL*100:.1f}%)'
|
||||
svg += f' 空闲: {CCM_FREE}B ({CCM_FREE/CCM_TOTAL*100:.1f}%)'
|
||||
svg += f' 总量: 64KB</text>\n'
|
||||
svg += f' 总量: 63.75KB(+256 B UNINIT_CCM 尾区)——CCM 是当前全局卡点</text>\n'
|
||||
|
||||
# Legend(主 SRAM 两列 + CCM 两行)
|
||||
ly = y2 + BAR_H + 40
|
||||
@@ -239,7 +246,7 @@ def gen_flash_svg():
|
||||
SCALE = (W - 80) / FLASH_TOTAL
|
||||
|
||||
svg = svg_header(W, H)
|
||||
svg += f'<text x="{W/2}" y="24" text-anchor="middle" class="title">Flash (1MB) 使用布局 — 2026-09-21 @build</text>\n'
|
||||
svg += f'<text x="{W/2}" y="24" text-anchor="middle" class="title">Flash (1MB) 使用布局 — 2026-10-22 @build</text>\n'
|
||||
|
||||
x = BAR_X
|
||||
for label, size, color in FLASH_CATEGORIES:
|
||||
@@ -255,29 +262,39 @@ def gen_flash_svg():
|
||||
svg += f'<text x="{BAR_X}" y="{BAR_Y+BAR_H+18}" class="label" fill="#333">'
|
||||
svg += f'已用: {FLASH_USED/1024:.1f}KB ({FLASH_USED/FLASH_TOTAL*100:.1f}%)'
|
||||
svg += f' 空闲: {FLASH_FREE/1024:.1f}KB ({FLASH_FREE/FLASH_TOTAL*100:.1f}%)'
|
||||
svg += f' 总量: 1024KB</text>\n'
|
||||
svg += f' ER_IROM1(Code+RO): {FLASH_IROM/1024:.1f}KB ({FLASH_IROM/FLASH_TOTAL*100:.1f}%)'
|
||||
svg += f' 总量: 1MB (= ROM 合计口径)'
|
||||
svg += f'</text>\n'
|
||||
|
||||
# Code sub-breakdown mini bar
|
||||
Y2 = 130
|
||||
svg += f'<text x="{BAR_X}" y="{Y2-6}" class="label" fill="#555">代码段明细 ({FLASH_CODE/1024:.1f}KB)</text>\n'
|
||||
SCALE2 = (W - 80) / FLASH_CODE
|
||||
svg += f'<text x="{BAR_X}" y="{Y2-6}" class="label" fill="#555">Code + RO 分布(ER_IROM1 {FLASH_IROM/1024:.1f}KB,按 .map 对象归类)</text>\n'
|
||||
SCALE2 = (W - 80) / FLASH_IROM
|
||||
x2 = BAR_X
|
||||
for label, size, color in FLASH_CODE_SUB:
|
||||
w = size * SCALE2
|
||||
if w < 1:
|
||||
continue
|
||||
inside = f"{label} {size/1024:.1f}KB" if w > 50 else ""
|
||||
outside = "" if w > 50 else f"{label} {size/1024:.1f}KB"
|
||||
svg += _draw_bar_segment(x2, Y2, w, 24, color, inside, outside)
|
||||
# 窄段(多数桶 < 40px)不放内嵌文字,统一列到下方图例,避免互相压字
|
||||
inside = f"{size/1024:.1f}KB" if w > 40 else ""
|
||||
svg += _draw_bar_segment(x2, Y2, w, 24, color, inside, "")
|
||||
x2 += w
|
||||
|
||||
# 图例:四列三行(10 个桶)
|
||||
for i, (label, size, color) in enumerate(FLASH_CODE_SUB):
|
||||
col, row = i % 4, i // 4
|
||||
lx = 60 + col * 195
|
||||
ly = 176 + row * 16
|
||||
svg += f' <rect x="{lx}" y="{ly-9}" width="10" height="10" fill="{color}" rx="2"/>\n'
|
||||
svg += f' <text x="{lx+14}" y="{ly}" class="legend-text" fill="#333">{label} {size/1024:.1f}KB</text>\n'
|
||||
|
||||
svg += svg_footer()
|
||||
return svg
|
||||
|
||||
|
||||
def gen_taskstack_svg():
|
||||
"""任务栈预算.svg — 每任务:分配栈条 + 最坏占用叠加条 + 实测余量/判定。"""
|
||||
W, H = 880, 440
|
||||
W, H = 880, 620 # 9 个任务 + 2 内核栈 + 堆汇总,行高 40 需要 ~600 高
|
||||
BAR_X = 190
|
||||
MAX_STACK = 16384
|
||||
SCALE = (W - BAR_X - 40) / MAX_STACK
|
||||
@@ -286,16 +303,19 @@ def gen_taskstack_svg():
|
||||
BAR_H = 16
|
||||
|
||||
svg = svg_header(W, H)
|
||||
svg += f'<text x="{W/2}" y="22" text-anchor="middle" class="title">FreeRTOS 任务栈预算(48KB 堆,2026-09-21 已迁 CCM)</text>\n'
|
||||
svg += f'<text x="{W/2}" y="40" text-anchor="middle" class="legend-text" fill="#777">数据: 2026-10-10 @build + 开机/空闲实测(data/stack_report_20261010.md);最坏 = max(静态最坏链, 实测峰值)</text>\n'
|
||||
svg += f'<text x="{W/2}" y="22" text-anchor="middle" class="title">FreeRTOS 任务栈预算(9 任务;栈全部从 56KB FreeRTOS 堆分配,堆位于 CCM)</text>\n'
|
||||
svg += f'<text x="{W/2}" y="40" text-anchor="middle" class="legend-text" fill="#777">数据: 2026-10-22 @build + 同日真机 [STACK] 水位(data/stack_report_20261022.md);最坏 = max(静态最坏链, 实测峰值);判定线 = 余量 ≥ max(1024B ISR, 配置×30%)</text>\n'
|
||||
svg += f'<text x="{BAR_X}" y="{Y_START-10}" class="legend-text" fill="#555">浅色条 = 分配栈 深色条 = 最坏占用(max(静态最坏, 实测峰值)) 下方文字 = 实测余量/判定</text>\n'
|
||||
|
||||
y = Y_START
|
||||
for name, cfg, prio, worst, peak, margin, pct, verdict, desc in TASK_STACKS:
|
||||
w = cfg * SCALE
|
||||
wc = worst * SCALE
|
||||
dark = "#2196F3" if prio == "Normal" else "#FF9800"
|
||||
light = "#BBDEFB" if prio == "Normal" else "#FFE0B2"
|
||||
# 三档优先级配色:Normal 蓝 / BelowNormal 琥珀 / AboveNormal 绿(adcTask)
|
||||
dark = {"Normal": "#2196F3", "BelowNormal": "#FF9800",
|
||||
"AboveNormal": "#4CAF50"}[prio]
|
||||
light = {"Normal": "#BBDEFB", "BelowNormal": "#FFE0B2",
|
||||
"AboveNormal": "#C8E6C9"}[prio]
|
||||
vc = "#2E7D32" if verdict == "PASS" else "#C62828"
|
||||
|
||||
# 任务名(左侧)
|
||||
@@ -321,18 +341,25 @@ def gen_taskstack_svg():
|
||||
# 堆汇总(实测值)
|
||||
y += 8
|
||||
svg += f'<text x="{BAR_X}" y="{y}" class="label" fill="#555">'
|
||||
svg += f'堆总量: {HEAP_TOTAL}B (48KB, RW_CCM) 任务栈合计: {TOTAL_STACKS}B ({TOTAL_STACKS/1024:.1f}KB) + 内核栈 {512+1024}B</text>\n'
|
||||
svg += f'堆总量: {HEAP_TOTAL}B(configTOTAL_HEAP_SIZE=56KB,位于 RW_CCM)'
|
||||
svg += f' 任务栈合计: {TOTAL_STACKS}B(含 testTask 8192B)</text>\n'
|
||||
y += 16
|
||||
svg += f'<text x="{BAR_X}" y="{y}" class="label" fill="#555">'
|
||||
svg += f'实测: free={HEAP_FREE}B / min_ever={HEAP_MIN_EVER}B(2026-09-21,含 FTP 负载) 判定: 6/6 PASS(余量 ≥ max(1024B, 配置×30%))</text>\n'
|
||||
svg += f'产品构建 8 任务栈 = 39168B + 内核栈 {512+1024}B'
|
||||
svg += f' 实测: free={HEAP_FREE}B / min_ever={HEAP_MIN_EVER}B(2026-10-22)</text>\n'
|
||||
y += 16
|
||||
svg += f'<text x="{BAR_X}" y="{y}" class="label" fill="#555">'
|
||||
svg += '判定: 9/9 PASS(testTask 无实测,取静态最坏链)</text>\n'
|
||||
y += 24
|
||||
# 颜色图例
|
||||
svg += f' <rect x="{BAR_X}" y="{y}" width="10" height="10" fill="#2196F3" rx="2"/>\n'
|
||||
svg += f' <text x="{BAR_X+14}" y="{y+8}" class="legend-text" fill="#333">Normal 优先级</text>\n'
|
||||
svg += f' <rect x="{BAR_X+130}" y="{y}" width="10" height="10" fill="#FF9800" rx="2"/>\n'
|
||||
svg += f' <text x="{BAR_X+144}" y="{y+8}" class="legend-text" fill="#333">BelowNormal 优先级</text>\n'
|
||||
svg += f' <rect x="{BAR_X+290}" y="{y}" width="10" height="10" fill="#90A4AE" rx="2"/>\n'
|
||||
svg += f' <text x="{BAR_X+304}" y="{y+8}" class="legend-text" fill="#333">内核任务栈 (idle/timer)</text>\n'
|
||||
svg += f' <rect x="{BAR_X+300}" y="{y}" width="10" height="10" fill="#4CAF50" rx="2"/>\n'
|
||||
svg += f' <text x="{BAR_X+314}" y="{y+8}" class="legend-text" fill="#333">AboveNormal 优先级(adcTask)</text>\n'
|
||||
svg += f' <rect x="{BAR_X+520}" y="{y}" width="10" height="10" fill="#90A4AE" rx="2"/>\n'
|
||||
svg += f' <text x="{BAR_X+534}" y="{y+8}" class="legend-text" fill="#333">内核栈 idle/timer</text>\n'
|
||||
|
||||
svg += svg_footer()
|
||||
return svg
|
||||
|
||||
Reference in New Issue
Block a user