客户产品中使用STM32F401RB,产品本身已经烧录固件,并在功能实现上无问题。在想更新固件时,PC软件无法识别设备,DFU功能失败。
- 首先检查USB硬件线路问题。
客户反馈,本身产品已经有固件,在正常模式下(BOOT0 = 0 ,BOOT1 = 0时)功能完整,USB功能可以正常使用。说明USB线路是正常。
备注:如果没有现成固件作为测试,可以使用STM32CubeMX工具生成一个HID测试程序代码来验证。如果运行正常,说明不是USB线路问题。2. 检查Bootloader版本
打开应用文档 AN2606-STM32 microcontroller system memory boot mode.pdf,通过此应用文档可知,不同的 Bootloader 版本可用于固件升级的方式不尽相同,如 4.2 节如下内容:
并且通过表3可以确认,STM32F401RB对应的BID版本以及其支持的Bootloader支持的接口。
在上述可能性都排除外,客户提出怀疑芯片本身或 Bootloader 烧录的代码有问题,于是找出一块开发板进行 MCU 替换,替换后的结果为 STM32F401RB 在放到开发板上则能正常通过 Bootloader 的 DFU 方式进行固件升级,因此,这就明确排除了芯片本身问题的可能性,因此,只可能是用户板子外围电路的问题。
3. 检查MCU外围电路
再次回到 AN2606 这个应用文档,在 29.2节找到 Bootloader 的工作流程图,如下所示:
通过上图可知,Bootloader 是依次检查 USART ->DFU ->I2C -> SPI 的方式,怀疑 Bootloader 程序在 DFU 之前由于某种未知原因是否已经进入到 USART的方式中而一直没有出来?
为了排除这种可能性,我们针对 USART1 的 RX 脚 PA10,USART2 的 RX 脚 PA3, USART6 的 RX 脚 PC7拉高,I2C 的SDA脚拉高,SPI的MISO脚上拉。结果还是无法检测到 DFU 设备。
再次回到上图进行分析,如上图,若 USART 和 CAN 都没有检测到的话,Bootloader 程序会检测 USB 线是否连接,然后检测外部 HSE,若 HSE 不存在,则产生系统复位,否则将会重现配置系统主频到 60M。
由于我们是连着 USB 线且在正常运行模式下 USB 是能正常工作的,因此,这里检测 USB 线结果应该是通过的,于是按照程序流程,接下来检测外部 HSE,若检测失败则复位系统。
与是用示波器查看VDD 与 NRST 脚的波形,发现系统在 VDD 上电后有 3 次复位,如此,可以得出 Bootloader 程序在检测外部 HSE 时结果为失败,如下:
为什么会检测外部 HSE 失败? 用户使用的 HSE 是 8M 晶振,与开发板一样都是 8M 外部晶振,对比用户的外部晶振电路与 DISCOVERY 的对应电路,如下图所示:
如上图,左边为客户板子的晶振电路,右边为 DISCOVERY 板的晶振电路,对比可知,用户的负载电容使用的是 33pF,且多了个 1M 的反馈电阻。
首先将反馈电阻去掉后测试,结果还是一样。进一步将客户板子的晶振负载电容换成 20pF 后进行测试,结果可以正常检测到 DFU 设备,如此可见,正是因为这个负载电容的原因造成 Bootloader 的 DFU 无法正常工作!
- 总结
此问题是由于晶振负载电容过大,导致内置 Bootloader 程序在检测外部 HSE 的时间点与实际 HSE 稳定震荡所需的时间不同步造成,结果就是检测不到HSE,进而引起系统复位,最终无法使用Bootloader 的 DFU 方式进行固件升级。
评论