Linux下使用 OpenOCD 烧录 STM32, 出现了 Error: init mode failed (unable to connect to the target)
错误.
如果在代码中, 不小心将 PA13,PA14 的 SWD 功能关闭, 例如使用了下面的代码
rcc_periph_clock_enable(RCC_GPIOA); // Need GPIOA clock gpio_primary_remap( AFIO_MAPR_SWJ_CFG_JTAG_OFF_SW_OFF, // Optional AFIO_MAPR_TIM2_REMAP_NO_REMAP); // This is default: TIM2.CH2=GPIOA1
或者在 STM32CubeMX 中忘记勾选 PA13/PA14 的串口调试功能, 都会导致后续烧录和连接失败, 出现
Uploading .pio/build/bluepill_f103c8/firmware.elf xPack OpenOCD x86_64 Open On-Chip Debugger 0.11.0+dev (2021-10-16-21:15) Licensed under GNU GPL v2 For bug reports, read http://openocd.org/doc/doxygen/bugs.html debug_level: 1 hla_swd none separate Error: init mode failed (unable to connect to the target) in procedure 'program' ** OpenOCD init failed ** shutdown command invoked *** [upload] Error 1
首先检查一下系统中是否有st-flash
和st-info
命令, 没有的话需要安装
安装步骤
git clone https://github.com/stlink-org/stlink.git cd stlink/ make # 如果报 libusb 错误, 就安装一下 libusb-1.0-0-dev, 再make sudo apt install libusb-1.0-0-dev make clean make cd build/Release/ sudo make install
通过 st-info 检查 会提示无法进入 SWD 模式
$ st-info --probe Failed to parse flash type or unrecognized flash type Failed to enter SWD mode Found 1 stlink programmers version: V2J37S7 serial: 56FF6B064966485627161123 flash: 0 (pagesize: 0) sram: 0 chipid: 0x000 detected chip_id parametres # Device Type: unknown # Reference Manual: RM0000 # chip_id 0x0 flash_type 0 flash_size_reg 0x0 flash_pagesize 0x0 sram_size 0x0 bootrom_base 0x0 bootrom_size 0x0 option_base 0x0 option_size 0x0 flags 0 dev-type: unknown
在网上搜到的大部分方案, 例如这个stackoverflow的解答, 都是要到Windows下, 通过 ST-link utility 去重置擦除, 这里介绍一下 Linux 下的处理方法
此时需要使用--connect-under-reset
参数, 按住开发板的 RESET 键之后, 执行下面的命令, 就能正确检测到芯片信息
$ st-info --probe --connect-under-reset Failed to parse flash type or unrecognized flash type detected chip_id parametres # Device Type: STM32F1xx_MD # Reference Manual: RM0008 # chip_id 0x410 flash_type 1 flash_size_reg 0x1ffff7e0 flash_pagesize 0x400 sram_size 0x5000 bootrom_base 0x1ffff000 bootrom_size 0x800 option_base 0x1ffff800 option_size 0x10 flags 2 Found 1 stlink programmers version: V2J37S7 serial: 56FF6B064966485627161123 flash: 0 (pagesize: 1024) sram: 20480 chipid: 0x410 detected chip_id parametres # Device Type: STM32F1xx_MD # Reference Manual: RM0008 # chip_id 0x410 flash_type 1 flash_size_reg 0x1ffff7e0 flash_pagesize 0x400 sram_size 0x5000 bootrom_base 0x1ffff000 bootrom_size 0x800 option_base 0x1ffff800 option_size 0x10 flags 2 dev-type: STM32F1xx_MD
如果是这种情况, 说明是PA13/PA14的功能复用问题, 可以通过固件擦除解决问题
st-flash 同样地要加上--connect-under-reset
参赛, 在按住 RESET 键后执行下面的命令
$ st-flash --connect-under-reset erase st-flash 1.7.0-184-g468b1d2 Failed to parse flash type or unrecognized flash type 2022-02-14T22:51:20 ERROR common.c: Soft reset failed: timeout detected chip_id parametres # Device Type: STM32F1xx_MD # Reference Manual: RM0008 # chip_id 0x410 flash_type 1 flash_size_reg 0x1ffff7e0 flash_pagesize 0x400 sram_size 0x5000 bootrom_base 0x1ffff000 bootrom_size 0x800 option_base 0x1ffff800 option_size 0x10 flags 2 2022-02-14T22:51:20 INFO common.c: STM32F1xx_MD: 20 KiB SRAM, 0 KiB flash in at least 1 KiB pages. Mass erasing
在出现Mass erasing
后, 不能立即断电, 需要等待一小段时间, 之后用st-info --probe
检查是否成功, 如果还显示Failed to enter SWD mode
, 就再重复一遍上面的操作.
如果st-info --probe
能直接检测到芯片, 就说明SWD功能已经恢复, 可以继续在 Linux 下用 OpenOCD 愉快地烧录 STM32 了.