4、低功耗MCU选型与配置:对比STM32L0、STM32U5、ESP32-S3等芯片的功耗模式

做内窥镜最头疼的是什么?我个人觉得,不是图像处理,也不是无线传输,而是——电池。你想想看,一根管子伸进人体,总不能拖根电源线吧?所以MCU的功耗,直接决定了这台设备能用几分钟。

今天咱们就来聊聊三款主流低功耗MCU:STM32L0、STM32U5、ESP32-S3。我会结合自己的项目经验,把它们的功耗模式掰开揉碎了讲清楚。

4.1 三款芯片的功耗模式对比

先看一张表,心里有个底。我当年选型时,就是靠这张表拍板的。

功耗模式STM32L0STM32U5ESP32-S3
Run(运行)~88 µA/MHz~19 µA/MHz~160 µA/MHz(双核)
Sleep(睡眠)~3.4 µA~1.2 µA~130 µA(保留WiFi)
Stop(停止)~1.3 µA~0.6 µA~5 µA(深度睡眠)
Standby(待机)~0.27 µA~0.16 µA~2.5 µA(RTC保留)

关键发现:STM32U5在Run模式下的功耗只有L0的1/4不到。但ESP32-S3的Standby模式功耗偏高,不适合需要长时间待机的内窥镜场景。

4.2 各模式详解与实战经验

4.2.1 Run模式——别让CPU空转

很多新手一上来就开最高主频。我刚开始做内窥镜时也犯过这个错。其实内窥镜大部分时间在等待指令,CPU跑那么快干嘛?

我的习惯是:按需调频。图像采集时跑32MHz,空闲时降到2MHz。STM32U5支持动态电压调节,降频的同时还能降压,功耗能再降30%。

小技巧:用HAL库的HAL_RCC_ClockConfig()函数,可以在运行时切换系统时钟源。我一般把HSI(内部高速振荡器)作为默认源,需要高精度时再切到HSE(外部晶振)。

4.2.2 Sleep模式——关掉CPU,保留外设

Sleep模式下,CPU内核停了,但外设还在跑。比如ADC还在采集图像数据,DMA还在搬运。这时候功耗能降到Run模式的1/10。

我曾经在STM32L0上做过测试:用Sleep模式配合DMA采集图像,比用Run模式轮询采集,功耗降低了65%。

// STM32L0进入Sleep模式示例
HAL_SuspendTick();          // 暂停系统滴答定时器
__WFI();                    // 等待中断唤醒
HAL_ResumeTick();           // 恢复滴答定时器

注意:进入Sleep前,记得把不用的外设时钟关掉。我见过有人进了Sleep,但USART时钟没关,白白多耗了2µA。

4.2.3 Stop模式——保留RAM,关掉大部分时钟

Stop模式是内窥镜待机时的首选。RAM数据保留,但所有时钟都停了。唤醒后能快速恢复运行。

STM32U5的Stop 2模式特别适合我们。它保留了SRAM1和SRAM2,但把SRAM3(通常存图像缓存)给关了。这样功耗从1.2µA降到0.6µA。

嗯,这里要注意:唤醒时间。STM32L0从Stop唤醒需要5µs,而U5只要3µs。对于需要快速响应的内窥镜,这2µs的差距可能决定图像会不会丢帧。

4.2.4 Standby模式——最低功耗,但代价最大

Standby模式下,除了RTC和备份寄存器,其他全部断电。功耗最低,但唤醒等于复位。

我一般只在关机前用这个模式。比如用户按了电源键,系统保存最后一张图像到Flash,然后进入Standby。下次开机,从Bootloader重新启动。

避坑指南:我曾经在ESP32-S3上用过Standby模式,结果发现WiFi模块没完全断电,功耗还有2.5µA。后来查手册才知道,要调用esp_deep_sleep_disable_rom_logging()才能彻底关掉。嗯,教训深刻。

4.3 时钟树配置——降低动态功耗的核心

动态功耗跟频率成正比,跟电压的平方成正比。说白了,降频降压是王道。

4.3.1 选择合适的时钟源

内窥镜对时钟精度要求不高(图像采集允许±5%误差),所以尽量用内部振荡器。

  • HSI(内部高速):16MHz,精度±1%,适合日常运行
  • LSI(内部低速):32kHz,精度±5%,适合RTC
  • HSE(外部晶振):8MHz,精度±0.01%,只在需要高精度时用

我的做法是:默认用HSI,只有在校准或无线同步时才切到HSE。这样能省掉外部晶振的功耗(约0.5µA)。

4.3.2 关闭未使用的外设时钟

这是最容易被忽略的。STM32的每个外设都有独立的时钟门控。不用的外设,时钟一定要关掉。

// 关闭不用的外设时钟示例
__HAL_RCC_USART1_CLK_DISABLE();   // 不用串口就关掉
__HAL_RCC_TIM2_CLK_DISABLE();     // 不用定时器就关掉
__HAL_RCC_ADC1_CLK_DISABLE();     // 不用ADC就关掉

我的习惯:在初始化函数里,先全部关闭,然后按需打开。这样不会漏掉。我曾经在STM32U5上试过,关掉所有不用的外设时钟后,Run模式功耗从19µA/MHz降到了14µA/MHz。

4.3.3 使用PLL分频降低总线频率

内窥镜的CPU不需要一直跑在最高频。图像处理时,CPU跑32MHz就够了。但DMA搬运数据时,AHB总线可以降到8MHz。

STM32U5的时钟树支持独立配置AHB、APB1、APB2的分频系数。我一般这样配:

  • CPU:32MHz(图像处理)或 2MHz(空闲)
  • AHB:16MHz(DMA搬运)
  • APB1:8MHz(低速外设如I2C)
  • APB2:16MHz(高速外设如SPI)

这样动态功耗能再降20%左右。

4.4 实战建议:内窥镜场景下的选型

说了这么多,到底选哪款?我直接给结论:

  • STM32L0:适合成本敏感、功能简单的内窥镜。比如一次性内窥镜,用完就扔。功耗够用,价格便宜。
  • STM32U5:适合高端内窥镜。比如需要高清图像、无线传输的。功耗低,性能强,但价格贵。
  • ESP32-S3:适合需要WiFi/蓝牙的内窥镜。但Standby功耗偏高,不适合长时间待机。我一般只在需要无线传输时才用它。

最后说一句:选型不是看数据手册上的数字,而是看你的实际场景。我见过有人选了STM32U5,结果因为没优化时钟树,功耗比L0还高。嗯,工具再好,也得会用。

下一章,咱们聊聊如何用RTOS的任务调度来进一步降低功耗。到时候我会分享一个真实案例:如何把内窥镜的待机功耗从50µA降到5µA。