电源管理与低功耗设计
本文档介绍 AD16N 平台(fw-AD16N_GP-MCU_SDK)的电源管理与低功耗设计,涵盖应用层电源管理模块 app_power_mg 的电压监测、低电告警、自动关机机制,以及 CPU 层电源抽象接口 power_interface 的组成与设计意图。
Purpose and Scope
本页面聚焦 AD16N SDK 中与电源管理、低功耗相关的完整链路:
- 应用层电源管理:
app_power_mg.c / app_power_mg.h实现的 VBAT 电压采样、LVD(低电压检测)警戒线、低电计数滤波、自动关机消息上报; - CPU 层电源抽象:
power_interface.h聚合的 P33 寄存器、GPIO 电源端口、电源 API、唤醒与复位模块的接口划分; - 配置与扩展:
app_config.h中的TCFG_CHARGE_ENABLE、TCFG_SHUTDOWN_TIME等配置项如何影响电源行为。
以下内容不在本页范围,属于同仓库其他能力页的主题,仅在必要时交叉引用:充电管理(charge.h / charge_get_lvcmp_det())的完整充电算法、ADC 驱动(adc_api.h)的采样实现细节、按键与消息系统(msg.h)的通用机制。
Overview
在电池供电的 MCU 产品(如 TWS 耳机、便携音箱、遥控器)中,电源管理决定了产品的续航、安全性与用户体验。AD16N 的电源管理采用分层设计:
- 硬件层:PMU(电源管理单元)内部集成 LVD 比较器与 VBAT 采样通道,通过 P33 寄存器控制;
- CPU 层:
power_api/power_port/power_wakeup/power_reset等模块封装寄存器读写、GPIO 电源控制、唤醒源配置与复位逻辑; - 应用层:
app_power_mg周期性读取 VBAT 电压,与 LVD 警戒线比较,经过连续计数滤波后触发低电告警与关机消息,避免误关机。
低功耗设计的关键意图(WHY):
- 使用 LVD 作为警戒线而非固定值:LVD 电压随芯片批次、温度存在差异,
lvd_warning_voltage = lvd_voltage + 300在 LVD 阈值基础上加 300mV 裕量,保证在真正触发 LVD 复位之前应用已有足够时间保存状态并关机; - 充电期间禁止低电关机:充电时 VBAT 会被充电器拉高/波动,直接判断电压会导致误关机,因此通过
CHARGE_IN_DET检测充电插入状态并跳过低电判断; - 连续计数防抖:电压短暂跌落(如射频发射瞬间的电流尖峰)不应触发关机,
app_power_scan使用low_power_cnt连续计数,只有持续低电达到TCFG_SHUTDOWN_TIME才上报MSG_POWER_OFF。
Architecture
flowchart TD
subgraph sg_App["应用层 (App BSP Common)"]
AppPowerMg["app_power_mg.c<br/>电压扫描/低电关机"]
AppConfig["app_config.h<br/>TCFG_SHUTDOWN_TIME / TCFG_CHARGE_ENABLE"]
Msg["msg.h<br/>post_msg(MSG_POWER_OFF)"]
end
subgraph sg_Cpu["CPU 层抽象 (power_interface.h)"]
PowerApi["asm/power/power_api.h<br/>电源/低功耗 API"]
PowerPort["asm/power/power_port.h<br/>GPIO 电源端口"]
PowerWakeup["asm/power/power_wakeup.h<br/>唤醒源"]
PowerReset["asm/power/power_reset.h<br/>复位"]
P33["asm/power/p33.h<br/>PMU 寄存器"]
end
subgraph sg_Hw["硬件层"]
PMU["PMU / LVD / VBAT 采样通道"]
Charge["charge.h<br/>充电检测 lvcmp"]
ADC["adc_api.h<br/>AD_CH_PMU_VBAT"]
end
AppPowerMg -->|"读电压"| ADC
AppPowerMg -->|"充电检测"| Charge
AppPowerMg -->|"读配置"| AppConfig
AppPowerMg -->|"低电持续超时"| Msg
AppPowerMg -->|"调用"| PowerApi
PowerApi --> P33
PowerPort --> P33
PowerWakeup --> P33
PowerReset --> P33
P33 --> PMU
架构说明:
app_power_mg.c是应用层唯一的电源管理入口,通过power_interface.h间接使用 CPU 层能力,与应用业务(消息、按键)解耦——它只负责"测电压 → 判低电 → 发消息",不直接操作寄存器;power_interface.h是 CPU 层对外唯一头文件(接口门面),内部按职责聚合p33.h(寄存器定义)、power_port.h(GPIO 电源控制)、power_api.h(电源/低功耗 API)、power_wakeup.h(唤醒)、power_reset.h(复位)。这种聚合设计使应用层只需包含一个头文件即可获得全部电源能力,同时保持各子模块可独立演进;- 硬件层(PMU、ADC、充电检测)通过
adc_api.h与charge.h暴露给应用层,应用层不感知具体寄存器地址。
Source: app_power_mg.c、power_interface.h
应用层电源管理实现解析
应用层电源管理全部实现在 sdk/apps/app/bsp/common/power_manage/ 目录下,仅两个文件:app_power_mg.c(实现)与 app_power_mg.h(对外声明与低电阈值宏)。
模块初始化 app_power_init()
void app_power_init(void)
{
low_power_warning_init();
adc_add_sample_ch(AD_CH_PMU_VBAT);
app_power_scan();
}
Source: app_power_mg.c
初始化做三件事,顺序有明确意图:
low_power_warning_init():先建立低电警戒线。在LVD_WARNING_FOR_LOW_POWER == 1时该宏展开为lvd_warning_init(),它读取 PMU 的 LVD 阈值并加上 300mV 裕量:static void lvd_warning_init(void) { extern u32 get_lvd_vol(void); u32 lvd_voltage = get_lvd_vol(); lvd_warning_voltage = lvd_voltage + 300; log_info("lvd_warning_voltage : %d\n", lvd_warning_voltage); }Source: app_power_mg.c
LVD(Low Voltage Detector)是硬件比较器,当 VBAT 跌到 LVD 阈值时芯片会触发复位。软件警戒线比硬件阈值高 300mV,就是为了在硬件复位前给应用留出关机窗口——这是"软件先于硬件动作"的低功耗设计核心思想。若不希望依赖 LVD(例如硬件未校准),可在
app_power_mg.h中把LVD_WARNING_FOR_LOW_POWER改为 0,此时警戒线退化为固定值3300(3.3V),low_power_warning_init展开为空操作。adc_add_sample_ch(AD_CH_PMU_VBAT):向 ADC 驱动注册 VBAT 采样通道。AD_CH_PMU_VBAT是 PMU 内置的电池电压采样通道,采样结果由 ADC 驱动周期性刷新,app_power_scan每次直接读最新值,不阻塞等待。app_power_scan():立即执行一次扫描,使vbat_voltage全局变量在模块初始化完成时就有有效初值,避免上层首次读取拿到 0。
周期扫描 app_power_scan() —— 低电检测与防抖
void app_power_scan(void)
{
static u16 low_power_cnt = 0;
u16 vol = adc_get_voltage(AD_CH_PMU_VBAT) * 4;
if (0 == vol) {
return;
}
/* log_info("vbat voltage : %d", vol); */
if ((vol <= LOW_POWER_VOL) && (0 == CHARGE_IN_DET)) {
//充电时不进入低功耗
low_power_cnt++;
if (low_power_cnt == (TCFG_SHUTDOWN_TIME / 500)) {
log_error(LOW_POWER_LOG);
post_msg(1, MSG_POWER_OFF);
}
} else {
low_power_cnt = 0;
}
vbat_voltage = vol;
}
Source: app_power_mg.c
逐行分析:
vol = adc_get_voltage(AD_CH_PMU_VBAT) * 4:ADC 采样值需乘以 4 得到毫伏(mV)单位的真实电压。vol == 0时直接返回,防止 ADC 尚未就绪(返回 0)时误判为"0V 超低电"而累积计数;- 低电条件
(vol <= LOW_POWER_VOL) && (0 == CHARGE_IN_DET):LOW_POWER_VOL在默认配置下即lvd_warning_voltage(LVD + 300mV);CHARGE_IN_DET在TCFG_CHARGE_ENABLE == 1时是charge_get_lvcmp_det()(充电器插入检测),充电时强制跳过低电判断。这是因为充电过程中电池电压会被充电器抬高/波动,若按空载电压判断会误关机;
- 连续计数滤波:低电时
low_power_cnt++,非低电时清零。只有连续低电计数达到TCFG_SHUTDOWN_TIME / 500才触发动作。该公式隐含app_power_scan的调用周期为 500ms:TCFG_SHUTDOWN_TIME以毫秒为单位配置"持续低电多久后关机",除以 500 得到需要连续低电的扫描次数。例如默认关机延时 3 秒时,需要连续 6 次(3 秒)扫描均判定低电; - 动作:
post_msg(1, MSG_POWER_OFF):通过消息系统上报关机消息(1为消息优先级),由应用主循环统一处理关机流程。电源模块本身不执行关机,只负责"汇报"——这种事件驱动设计使关机动作(保存参数、关蓝牙、关外设)可以复用应用已有的消息处理链路; vbat_voltage = vol:无论是否低电,每次都刷新全局电压值,供app_power_get_vbat()查询。
电压读取 app_power_get_vbat()
u16 app_power_get_vbat(void)
{
return vbat_voltage;
}
Source: app_power_mg.c
该接口返回最近一次扫描缓存的 VBAT 电压(mV),供 UI 显示电量、电量分级等业务使用。由于电压由周期扫描刷新,业务侧读取是 O(1) 且无阻塞的,不会引入额外 ADC 占用。
低电阈值宏定义
#define LVD_WARNING_FOR_LOW_POWER 1//1:LVD作为低电警戒线 0:固定值作为警戒线
#if LVD_WARNING_FOR_LOW_POWER
#define LOW_POWER_VOL lvd_warning_voltage
#define LOW_POWER_LOG "Waring!!! Vbat is near to lvd!\n"
#define low_power_warning_init lvd_warning_init
#else
#define LOW_POWER_VOL 3300//3.3V
#define LOW_POWER_LOG "low power\n"
#define low_power_warning_init
#endif
//TODO by bt
#define LOW_POWER_WARN_VAL 240
#define LOW_POWER_OFF_VAL 220
Source: app_power_mg.h
设计要点:
- 用编译期宏开关切换两种警戒线策略,避免运行期分支开销:默认走 LVD 动态警戒线(更精确、自适应批次差异),固定值 3300mV 作为后备方案;
LOW_POWER_WARN_VAL(240)与LOW_POWER_OFF_VAL(220)标注TODO by bt,从命名看是电量百分比级别的"低电提醒/强制关机"分级阈值,当前版本未在app_power_scan中使用,属于预留扩展点;LOW_POWER_LOG区分两种策略下的告警日志文案,便于从日志直接判断当前生效的是哪种警戒线策略。
核心流程:从电压采样到自动关机
app_power_scan 由应用主循环周期调用(典型周期 500ms),整个低电关机链路如下:
sequenceDiagram
participant App as 应用主循环
participant Mg as app_power_scan
participant ADC as adc_api
participant PMU as PMU/LVD
participant Chg as charge (lvcmp)
participant Msg as 消息系统
App->>Mg: 周期调用 (500ms)
Mg->>ADC: adc_get_voltage(AD_CH_PMU_VBAT)
ADC-->>Mg: 采样值
Mg->>Mg: vol = 采样值 * 4 (mV)
alt vol == 0
Mg-->>App: return (ADC未就绪)
else vol <= LOW_POWER_VOL
Mg->>Chg: charge_get_lvcmp_det()
alt 充电中
Mg->>Mg: low_power_cnt = 0
else 未充电
Mg->>Mg: low_power_cnt++
alt low_power_cnt == TCFG_SHUTDOWN_TIME / 500
Mg->>Msg: log_error + post_msg(1, MSG_POWER_OFF)
Msg-->>App: 应用处理关机流程
end
end
else 电压正常
Mg->>Mg: low_power_cnt = 0
end
Mg->>Mg: vbat_voltage = vol
流程关键点:
- 每次扫描先读 ADC 再判断,
vol == 0直接短路返回,这是对 ADC 采样未就绪的防御; - 低电判断是两重条件:电压低于警戒线 且 未插入充电器,二者缺一不可;
- 关机触发是持续条件而非瞬时条件:
low_power_cnt连续计数到TCFG_SHUTDOWN_TIME / 500才post_msg(1, MSG_POWER_OFF),任何一次电压恢复都会清零计数——这是典型的软件防抖(debounce)设计,用于滤除射频脉冲、电机启停等造成的瞬时电压跌落; - 电源模块只发消息不执行关机,实际关机动作由应用在消息处理中完成,保证与业务状态(如蓝牙连接、参数保存)安全协同。
Usage Examples
示例 1:初始化电源管理模块
在应用初始化阶段调用一次,注册 VBAT 采样通道并建立 LVD 警戒线:
void app_power_init(void)
{
low_power_warning_init();
adc_add_sample_ch(AD_CH_PMU_VBAT);
app_power_scan();
}
Source: app_power_mg.c
示例 2:在周期任务中扫描电压
将 app_power_scan 挂到 500ms 周期任务(如定时器/主循环),低电检测与 vbat_voltage 缓存都会随之更新:
void app_power_scan(void)
{
static u16 low_power_cnt = 0;
u16 vol = adc_get_voltage(AD_CH_PMU_VBAT) * 4;
if (0 == vol) {
return;
}
if ((vol <= LOW_POWER_VOL) && (0 == CHARGE_IN_DET)) {
//充电时不进入低功耗
low_power_cnt++;
if (low_power_cnt == (TCFG_SHUTDOWN_TIME / 500)) {
log_error(LOW_POWER_LOG);
post_msg(1, MSG_POWER_OFF);
}
} else {
low_power_cnt = 0;
}
vbat_voltage = vol;
}
Source: app_power_mg.c
示例 3:读取当前电池电压(用于电量显示)
UI 或电量分级逻辑可直接读取缓存的 VBAT 电压,无需再次触发 ADC 采样:
u16 app_power_get_vbat(void)
{
return vbat_voltage;
}
Source: app_power_mg.c
示例 4:切换低电警戒线策略
在 app_power_mg.h 中修改编译期开关,可将警戒线从"LVD 动态值"切换为"固定 3.3V":
#define LVD_WARNING_FOR_LOW_POWER 1//1:LVD作为低电警戒线 0:固定值作为警戒线
#if LVD_WARNING_FOR_LOW_POWER
#define LOW_POWER_VOL lvd_warning_voltage
#define LOW_POWER_LOG "Waring!!! Vbat is near to lvd!\n"
#define low_power_warning_init lvd_warning_init
#else
#define LOW_POWER_VOL 3300//3.3V
#define LOW_POWER_LOG "low power\n"
#define low_power_warning_init
#endif
Source: app_power_mg.h
Configuration Options
应用层电源管理的可配置项如下,其中 TCFG_* 宏定义于 app_config.h,LVD_WARNING_FOR_LOW_POWER 定义于 app_power_mg.h:
| 配置项 | 类型 | 默认值 | 说明 |
|---|---|---|---|
LVD_WARNING_FOR_LOW_POWER | 宏开关 | 1 | 1:以 LVD 动态电压 + 300mV 作为低电警戒线;0:以固定值 3300mV 作为警戒线 |
LOW_POWER_VOL | 宏 | lvd_warning_voltage / 3300 | 低电判定阈值(mV),由 LVD_WARNING_FOR_LOW_POWER 决定展开值 |
LOW_POWER_LOG | 宏 | "Waring!!! Vbat is near to lvd!\n" | 触发低电关机时打印的告警日志 |
low_power_warning_init | 宏 | lvd_warning_init(或空) | 警戒线初始化函数,固定值策略下为空操作 |
LOW_POWER_WARN_VAL | 宏 | 240 | 预留的低电提醒阈值(TODO by bt,当前未使用) |
LOW_POWER_OFF_VAL | 宏 | 220 | 预留的强制关机阈值(TODO by bt,当前未使用) |
TCFG_SHUTDOWN_TIME | 宏(ms) | 由 app_config.h 定义 | 持续低电多长时间(毫秒)后触发 MSG_POWER_OFF;app_power_scan 以 500ms 为周期,将其除以 500 得到连续低电计数目标 |
TCFG_CHARGE_ENABLE | 宏开关 | 由 app_config.h 定义 | 1 时启用充电检测(CHARGE_IN_DET = charge_get_lvcmp_det()),充电中禁止低电关机;0 时 CHARGE_IN_DET 恒为 0 |
配置联动关系:TCFG_SHUTDOWN_TIME 必须与 app_power_scan 的实际调用周期匹配。若扫描周期不是 500ms,TCFG_SHUTDOWN_TIME / 500 的换算将失真,需要在移植时同步调整。
API Reference
void app_power_init(void)
初始化电源管理模块:建立低电警戒线、注册 VBAT ADC 采样通道,并执行首次电压扫描。
- 调用时机:应用初始化阶段,早于首次使用
app_power_get_vbat; - 副作用:向 ADC 驱动注册
AD_CH_PMU_VBAT通道;写入全局vbat_voltage。
Source: app_power_mg.c、app_power_mg.h
void app_power_scan(void)
周期扫描 VBAT 电压,执行低电判断与防抖计数,达到条件时 post_msg(1, MSG_POWER_OFF)。
- 参数:无;
- 返回:无;
- 行为:更新全局
vbat_voltage(mV);低电且未充电时累加low_power_cnt,连续计数达到TCFG_SHUTDOWN_TIME / 500后打印LOW_POWER_LOG并发送关机消息;电压恢复或充电中清零计数; - 边界:ADC 返回 0 时直接返回,不更新电压、不计数。
Source: app_power_mg.c、app_power_mg.h
u16 app_power_get_vbat(void)
返回最近一次扫描缓存的 VBAT 电压(mV)。
- 参数:无;
- 返回:
vbat_voltage,单位 mV;app_power_init之前或扫描尚未成功时可能为 0。
Source: app_power_mg.c、app_power_mg.h
内部函数与依赖接口
| 名称 | 类型 | 说明 |
|---|---|---|
lvd_warning_init() | static | 读取 get_lvd_vol()(PMU LVD 阈值)并 +300mV 得到警戒线 |
get_lvd_vol() | extern u32 | 获取硬件 LVD 阈值,来自 CPU 层电源 API |
adc_get_voltage(AD_CH_PMU_VBAT) | ADC API | 读取 VBAT 采样值,需乘以 4 换算为 mV |
charge_get_lvcmp_det() | 充电 API | 充电器插入检测(TCFG_CHARGE_ENABLE==1 时启用) |
post_msg(1, MSG_POWER_OFF) | 消息 API | 上报关机消息,优先级 1 |
CPU 层电源抽象
CPU 层通过 power_interface.h 对外暴露统一电源接口,它本身不实现逻辑,而是聚合五个职责清晰的子模块:
//p33寄存器
#include "asm/power/p33.h"
//gpio相关
#include "asm/power/power_port.h"
//电源、低功耗
#include "asm/power/power_api.h"
//唤醒
#include "asm/power/power_wakeup.h"
//复位
#include "asm/power/power_reset.h"
Source: power_interface.h
各子模块职责划分:
p33.h:PMU(电源管理单元)P33 寄存器定义,是所有电源行为的硬件基础——LVD 配置、稳压器控制、VBAT 采样的使能都通过 P33 寄存器完成;power_port.h:GPIO 电源端口控制,管理 VDDIO 等电源域 GPIO 的上下电,用于外设电源的精细控制(降低静态漏电);power_api.h:电源与低功耗核心 API(如get_lvd_vol、进入低功耗/关机等),是应用层与硬件交互的主要入口;power_wakeup.h:唤醒源配置(GPIO 唤醒、定时器唤醒、充电插入唤醒等),定义系统从低功耗状态恢复的途径;power_reset.h:复位管理(软复位、看门狗复位等)。
仓库中该抽象存在 uc03(sdk/apps/include_lib/cpu/uc03/asm/power/)与 bd49(sdk/apps/include_lib/cpu/bd49/asm/power/)两个 CPU 变体,以及 sdk/apps/app/bsp/cpu/uc03/ 下的 power_api.c、power_port.c 实现。本页不展开 CPU 层各 API 的具体寄存器操作——那属于芯片 BSP 层文档主题;此处仅说明接口边界:应用层代码只依赖 power_interface.h 聚合出的稳定接口,CPU 更换时电源管理逻辑无需改动。
Failure Modes, Edge Cases & Concurrency
电压读数异常(0 值)
ADC 通道尚未就绪或采样失败时 adc_get_voltage 可能返回 0,app_power_scan 在 vol == 0 时直接 return。这是刻意的防御:若把 0 当作真实电压参与判断,会立刻被判定为"极低电压"并可能误触发关机。代价是本次扫描不刷新 vbat_voltage,上层读取到的是上一次缓存值——对 UI 显示无影响,对低电判断只是顺延一个周期。
充电状态与低电判断的竞争
CHARGE_IN_DET(charge_get_lvcmp_det)在 TCFG_CHARGE_ENABLE 关闭时恒为 0,此时充电中也可能触发低电关机。因此启用充电功能的产品必须开启 TCFG_CHARGE_ENABLE,否则会出现"插着充电器却因电压波动关机"的异常。另一个边界是充电器刚插入、lvcmp 尚未稳定时的短暂窗口——由于低电判断要求连续 TCFG_SHUTDOWN_TIME / 500 次低电,单次误判会被后续清零计数抵消,防抖机制天然覆盖该窗口。
电压抖动与防抖计数
射频发射、电机启动等瞬态负载会造成 VBAT 数十至数百毫伏的跌落。若警戒线设置过近(裕量不足 300mV),低电计数可能累积;但只要有一次扫描电压高于警戒线,low_power_cnt 即清零,因此误关机概率与扫描周期 × 低电持续时间成正比。调大 TCFG_SHUTDOWN_TIME 可增强抗抖动,但会延长真实低电下的关机响应时间,需要按产品场景权衡。
并发与可重入性
app_power_scan 使用 static u16 low_power_cnt 与 static u16 vbat_voltage,无锁、非可重入。它由单一周期任务(主循环/定时器)串行调用,模块内部不创建线程。若在中断上下文调用 app_power_scan,与主循环调用之间会存在对 vbat_voltage / low_power_cnt 的竞争,应在设计上保证只有一个调用者。post_msg 本身是线程安全的消息投递接口,故从扫描中发消息无竞态问题。
关机消息的异步性
app_power_scan 只投递 MSG_POWER_OFF 就返回,不等待关机完成。若应用在消息处理中执行耗时的参数保存、蓝牙断开等操作,期间系统仍可能因电压继续下降触发硬件 LVD 复位。设计上应让消息处理路径尽量短,或利用 LVD 的 300mV 裕量窗口完成收尾。
Performance & Operational Considerations
- ADC 开销:
AD_CH_PMU_VBAT由 ADC 驱动后台采样,app_power_scan每次只做一次寄存器读与乘法/比较,CPU 开销可忽略;以 500ms 周期扫描,功耗占比极低,适合常驻运行; - 日志行为:低电关机时打印
log_error(LOW_POWER_LOG),正常运行时adc_get_voltage附近的log_info被注释掉,避免高频日志占用串口与 Flash,调试时可临时打开; - 观测手段:开机日志中的
lvd_warning_voltage : xxx(mV)可用于确认警戒线是否符合硬件 LVD 实际值;若LOW_POWER_LOG出现即代表系统已进入关机流程; - 集成约束:
TCFG_SHUTDOWN_TIME / 500的换算假设扫描周期固定为 500ms,移植到其他周期调度时需同步修改,否则关机延时将偏离配置值。
Extension Points
- 警戒线策略切换:通过
app_power_mg.h的LVD_WARNING_FOR_LOW_POWER宏,可在 LVD 动态警戒线与固定 3.3V 警戒线之间切换,适配不同硬件校准方案; - 预留阈值
LOW_POWER_WARN_VAL/LOW_POWER_OFF_VAL:标注TODO by bt的两级阈值(240/220,疑似电量百分比),可用于实现"先提醒、后关机"的两级低电策略,当前版本未接入,是官方预留的扩展点; - 充电检测注入:
CHARGE_IN_DET的宏抽象使充电状态来源可替换(charge_get_lvcmp_det或其他 GPIO 检测),不修改扫描逻辑即可适配不同充电方案; - 关机动作自定义:模块只发
MSG_POWER_OFF,关机前需要保存的状态、需要关闭的外设均可在应用的消息处理器中扩展,无需改动电源模块。
Tests
仓库内 app_power_mg 为轻量应用层模块,未发现独立的单元测试文件。其行为可通过以下方式验证:
- 静态验证:检查
lvd_warning_voltage日志是否等于get_lvd_vol() + 300; - 动态验证:用可调电源模拟 VBAT,从正常工作电压缓慢下降,确认:①低于警戒线但未到
TCFG_SHUTDOWN_TIME时回升电压不会关机(防抖生效);②持续低电达到配置时间后打印LOW_POWER_LOG并收到MSG_POWER_OFF;③插入充电器后即使电压低于警戒线也不关机; - 回归关注点:
vol == 0分支、low_power_cnt清零路径、vbat_voltage缓存更新。
Related Links
- app_power_mg.c — 应用层电源管理实现
- app_power_mg.h — 低电阈值宏与对外声明
- power_interface.h (uc03) — CPU 层电源接口聚合
- power_api.c (uc03) — CPU 层电源 API 实现(BSP 层主题)
- power_port.c (uc03) — GPIO 电源端口实现(BSP 层主题)
- 相关能力页:充电管理(
charge.h/TCFG_CHARGE_ENABLE)、ADC 采样(adc_api.h/AD_CH_PMU_VBAT)、消息系统(msg.h/MSG_POWER_OFF)