STM32CubeIDE+Ceedling单元测试报错:找不到Reset_Handler符号
问题分析与解决方案
核心错误拆解
你遇到的两个关键问题:
- 链接器找不到
Reset_Handler符号:STM32交叉编译需要启动汇编文件(如startup_stm32g474rbtx.s)提供入口符号,当前配置未正确引入该文件或未开启汇编编译支持。 - 测试可执行文件找不到:链接器硬编码了输出文件名,与Ceedling预期的输出路径/文件名不匹配,导致执行时找不到文件。
具体修复步骤
1. 修正链接器输出文件名
修改project.yml中test_linker的输出参数,将硬编码的文件名替换为Ceedling内置变量${2}(Ceedling会自动传递测试可执行文件的目标路径):
:tools: :test_linker: :executable: arm-none-eabi-gcc :arguments: - '-o "${2}"' # 替换原硬编码的 "-o "STM32G474RB - PLATFORM.elf"" - '-mcpu=cortex-m4' - '-T"./STM32G474RBTX_FLASH.ld"' # 建议改成相对路径,避免移植问题 # 其余参数保持不变
2. 解决Reset_Handler未定义问题
如果坚持使用ARM交叉编译(目标机测试):
- 开启汇编文件编译支持,取消
test_build的注释并设置:use_assembly: TRUE:
:test_build: :use_assembly: TRUE
- 确保
Core/Startup目录下的启动.s文件被包含在编译路径中(当前paths:source已包含Core/Startup/**,需确认该目录下确实存在对应型号的启动文件)。
更推荐的主机端单元测试方案(无需交叉编译)
直接使用本地gcc(macOS为clang/Xcode gcc)做主机测试,通过CMock模拟HAL/CMSIS硬件相关函数,无需启动文件和STM32链接脚本:
:tools: :test_compiler: :executable: gcc :arguments: - '${1}' - '-std=gnu11' - '-g3' - '-DDEBUG' - '-DTEST' - '-c' - '-I Core/Inc' - '-I Drivers/CMSIS/Include' - '-I #{Ceedling.load_path}/../vendor/unity/src' - '-O0' - '-Wall' :test_linker: :executable: gcc :arguments: - '-o "${2}"' - '${1}' - '-lm'
之后编写Mock文件(如mock_stm32g4xx_hal.h)模拟硬件函数,比如MockHAL_GPIO_WritePin等,实现脱离硬件的单元测试。
3. 额外检查点
- 确认
paths:source路径覆盖了所有必要的源文件目录; - 链接脚本路径尽量使用相对路径,避免绝对路径导致的移植问题;
- 若使用主机测试,需确保所有硬件相关代码都被Mock替代,避免编译依赖硬件寄存器定义。
内容的提问来源于stack exchange,提问作者RPG
相关产品推荐
相关产品推荐

