一个STM32项目的makefile模版详解

本模板为STM32流水灯项目的Makefile配置文件,适用于STM32F10x系列MCU,详细说明了编译链接过程及所需工具链配置。包括编译目标、编译选项、链接脚本等。

啥都不说了,直接上代码,注释相当详细了。

#STM32 makefile template

# 生成的文件名<项目名>
PROJECT                  = stm32_Mini_Led

# 定义文件格式和文件名
TARGET                  := $(PROJECT)
TARGET_ELF              := $(TARGET).elf
TARGET_BIN              := $(TARGET).bin
TARGET_HEX              := $(TARGET).hex
OBJCPFLAGS_ELF_TO_BIN    = -Obinary
OBJCPFLAGS_ELF_TO_HEX    = -Oihex
OBJCPFLAGS_BIN_TO_HEX    = -Ibinary -Oihex

# 定义路径
TOP_DIR      = .
SCRIPT_DIR  := $(TOP_DIR)/scripts
STARTUP_DIR := $(TOP_DIR)/third_party/Libraries/CMSIS/CM3/DeviceSupport/ST/STM32F10x/startup
INC_DIR     := -I $(TOP_DIR)/src -I $(TOP_DIR)/src/Driver -I $(TOP_DIR)/src/EDP -I $(TOP_DIR)/src/Network

# 设置shell环境变量
#export LD_LIBRARY_PATH = $LD_LIBRARY_PATH:/Users/ch-yanghl/gcc-arm-none-eabi/arm-none-eabi/lib/thumb/

# 设置ld链接脚本文件
LDSCRIPT    := $(SCRIPT_DIR)/stm32_flash.ld

# 定义编译工具
CC          = arm-none-eabi-gcc
AS          = arm-none-eabi-as
LD          = arm-none-eabi-ld
AR          = arm-none-eabi-ar
OBJCP       = arm-none-eabi-objcopy

# 定义编译标志
CCFLAGS     += -Wall -mcpu=cortex-m3 -mthumb -g -mfloat-abi=soft -march=armv7-m
ASFLAGS     += -Wall -mcpu=cortex-m3 -mthumb
LDFLAGS     += -T $(LDSCRIPT) #-A armv7-m
LDFLAGS     += -L /Users/ch-yanghl/gcc-arm-none-eabi/lib/gcc/arm-none-eabi/5.4.1
LDFLAGS     += -L /Users/ch-yanghl/gcc-arm-none-eabi/arm-none-eabi/lib/thumb

# 要链接的静态库
#LDLIBS         += /Users/ch-yanghl/gcc-arm-none-eabi/arm-none-eabi/lib/thumb/libc.a
#LDLIBS         += /Users/ch-yanghl/gcc-arm-none-eabi/arm-none-eabi/lib/thumb/libg.a
#LDLIBS         += /Users/ch-yanghl/gcc-arm-none-eabi/arm-none-eabi/lib/thumb/libm.a
#LDLIBS      += /Users/ch-yanghl/gcc-arm-none-eabi/lib/gcc/arm-none-eabi/5.4.1/libgcc.a
#LDLIBS      += /Users/ch-yanghl/gcc-arm-none-eabi/arm-none-eabi/lib/thumb/libnosys.a


# .c文件中的头文件引用查找路径
CCFLAGS     += $(INC_DIR)

# .s文件的flags
#ASFLAGS        +=

# .c文件编译时定义宏
CCFLAGS     += -D STM32F10X_MD -D USE_STDPERIPH_DRIVER

# 添加启动文件
#SOURCE         += $(SCRIPT_DIR)/startup_stm32f10x_md.c
SOURCE_ASM      += $(STARTUP_DIR)/gcc_ride7/startup_stm32f10x_md.s

# 展开工作 子目录中的inc文件(inc文件中添加需要编译链接的.c,.s等文件)
-include $(TOP_DIR)/src/make.inc
-include $(TOP_DIR)/third_party/make.inc

# 替换文件后缀
C_OBJS      := $(SOURCE:%.c=%.o)
ASM_OBJS    := $(SOURCE_ASM:%.s=%.o)

# 编译命令的定义
COMPILE     = $(CC) $(CCFLAGS) -c $< -o $@ 
ASSEMBLE    = $(AS) $(ASFLAGS) -c $< -o $@ 
LINK        = $(LD) $+ $(LDFLAGS) $(LDLIBS) -o $@ 
ELF_TO_BIN  = $(OBJCP) $(OBJCPFLAGS_ELF_TO_BIN) $< $@
BIN_TO_HEX  = $(OBJCP) $(OBJCPFLAGS_BIN_TO_HEX) $< $@ 

# 定义伪目标
.PHONY: all clean printf

# 定义规则
all: $(TARGET_HEX)
    @echo "build done"

$(TARGET_HEX): $(TARGET_BIN)
    $(BIN_TO_HEX)

$(TARGET_BIN): $(TARGET_ELF)
    $(ELF_TO_BIN)

$(TARGET_ELF): $(C_OBJS) $(ASM_OBJS)
    $(LINK)

$(C_OBJS):%.o:%.c
    $(COMPILE)

$(ASM_OBJS):%.o:%.s
    $(ASSEMBLE) 

printf:
    @echo $(ASM_OBJS)
    @echo $(ASSEMBLE)

# 清理项
clean:
    rm -f $(TARGET_HEX)
    rm -f $(TARGET_BIN)
    rm -f $(TARGET_ELF)
    rm -f $(C_OBJS) $(ASM_OBJS)
    @echo "clean done"

这个一个LED流水灯的STM32工程,包含STM32库v3.5.0版本,下载地址
再详细说一下注释中没有的可能有疑问的地方:

# 要链接的静态库
#LDLIBS         += /Users/ch-yanghl/gcc-arm-none-eabi/arm-none-eabi/lib/thumb/libc.a
#LDLIBS         += /Users/ch-yanghl/gcc-arm-none-eabi/arm-none-eabi/lib/thumb/libg.a
#LDLIBS         += /Users/ch-yanghl/gcc-arm-none-eabi/arm-none-eabi/lib/thumb/libm.a
#LDLIBS      += /Users/ch-yanghl/gcc-arm-none-eabi/lib/gcc/arm-none-eabi/5.4.1/libgcc.a
#LDLIBS      += /Users/ch-yanghl/gcc-arm-none-eabi/arm-none-eabi/lib/thumb/libnosys.a

-这一块为什么要注释:因为文中使用了

# 设置ld链接脚本文件
LDSCRIPT    := $(SCRIPT_DIR)/stm32_flash.ld
/*stm32_flash.ld文件中最后部分内容*/
/DISCARD/ :
  {
    libc.a ( * )
    libm.a ( * )
    libg.a ( * )
    libgcc.a ( * )
  }

这个ld脚本文件,该文件中已经包含了这些库。

### EIDE 中创建 STM32 项目标准模板 #### 准备工作 为了顺利创建 STM32F4 的工程模板,在开始之前需确认已安装必要的工具链,包括但不限于 GCC 编译器、OpenOCD 调试工具以及 Eclipse IDE 或 VSCode 环境配置完成[^1]。 #### 使用 STM32CubeMX 初始化硬件配置 通过 STM32CubeMX 可以为特定型号的 MCU 配置外设功能并自动生成初始化代码。对于希望构建稳定可靠的嵌入式应用来说,这一步骤至关重要。启动 STM32CubeMX 后选择目标设备 (如 STM32F4),随后按照向导提示逐步设定系统时钟频率、启用所需外设等功能模块,并最终生成适用于所选集成开发环境(IDE)的项目框架文件[^2]。 #### 导入到 EIDE 并完善项目结构 当从 CubeMX 完成了初步设置之后,下一步就是将生成好的 Makefile 和源码导入至 Eclipse CDT 或者 Visual Studio Code 这样的编辑环境中去。确保正确设置了编译选项与链接参数以便于后续调试工作的开展;同时也可以利用这些平台提供的插件来增强用户体验,比如更友好的界面操作或是更加高效的编程辅助特性[^3]。 #### 添加通用组件和支持库 除了由 CubeMX 自动生成的基础部分之外,还应该考虑加入一些常用的第三方类库或者是自己积累下来的经验片段作为补充材料放入工程项目当中。这样做不仅有助于提高程序性能表现力,而且也方便日后维护升级时查找定位问题所在位置[^4]。 ```c // 示例:添加 FreeRTOS 支持 #include "FreeRTOS.h" #include "task.h" void vTaskFunction(void *pvParameters){ while(1){ // Task code here... vTaskDelay(pdMS_TO_TICKS(100)); } } int main(){ xTaskCreate(vTaskFunction, "TASK", configMINIMAL_STACK_SIZE, NULL, tskIDLE_PRIORITY + 1, NULL); vTaskStartScheduler(); } ```
### STM32 HAL Makefile 工程构建详解 #### 1. 基于MakefileSTM32 HAL工程结构 在使用Makefile构建基于HAL库的STM32项目时,首先需要明确项目的目录结构。通常情况下,一个典型的STM32 HAL工程会包含以下几个主要部分: - **Core 文件夹**: 存放由STM32CubeMX生成的核心文件,包括`startup_stm32f4xx.s`启动文件和`.ld`链接器脚本。 - **Drivers 文件夹**: 包含ST官方提供的标准外设驱动程序以及CMSIS核心文件。 - **Inc 和 Src 文件夹**: 用户自定义头文件和源文件分别存放在这两个文件夹中。 - **User 文件夹 (可选)**: 如果有额外的功能模块或者第三方库可以放置在此处。 这些文件夹中的内容可以通过手动创建或通过STM32CubeMX工具自动生成功能框架来初始化[^1]。 #### 2. 制作适合Linux下的Makefile文件 为了使项目能够在Linux环境下编译运行,在编写Makefile之前要确保安装好GNU ARM Embedded Toolchain等相关交叉编译工具链。以下是关于如何设置Makefile的一些关键点: - 定义目标二进制名称、输入源文件列表、汇编文件路径以及其他依赖项; - 设置CFLAGS用于指定优化级别(-O2),调试信息支持(-g),并加入特定芯片架构参数(如-cpu=cortex-m4 -mfpu=fpv4-sp-d16 -mfloat-abi=hard); - 添加LDFLAGS变量指向正确的链接描述符(.ld file)位置; 下面是一个简单的Makefile模板示例: ```makefile # Project Name TARGET := my_project # Compiler and tools paths CC := arm-none-eabi-gcc AS := arm-none-eabi-as LD := arm-none-eabi-ld OBJCOPY := arm-none-eabi-objcopy SIZE := arm-none-eabi-size # Source files directories VPATH := src inc drivers/cmsis/core \ drivers/stm32f4xx_hal_driver/inc \ drivers/stm32f4xx_hal_driver/src # Output directory BUILD_DIR := build/ # Flags configuration CFLAGS += -std=gnu99 -Wall -Wextra -pedantic-errors -c -MMD -MP CFLAGS += -DUSE_HAL_DRIVER -DSTM32F407xx CFLAGS += -Iinc -Idrivers/cmsis/core -Idrivers/stm32f4xx_hal_driver/inc ASM_FLAGS += -x assembler-with-cpp $(CFLAGS) LDFLAGS += -TSTM32F407VG_FLASH.ld LDFLAGS += --specs=nano.specs --specs=nosys.specs SRC_FILES := main.c system_stm32f4xx.c stm32f4xx_it.c startup_stm32f407xx.s OBJS := $(addprefix $(BUILD_DIR),$(notdir $(SRC_FILES:.c=.o))) DEPS := $(OBJS:.o=.d) all: elf hex size elf: $(OBJS) @echo "[LINKER]" $(LD) $^ -o $(BUILD_DIR)$(TARGET).elf $(LDFLAGS) hex: elf @echo "[HEX]" $(OBJCOPY) -O ihex $(BUILD_DIR)$(TARGET).elf $(BUILD_DIR)$(TARGET).hex size: elf @echo "[SIZE]" $(SIZE) $(BUILD_DIR)$(TARGET).elf clean: rm -rf $(BUILD_DIR)* -include $(DEPS) ``` 此段代码展示了基本的Makefile配置方法及其组成部分解释。 #### 3. 修改启动文件与链接脚本 对于不同的微控制器型号可能需要用到不同版本的启动文件(`startup_*.s`)及相应的链接脚本文件(*_FLASH.ld*)。这两者都是由STM32CubeMX依据所选硬件平台而定制化产生的。如果有必要调整内存布局或是增加新的节区,则可以直接编辑`.ld`文件实现更精细控制[^2]。 例如,在某些应用场合下希望把常量数据放到Flash区域而不是RAM里去存储的话就可以这样改动: ```text /* Add this section inside the MEMORY block */ PROGBITS : ORIGIN = LOAD_ADDRESS, LENGTH = CONSTANT_SIZE_IN_KB * KBYTE ... /* Then add a new output section definition below others like so*/ .constant_data : { KEEP(*(.rodata*)) } > FLASH AT> PROGBITS ``` 上述操作允许开发者灵活分配资源从而满足特殊应用场景的需求。 ---
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值