本帖最后由 Alden 于 2024-4-8 15:29 编辑
#申请原创# #技术资源#
在一些MCU应用中,需要MCU进入低功耗模式,关闭外设来减少功耗,延长待机时间。APM32的低功耗模式有以下三种:
1. 睡眠模式(Sleep Mode)
在睡眠模式下,CPU停止工作,但所有时钟和外设仍然工作,可以通过外部中断或者某些内部中断源唤醒CPU。这种模式适用于等待外设操作完成或外部事件的场景。
2. 停止模式(Stop Mode)
停止模式下,所有内核时钟停止,外设时钟可以选择性地停止,RAM和寄存器内容被保留。微控制器的功耗进一步降低,可以通过外部中断、内部中断源或者复位信号唤醒。唤醒后,微控制器从停止模式恢复到正常工作模式。
3. 待机模式(Standby Mode)
待机模式是STM32F103中功耗最低的模式。在此模式下,电源电压监控器(PVD)、低速外部晶振(LSE)、实时时钟(RTC)和唤醒引脚保持工作状态,而CPU和大部分外设的电源被关闭。RAM和寄存器的内容不被保留。可以通过RTC闹钟、外部中断引脚或复位信号唤醒微控制器。
低功耗模式的选择:
选择哪种低功耗模式取决于应用的具体需求,比如需要保持的外设活动、唤醒时间、功耗预算等。通常,待机模式的功耗最低,但从待机模式唤醒的时间也最长。睡眠模式虽然功耗相对较高,但能快速唤醒,适合需要快速响应外部事件的应用。
而在功耗测试时会面临选择进入哪个低功耗模式,实际功耗是多少,数据手册标的是否真实,测试环境是怎样的等等问题。
在APM32E103的数据手册中对功耗测试环境和低功耗模式下的功耗有进行说明:
其中比较重要的一点就是所有IO引脚都处于输入模式,这样能够避免引脚电平对功耗测试产生干扰。
数据手册中标注的低功耗电流见上表,接下来实际验证下APM32系列中STOP模式和STANDBY模式的功耗。
测试环境使用APM32F103ZET6 MINIBOARD开发板进行测试,在这款开发板中,VDD、VDDA、VREF引脚都采用跳帽隔开,可以方便的将万用表串入其中进行功耗测试。
休眠代码的配置在极海SDK的基础上修改,便于唤醒和测试。
void ALL_Peri_OFF(void)
{
GPIO_Config_T configStruct;
RCM_EnableAPB2PeriphClock(RCM_APB2_PERIPH_GPIOA|RCM_APB2_PERIPH_GPIOB|RCM_APB2_PERIPH_GPIOC|
RCM_APB2_PERIPH_GPIOD|RCM_APB2_PERIPH_GPIOE|RCM_APB2_PERIPH_GPIOF|RCM_APB2_PERIPH_GPIOG);
configStruct.pin = GPIO_PIN_2|GPIO_PIN_3|GPIO_PIN_4|GPIO_PIN_5|GPIO_PIN_6|GPIO_PIN_7|GPIO_PIN_8|GPIO_PIN_9|
GPIO_PIN_10|GPIO_PIN_11|GPIO_PIN_12|GPIO_PIN_13|GPIO_PIN_14|GPIO_PIN_15;
configStruct.mode = GPIO_MODE_ANALOG;
configStruct.speed = GPIO_SPEED_50MHz;
GPIO_Config(GPIOA, &configStruct);
configStruct.pin = GPIO_PIN_ALL;
configStruct.mode = GPIO_MODE_ANALOG;
configStruct.speed = GPIO_SPEED_50MHz;
// GPIO_Config(GPIOA, &configStruct);
GPIO_Config(GPIOB, &configStruct);
GPIO_Config(GPIOC, &configStruct);
GPIO_Config(GPIOD, &configStruct);
GPIO_Config(GPIOE, &configStruct);
GPIO_Config(GPIOF, &configStruct);
GPIO_Config(GPIOG, &configStruct);
}
int main(void)
{
RCM_EnableAPB1PeriphClock((RCM_APB1_PERIPH_T)(RCM_APB1_PERIPH_PMU | RCM_APB1_PERIPH_BAKR));
APM_MINI_LEDInit(LED2);
APM_MINI_LEDInit(LED3);
Usart_Init();
/* KEY1 \ KEY2 Set */
APM_MINI_PBInit(BUTTON_KEY1, BUTTON_MODE_EINT);
APM_MINI_PBInit(BUTTON_KEY2, BUTTON_MODE_EINT);
/* NVIC Priority Set */
NVIC_ConfigPriorityGroup(NVIC_PRIORITY_GROUP_1);
NVIC_EnableIRQRequest(EINT0_IRQn, 0, 1);
NVIC_EnableIRQRequest(EINT1_IRQn, 1, 1);
APM_MINI_LEDOn(LED2);
APM_MINI_LEDOff(LED3);
/* Enable PMU Periph Clock */
RCM_EnableAPB1PeriphClock(RCM_APB1_PERIPH_PMU);
PMU_Reset();
printf("Press KEY1 to Enter STOP Mode\r\n");
while (1)
{
if(stopflag==1)
{
stopflag=0;
printf("\r\nSystem have entered STOP mode\r\n");
printf("now, LED2 remains in the previous state\r\n");
printf("please press KEY2 or reset System to exit STOP mode\r\n");
ALL_Peri_OFF();
PMU_EnterSTOPMode(PMU_REGULATOR_LOWPOWER, PMU_STOP_ENTRY_WFI);
// PMU_EnableWakeUpPin();
// PMU_EnterSTANDBYMode();
SystemInit();
Usart_Init();
APM_MINI_LEDInit(LED2);
APM_MINI_LEDInit(LED3);
APM_MINI_LEDOff(LED3);
/* Wait for system init */
Delay(0xff);
printf("Wake up from STOP Mode\r\n");
}
else
{
Delay(0x7FFFFF);
printf("mcu RUN\r\n");
APM_MINI_LEDToggle(LED2);
}
}
}
进入休眠前将IO除了需要用的按键外都配置成模拟输入模式来避免IO口的影响。
PA0、PA1引脚中断来判断进入推出低功耗模式。
void Eint1_Isr(void)
{
if (EINT_ReadIntFlag(KEY1_BUTTON_EINT_LINE) != RESET)
{
APM_MINI_LEDOn(LED3);
APM_MINI_LEDOff(LED2);
/* Enter STOP Mode in WFI*/
stopflag=1;
EINT_ClearIntFlag(KEY1_BUTTON_EINT_LINE);
}
}
void Eint0_Isr(void)
{
if (EINT_ReadIntFlag(KEY2_BUTTON_EINT_LINE) != RESET)
{
EINT_ClearIntFlag(KEY2_BUTTON_EINT_LINE);
}
}
通过main中屏蔽来测试stop模式还是standby模式。
stop模式的实测:
VDD:36.4uA VDDA:4.3uA
standby模式实测:
VDD:0uA VDDA:3uA
与规格书中的3.3V 25°常温常压的数据基本一直,证明测试方式的可靠性和规格书的真实性都是没问题的。
APM32E10x_SDK_V1.2-stop.zip
(3.73 MB)
|
测试APM32 MINI开发板在不同低功耗模式下的功耗表现,以及测量功耗的方法和注意事项