内存与 CPU 相互纠缠:内存不足 → alloc/free 频繁 → CPU 升高 → 帧率下降;CPU 过载 → Cache 同步不及时 → DDR 带宽争抢 → 延迟跳变。以下策略从根源打破这个循环。
一、内存优化
1. 关闭未使用后端
UCP 启动时为所有后端创建调度线程并预分配 ION 内存,即使未使用。每个关闭的后端省 ~数百 KB。
平台无硬件的后端不创建线程,无需手动关闭;硬件存在但不用的仍需设 0。
2. 启用 LRU 缓存
BPU 内存使用前需对齐/映射,频繁 alloc/free 致 CPU 升高 + 碎片。LRU 缓存已释放内存复用。
仅 NN 模块生效;hbUCPFree 后内存延迟回收,RSS 不立即下降是正常的。生命周期与模型一致时无需启用。
3. Task Handle 复用
小模型(< 2 ms/帧)每帧创建/销毁 task handle 开销占比大,复用可消除。
4. Tensor 内存复用
每帧 alloc/free → CPU 开销 + 碎片。一次分配循环复用是根本优化。
与 LRU 组合最佳:复用避免 alloc/free,LRU 兜底偶尔释放后的快速复用。
5. L2M 静态映射(J6P/H)
J6P/H 多核 BPU 共享 L2M,热数据固定其中可减 DDR 搬运。单核平台无此硬件。
仅 J6P/H;与抢占互斥;多进程需配相同值;上限查 /sys/kernel/debug/ion/heaps/custom。
6. Lazy hlog
仅链接 libhbucp 不调用时,hlog 预分配浪费内存。
7. Lazy HBTL
OE 新版本:无 CPU 算子模型不加载 HBTL。升级 OE 3.8.1 及以上版本即可。
二、CPU 负载优化
1. 关闭未使用后端的调度线程
线程 | 关闭 |
DSP-Recv | ENABLE_DSP=0 |
Sync-Scheduler | 关对应后端 |
Codec-Scheduler | ENABLE_JPU=0 + ENABLE_VPU=0 |
CPU-OP-Process | ENABLE_CPU=0(无 CPU 算子时) |
2. 提升调度线程优先级
需 root 或 CAP_SYS_NICE。
3. 谨慎使用抢占
抢占触发上下文保存/恢复,产生 DDR 开销拖慢全局。默认用普通优先级(0~253);安全关键场景才启用抢占,配合 max_time_per_fc。max_time_per_fc 为 BPU function-call 最大时长(μs),决定抢占窗口。无抢占不设;有抢占建议 1000~2000 μs。
优先级 | 范围 | 行为 |
🟢 普通 | 0~253 | 排队,不可抢占 |
🟠 High | 254 | 可抢占普通 |
🔴 Urgent | 255 | 可抢占普通及 High |
4. CPU 算子线程池
无 CPU 算子设 0;有 CPU 算子 ≤ CPU 核数 × 1/2。
