1.STM32的三种开发方式
单片机开发本质是对寄存器的操作,固件库是对寄存器的进一步封装
直接寄存器开发:执行效率最高,但是开发难度大不方便移植,需要经常查阅数据手册
标准外设库开发:将寄存器封装一整套标准化函数接口,大大降低开发难度,移植也较为方便,但是目前已经停止维护
HAL库开发:对寄存器的封装更加的抽象,因此移植性更强更方便,可在更多不同平台上运行,但是执行效率较低
2.HAL库开发
STM32CubeMX:是一款图形化开发工具,自动生成stm32芯片初始化相关代码,可配置引脚生成c代码,大大节省了移植HAL固件库和配置各种外设的时间,非常方便的开发工具
移植HAL固件库:手动移植HAL固件库较为繁琐耗时,可自行裁剪,自定义的工程目录文件夹结构更加清晰,对HAL库的理解更加深刻
3.HAL固件库包获取
官网获取:STM32CubeMX:图形化工具 - 意法半导体STMicroelectronics
百度网盘获取:https://pan.baidu.com/s/1EYSi4A_agQO8rC9t6voaPA?pwd=777w
提取码:777w
进入官网界面,点搜索输入STM32CubeF1,因为本次使用的开发板是STM32F103C8T6最小系统板,如果是f4系列开发板就搜索STM32CubeF4,h7系列搜索STM32CubeH7
点击STM32CudeF1
选择最新版本下载,下载是免费的,但是要输入个人邮箱注册,如果不想注册登录,可以选择前面提供的其他下载方式
4.HAL固件包
解压下载的压缩包,可得到这样的文件夹
简单移植只需要Drivers中其中两个核心文件夹,CMSIS文件夹和STM32F1xx_HAL_Driver文件夹的内容文件,CMSIS中包括:DSP库、Cortex-M内核及其设备文件、微控制器专用头文件、启动文件、专用系统文件等,STM32F1xx_HAL_Driver包含:是HAL外设驱动源码,包括F1系列HAL库源文件和头文件,如果其他系列开发板要更换固件包
CMSIS中保留Device文件夹和Include文件夹
Device可以只留下这五个文件
startup_stm32f103xb.s:启动文件根据开发板而定,如果是STM31F103C8T6开发板选择startup_stm32f103xb.s,STM31F103ZET6开发板选择startup_stm32f103xe.s,根据开发板选择对应的启动文件
stm32f1xx.h和stm32f103xb.h:微控制器专用头文件,同理根据开发板选择对应的启动文件
system_stm32f1xx.c:专用系统文件
Include可以只留下这六个关键文件,Cortex-M内核及其设备文件、编译器相关头文件
STM32F1xx_HAL_Driver文件夹,包含封装所有寄存器的函数接口(API),外设驱动源码建议全部保留,防止后续需要时找不到
基于CMSIS应用程序文件描述
STM32开发文件结构分布
5.开始外部文件移植
DRIVERS:硬件相关和HAL库驱动源码
HARDWARE:外设文件,如LED、KEY、BEEP等
MDK-PROJET:MDK工程文件
SYSTEM:系统级驱动代码,如sys.c、delay.c、usart.c等
USERS:main.c、stm32f1xx_hal_conf.h、stm32f1xx_it.c等
将STM32Cude固件包驱动源码Drivers放入DRIVERS中
在USERS中也要移植stm32f1xx_it.c,stm32f1xx_it.h,stm32f1xx_hal_conf.h 这三个文件,stm32f1xx_hal_conf.h 可以在STM32F1xx_HAL_Driver中找到,根据指示需要改名再放入,其他两个文件在STM32Cude固件包的示例工程中
移植完成的效果如下,在上面的Inc文件夹中,也有stm32f1xx_hal_conf.h可以在这里直接移植,也可以在之前的STM32F1xx_HAL_Driver文件夹中把stm32f1xx_hal_conf_template.h改名得到
再新建一个文本文件,然后改名为main.c文件
6.添加工程文件
建立一个新的工程
生成MDK工程文件,选择工程路径,存放在MDK_PROJET文件夹中,名字自定义
选择芯片型号,本次使用STM32F103C8T6,所以选择STM32F103C8,如果不同,选择自己相应的型号,点击OK
查看已经建立的工程
管理项目文件,将自定义的文件目录添加到工程中,这里少建立一个MDK-PROJET文件夹,多建立一个STARTUP工程文件夹,用于存放启动文件startup_stm32f103xb.s,点击OK保存
STARTUP工程文件夹中添加启动文件,在DRIVERS文件夹中,CMSIS中,Device中,选择All file(*.*),添加startup_stm32f103xb.s
DRIVRS工程文件夹添加system_stm32f1xx.c,以及一系列大致要用到的hal库接口,也可以全部添加
USERS工程文件夹添加,main.c,stm32f1xx_it.c,在多添加一个stm32f1xx_hal_conf.h
再添加文件路径
7.完善工程
虽然工程添加完成,但是编译任然有许多错误,开始完善工程,点击魔法棒,选择Target,如下配置,再选择c/c++添加宏,STM32F103xB,USE_HAL_DRIVER,表示使用这种容量的芯片和使用HAL库固件包,中间用英文的逗号隔开,注意:如果开发板不是STM32F103C8T6,要使用其他宏;如STM32F103ZET6,要使用STM32F103xE
再次编译,只有一个错误,表示没有main.h这个头文件删除即可,
再次编译,还有一个警告,找不到这个函数从何而来,添加hal库头文件stm32f1xx_hal.h
再次编译,还有一个错误,表示找不到程序入口,缺少main函数,在main.c中添加即可,编译无错误,移植成功
8.编写代码
编写代码,编译无错误,烧入程序
代码:
int main(void)
{
HAL_Init();//初始化HAL库
GPIO_InitTypeDef gpio_init_struct;
__HAL_RCC_GPIOC_CLK_ENABLE();//开启GPIOC的时钟
gpio_init_struct.Pin = GPIO_PIN_13; //选择13引脚
gpio_init_struct.Mode = GPIO_MODE_OUTPUT_PP; //推挽输出
gpio_init_struct.Pull = GPIO_PULLUP; //上拉
gpio_init_struct.Speed = GPIO_SPEED_FREQ_HIGH; //高速
HAL_GPIO_Init(GPIOC, &gpio_init_struct);//初始化引脚
HAL_GPIO_WritePin(GPIOC, GPIO_PIN_13, GPIO_PIN_RESET);//开启LED
while(1) {
}
}
#include <stdio.h>
#include "stm32f1xx_hal.h"
void Mydelay_ms(int ms)//粗略的延时函数
{
int i,j,k;
for(i=0; i<ms; i++)
for(j=0; j<100; j++)
for(k=0; k<100; k++);
}
int main(void)
{
HAL_Init();//初始化HAL库
GPIO_InitTypeDef gpio_init_struct;
__HAL_RCC_GPIOC_CLK_ENABLE();//开启GPIOC的时钟
gpio_init_struct.Pin = GPIO_PIN_13; //选择13引脚
gpio_init_struct.Mode = GPIO_MODE_OUTPUT_PP; //推挽输出
gpio_init_struct.Pull = GPIO_PULLUP; //上拉
gpio_init_struct.Speed = GPIO_SPEED_FREQ_HIGH; //高速
HAL_GPIO_Init(GPIOC, &gpio_init_struct);//初始化引脚
HAL_GPIO_WritePin(GPIOC, GPIO_PIN_13, GPIO_PIN_RESET);//开启LED
while(1) {
HAL_GPIO_TogglePin(GPIOC, GPIO_PIN_13);
Mydelay_ms(100);
}
}
现象:
试验完成!!!