基于CMSIS库的Nucleo-F103RB裸机编程:库及Makefile获取方案
Nucleo-F103RB 基于CMSIS+Makefile的LED闪烁项目搭建方案
一、获取适配的CMSIS组件
Nucleo-F103RB搭载STM32F103RB芯片,你需要STM32F1系列的CMSIS库,具体获取方式:
- 下载ST官方的STM32CubeF1包,解压后提取以下CMSIS相关目录:
CMSIS/Core/Include:通用CMSIS核心头文件(如core_cm3.h)CMSIS/Device/ST/STM32F1xx/Include:STM32F1系列专属的设备头文件(stm32f1xx.h)和系统配置文件CMSIS/Device/ST/STM32F1xx/Source/Templates:包含对应芯片的启动汇编文件(startup_stm32f103xb.s,适配STM32F103xB系列,RB属于此系列)以及系统初始化C文件system_stm32f1xx.c
二、Makefile示例
以下是适配STM32F103RB的Makefile框架,需提前安装arm-none-eabi-gcc交叉编译工具链:
# 工具链定义 TOOLCHAIN_PREFIX = arm-none-eabi- CC = $(TOOLCHAIN_PREFIX)gcc AS = $(TOOLCHAIN_PREFIX)as LD = $(TOOLCHAIN_PREFIX)gcc OBJCOPY = $(TOOLCHAIN_PREFIX)objcopy SIZE = $(TOOLCHAIN_PREFIX)size # 编译参数 CPU = -mcpu=cortex-m3 CFLAGS = $(CPU) -mthumb -Wall -O0 -g \ -I./CMSIS/Core/Include \ -I./CMSIS/Device/ST/STM32F1xx/Include ASFLAGS = $(CPU) -mthumb -g # 链接脚本需自行创建(见下文) LDFLAGS = -T stm32f103rb.ld $(CPU) -mthumb -Wl,-Map=led_blink.map # 源文件列表 SRCS = main.c \ ./CMSIS/Device/ST/STM32F1xx/Source/Templates/system_stm32f1xx.c ASM_SRCS = ./CMSIS/Device/ST/STM32F1xx/Source/Templates/gcc/startup_stm32f103xb.s OBJS = $(SRCS:.c=.o) $(ASM_SRCS:.s=.o) # 目标规则 all: led_blink.elf led_blink.bin led_blink.elf: $(OBJS) $(LD) $(LDFLAGS) -o $@ $(OBJS) $(SIZE) $@ led_blink.bin: led_blink.elf $(OBJCOPY) -O binary $< $@ # 编译规则 %.o: %.c $(CC) $(CFLAGS) -c -o $@ $< %.o: %.s $(AS) $(ASFLAGS) -c -o $@ $< clean: rm -f $(OBJS) led_blink.elf led_blink.bin led_blink.map
三、链接脚本(stm32f103rb.ld)
根据STM32F103RB的Flash(128KB)和RAM(20KB)配置:
MEMORY { FLASH (rx) : ORIGIN = 0x08000000, LENGTH = 128K RAM (rwx) : ORIGIN = 0x20000000, LENGTH = 20K } SECTIONS { .text : { KEEP(*(.isr_vector)) *(.text*) *(.rodata*) } > FLASH .data : AT(__DATA_ROM) { __DATA_RAM = .; *(.data*) __DATA_END = .; } > RAM .bss : { __BSS_START = .; *(.bss*) *(COMMON) __BSS_END = .; } > RAM __DATA_ROM = LOADADDR(.data); __DATA_SIZE = __DATA_END - __DATA_RAM; __BSS_SIZE = __BSS_END - __BSS_START; }
四、LED闪烁主程序(main.c)
Nucleo-F103RB的LD2 LED对应PA5引脚,直接通过CMSIS操作寄存器实现闪烁:
#include "stm32f1xx.h" // 简单延时函数(基于72MHz系统时钟) static void delay_ms(uint32_t ms) { while (ms--) { for (uint32_t i = 0; i < 7200; i++); } } int main(void) { // 使能GPIOA时钟 RCC->APB2ENR |= RCC_APB2ENR_IOPAEN; // 配置PA5为50MHz推挽输出 GPIOA->CRL &= ~(GPIO_CRL_MODE5 | GPIO_CRL_CNF5); GPIOA->CRL |= GPIO_CRL_MODE5_0 | GPIO_CRL_MODE5_1; while (1) { GPIOA->BSRR = GPIO_BSRR_BS5; // 点亮LED delay_ms(500); GPIOA->BSRR = GPIO_BSRR_BR5; // 熄灭LED delay_ms(500); } }
五、关键注意事项
- 确保
system_stm32f1xx.c中的系统时钟配置正确,默认可能为HSI(8MHz),可修改为HSE外接晶振的72MHz配置以匹配延时函数。 - VSCode中需配置C/C++插件的编译器路径,指向
arm-none-eabi-gcc的安装目录。 - 烧录程序可使用ST-Link工具配合
st-flash命令完成。
内容的提问来源于stack exchange,提问作者lucas mure
相关产品推荐
相关产品推荐

