前言

好久没写STM32的博客了,主要还是涉及到很多核心技术,再加上代码量巨大,懒得整理,就不了了之了。
之前的开发的工程都是在已有框架上的已有产品中增加新功能,这次我决定从0开始,学习STM32,从搭建环境开始,到烧录程序运行成功,系统的从零开始学习。
本人已经绘制成功一块STM32的电路版,已经将硬件焊接成功,主要器件如下:
STM32F407ZET6
正点原子2.8 LCD MODULE
一个摄像头
几个二极管

本篇博客主要记录从零创建一个全新的STM32F407的项目过程

STM32单片机学习资料均来自 正点原子 ,仅用于学习,如有侵权请联系我删除
本博客内容原创,创作不易,转载请注明

本文链接
个人博客:https://ronglin.fun/?p=112
PDF链接: 见博客网站
CSDN: https://blog.csdn.net/RongLin02/article/details/121293268

资料下载

资料均来自 正点原子,感谢原子哥的开源奉献
正点原子资料下载中心
全部资料均来自以上网站

要下载有两个:
一个是 STM32F407最小系统板开发指南-库函数版本作为主要文档
还有一个是STM32F4xx固件库作为库函数,全在 A盘 资料里,有需要的在stm32f407探索者开发板中下载。

创建工程

开发工具:Keil uVision5
接下来就跟着文档,从零创建一个STM32的project
本次学习目标主要是学会用STM32F407实现摄像头的应用

创建目录

所以先创建一个新的空白文件夹叫:MyCamera
然后在MyCamera目录下创建五个子文件夹:CORE,FWLIB,OBJ,SYSTEM,USER,如下图:

至于这些文件夹名字,实际上是可以任取的,
这样取名只是为了方便识别。用来存储特定的类型的文件

创建工程

创建完目录之后,就要创建工程了
打开Keil
ProjectNew μVison Project

然后在弹出来的界面中,选择我们刚才创建的目录下的USER目录下,也就是...\MyCamera\USER路径下,然后输入文件名,我这里和我自己的工程名称一致,是MyCamera,然后点击保存。

之后就是弹出来选择设备,我的CPU型号是STM32F407ZET6所以说选择STM32F407ZETx型号

有关STM32的型号,正点原子的文档中都有解释,再次感谢原子哥
然后接下来的Manager Run-Time Environment界面直接点击Cancel就行了。

到此,我们的工程框架就创建好了,现在在工程里,只有一个Target1 下的 source Group 1
然后我们在系统中点开文件夹,发现在USER目录下多了几个文件:
MDK5.14生成的工程文件是以.uvprojx 为后缀。这个不能删除
Listings 和 Objects 文件夹是 MDK 自动生成的文件夹,用于存放编译过程产生的中间文件。这两个文件不用管它

复制库函数文件

框架已经建好,之后就是将官方的库函数复制到我们的项目文件里了。

文件复制

FWLib

第一个是:
打开官方固件库包,定位到我们之前准备好的固件库包的目录:
\STM32F4xx_DSP_StdPeriph_Lib_V1.4.0\Libraries\STM32F4xx_StdPeriph_Driver 下面,
将目录下面的 src,inc 文件夹 copy 到我们刚才建立的FWLib 文件夹下面。

src 存放的是固件库的.c 文件,inc 存放的是对应的.h 文件,还有一个html文件是一个说明文件

CODE

打开官方固件库包
\STM32F4xx_DSP_StdPeriph_Lib_V1.4.0\Libraries\CMSIS\Device\ST\STM32F4xx\Source\Templates\arm
将文件 startup_stm32f40_41xxx.s 复制到 CORE 目录下面。
然后定位到目录
\STM32F4xx_DSP_StdPeriph_Lib_V1.4.0\Libraries\CMSIS\Includ
将 里 面 的 四 个 头文件 :
core_cm4.hcore_cm4_simd.hcore_cmFunc.h 以及 core_cmInstr.h
同样复制到 CORE 目录下面。复制完的CODE结构如下图:

简单的说明一下,在arm文件夹下有很多.s文件,主要是和芯片有关,主要用于启动

USER

接下来我们要复制工程模板需要的一些其他头文件和源文件到我们工程。首先定位到目录:
STM32F4xx_DSP_StdPeriph_Lib_V1.4.0\Libraries\CMSIS\Device\ST\STM32F4xx\Include
将里面的 2 个头文件 stm32f4xx.hsystem_stm32f4xx.h 复制到 USER 目录之下。
这两个头文件是STM32F4 工程非常关键的两个头文件。然后进入目录
\STM32F4xx_DSP_StdPeriph_Lib_V1.4.0\Project\STM32F4xx_StdPeriph_Templates
将 目 录 下 面 的 5 个 文 件 main.cstm32f4xx_conf.hstm32f4xx_it.cstm32f4xx_it.hsystem_stm32f4xx.c
复制到 USER 目录下面。如下图

添加到工程

前面的步骤,我们已经将需要的固件库相关文件复制到了我们的工程目录下面
下面我们还要将这些文件加入我们的工程中去。

设置Groups

在MDK5中,右键点击 Target1,选择 Manage Project Items
然后在Project Targets一栏,我们双击Target将名字修改为 Template,然后在 Groups 一栏删掉一个 Source Group 1
建立三个 Groups:USER,CORE,FWLIB。然后点击 OK,可以看到我们的 Target名字以及 Groups 情况如下图:

Groups添加文件

FWLIB

下面我们往 Group 里面添加我们需要的文件。我们按照上边的方法, 右键点击点击Tempate,选择 Manage Project Items.
然后选择需要添加文件的 Group,这里第一步我们选择 FWLIB,然后点击右边的 Add Files
定位到我们刚才建立的目录\FWLIB\src下面,将里面所有的文件选中(Ctrl+A),然后点击 Add,然后 Close.
可以看到 Files 列表下面包含我们添加的文件,如下图

这里有个文件 stm32f4xx_fmc.c 比较特殊。这个文件是 STM32F42 和 STM32F43 系列才用到,
所以我们这里要把它删掉(注意是 stm32f4xx_fmc.c 要删掉,不要删掉 stm32f4xx_fsmc.c)。
这里需要说明一下,对于我们写代码,如果我们只用到了其中的某个外设,我们就可以不用添加没有用到的外设的库文件。
例如我只用 GPIO,我可以只用添加 stm32f4xx_gpio.c而其他的可以不用添加。这里我们全部添加进来是为了后面方便,不用每次添加,当然这样的坏处是工程太大,编译起来速度慢,用户可以自行选择。

CODE/USER

之后我们添加文件到 COREUSER
CORE 下面需要添加的文件为 startup_stm32f40_41xxx.s
*注意:默认添加的时候文件类型为.c,也就是添加 startup_stm32f40_41xxx.s 启动文件的时候,你需要选择文件类型为 All files才能看得到这个文件 *
USER 目录下面需要添加的文件为 main.cstm32f4xx_it.csystem_stm32f4xx.c
这样我们需要添加的文件已经添加到我们的工程中去了,最后点击 OK,回到工程主界面。如下图

设置头文件

接下来要在 MDK 里面设置头文件存放路径。
也就是告诉 MDK 到那些目录下面去寻找包含了的头文件。
这一步骤非常重要。如果没有设置头文件路径,那么工程会出现报错头文件路径找不到。

设置目录

先进入 PATH 配置界面,选择C/C++标签,然后点击Include Paths

在弹出的界面中,点击New(Insert),然后添加点击添加路径
这里我们需要添加的头文件路径包括:\CORE, \USER\, \FWLIB\inc
这里大家务必要仔细,固件库存放的头文件子目录是\FWLIB\inc,不是 FWLIB\src。
很多朋友都是这里弄错导致报很多奇怪的错误。添加完成之后如下图

添加标识符

接下来对于 STM32F40 系列的工程,还需要添加一个全局宏定义标识符。
添加方法是点击魔术棒之后,进入 C/C++选项卡,然后在 Define 输入框连输入:

STM32F40_41xxx,USE_STDPERIPH_DRIVER

注意这里是两个标识符 STM32F40_41xxxUSE_STDPERIPH_DRIVER,他们之间是用逗号隔开的。
如下图:

编译

接下来我们要编译工程,在编译之前我们首先要选择编译中间文件编译后存放目录。
方法是点击魔术棒 ,然后选择Output选项下面的 Select folder for objects…
然后选择目录为我们之前新建的 OBJ 目录。
同时将下方的三个选项框都勾上,如下图:

这里说明一下勾选的意义。
Create HEX File 选项选上是要求编译之后生成 HEX 文件。
Browse Information 选项选上是方便我们查看工程中的一些函数变量定义。

然后main.c更换成一下的代码

#include "stm32f4xx.h"
void Delay(__IO uint32_t nCount);
void Delay(__IO uint32_t nCount)
{while(nCount--){}
}
int main(void)
{
GPIO_InitTypeDef GPIO_InitStructure;RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOF, ENABLE);GPIO_InitStructure.GPIO_Pin = GPIO_Pin_9 | GPIO_Pin_10;GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT;GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;GPIO_InitStructure.GPIO_Speed = GPIO_Speed_100MHz;GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP;GPIO_Init(GPIOF, &GPIO_InitStructure);
while(1){
GPIO_SetBits(GPIOF,GPIO_Pin_9|GPIO_Pin_10);
Delay(0x7FFFFF);
GPIO_ResetBits(GPIOF,GPIO_Pin_9|GPIO_Pin_10);
Delay(0x7FFFFF);
}
}

同时还需要将 USER 分组下面的 stm32f4xx_it.c 文件内容清空。
或者删掉其中的 32 行对main.h头文件的引入以及 144 行 SysTick_Handler 函数内容。

然后点击编译按钮Build(F7)编译工程,可以看到工程编译通过没有任何错误和警告。

恭喜,到这里,一个基于固件库 V1.4 的工程模板就建立完成,同时在工程的 OBJ 目录下面生成了对应的 hex 文件。

系统时钟设置

还有个非常重要的关键点,就是系统时钟的配置,有关系统时钟,文档中4.3节有详细的说明
这里我们要修改 System_stm32f4xx.c 文件,把 PLL 第一级分频系数 M 修改为 8,这样达到主时钟频率为 168MHz。
在316行处修改如下:

/************************* PLL Parameters *************************************/
#if defined (STM32F40_41xxx) || defined (STM32F427_437xx) || defined (STM32F429_439xx) || defined (STM32F401xx)
/* PLL_VCO = (HSE_VALUE or HSI_VALUE / PLL_M) * PLL_N */
#define PLL_M      8
#else /* STM32F411xE */
#if defined (USE_HSE_BYPASS)
#define PLL_M      8
#else /* STM32F411xE */
#define PLL_M      16
#endif /* USE_HSE_BYPASS */
#endif /* STM32F40_41xxx || STM32F427_437xx || STM32F429_439xx || STM32F401xx */

PLL_M 这里将25修改为 8,这样我们的系统时钟就是 168MHz。详细原因我们后面 4.3 小节会讲解。
同时,我们要在 stm32f4xx.h 里面修改外部时钟 HSE_VALUE 值为 8MHz,因为我们的外部高速时钟用的晶振为 8M.
具体修改方法如下:在大概123行处,将((uint32_t)25000000)修改成((uint32_t)8000000)

#if !defined  (HSE_VALUE)#define HSE_VALUE    ((uint32_t)25000000) /*!< Value of the External oscillator in Hz */#endif /* HSE_VALUE */

大家一定要在对应的配置文件中,找到相应的代码行,修改为符合我们硬件的值即可。

SYSTEM

实际上经过前面的步骤,我们的工程模板已经建立完成。
但是在 正点原子 提供的实验代码中,每个实验都有一个 SYSTEM 文件夹
下面有 3 个子目录分别为 sys,usart,delay,存放的是每个实验都要使用到的共用代码。
该代码是由 ALIENTEK 编写,该代码的原理在在文档第五章有详细的讲解
我们这里只是引入到工程中,方便后面的实验建立工程。

在原子哥提供的资料中
实验0 Template工程模板\目录下的SYSTEM文件夹,将SYSTEM文件夹移动到我们的工程下
然后在MDK5中,添加到我们的工程中。
根据前边的教程,完成配置后如下图:

接下来我们将对应的三个目录(sys,usart,delay)加入到 PATH 中去,因为每个目录下面都有相应的.h 头文件。
这请参考前边的步骤即可,加入后的截图如下图

最后点击 OK。这样我们的工程模板就彻底完成了。

最后修改一下main.c函数,测试一下

#include "stm32f4xx.h"
#include "usart.h"
#include "delay.h"
int main(void)
{u32 t=0;uart_init(115200);delay_init(84);while(1){printf("t:%d\r\n",t);delay_ms(500);t++;}
}

编译成功,全部完成!!!

总结

STM32工程的创建太麻烦了,不过这是学习的必要一环,等之后的项目就是在此基础上的增加了 =w=

STM32学习之新建工程模板相关推荐

  1. 【STM32】 keil新建工程模板

    Ⅰ.写在前面 本文使用目前(2016年11月)最新版本Keil(MDK-ARM)V5.21a开发环境.以STM32的处理器为例给大家讲述新建一个软件工程的详细过程. Keil(MDK-ARM)V4和V ...

  2. STM32基于库函数新建工程模板

    基于库函数版本 准备资料: a) V3.5 固件库包:STM32F10x_StdPeriph_Lib_V3.5.0 这是 ST 官网下载的固件库完 整版,我们光盘目录: 软件资料\STM32 固件库使 ...

  3. 从零开始学习STM32(一)—— 新建工程模板

    从零开始学习STM32(一)-- 新建工程模板 前言 准备工作 软件下载 必要文件下载 新建工程 结语 前言 从零开始学习STM32系列将由浅入深,和大家一起走进STM32的世界. 本系列的学习是基于 ...

  4. 学习笔记三(STM32串口程序下载新建工程模板)

    STM32串口程序下载 STM32F4 的程序下载有多种方法:USB.串口.JTAG.SWD 等,这几种方式,都可以用来给STM32F4下载代码. 利用串口给STM32下载程序 STM32 的串口下载 ...

  5. STM32入门笔记(02):MDK Keil5 开发环境搭建及新建工程模板教程(SPL库函数版)

    目录 Keil5 开发环境搭建 芯片数据手册 Mec 多功能智能小车底盘开发与使用手册 Mec 主控原理图 Mec STM32F103VET6集成主控板资源分配 Mec OLED 显示内容 如何给 S ...

  6. 正点原子stm32F407学习笔记1——新建工程模板

    一.基于固件库 1.新建文件夹 新建一个Template文件夹,在此文件夹下新建五个子文件夹 2.打开keil软件,点击菜单栏Project –>New Uvision Project,如果有其 ...

  7. STM32学习笔记——MDK新建项目

    STM32学习笔记 KIEL新建项目过程 文章目录 STM32学习笔记 前言 一.keil新建库函数版本项目 二.注意事项 1.文件分类 2.MDK配置 总结 前言 此处使用寄存器版,进行学习.后期看 ...

  8. 【STM32】新建工程模板及配置

    系列文章目录 ·[STM32]新建工程模板及配置 ·[STM32]STM32与PC端.HC-06.ROS进行USART串口通信 ·[ROS]ROS上位机使用Serial库和boost::asio库与S ...

  9. 正点原子STM32F103ZET6学习笔记-新建库函数工程模板

    STM32F10x系列官方固件包免费下载链接 新建STM32工程 步骤一:创建工程文件 1,新建工程目录temp 2,在工程目录temp下面新建四个文件夹 (1)USER:存放工程文件(templat ...

最新文章

  1. org.apache.shiro.ini不存在 shiro不能导包
  2. 2021-03-04 Halcon初学者知识 【18】谈谈秩滤波(Rank filter)
  3. 树的先序遍历,中序遍历,后续遍历(递归和非递归实现)
  4. Flex通用克隆(clone)方法
  5. SpringMVC_2.搭建SpringMVC
  6. 为何采用双亲委派机制
  7. php 接口说明文档,phpwind文章中心接口说明
  8. 数据库闪退_解决APP连续闪退的方案
  9. 基于R语言地理探测器包(GD)空间异质性与驱动力分析
  10. xps 转 pdf android版,xps文件转换pdf
  11. windows 批量创建文件夹
  12. 百度网盘无提取码分享文件方法
  13. linux kernel 摄像头驱动
  14. MySQL例题一 综合案例(多条件组合查询)
  15. NetSpeeder V3.70 绿色特别版
  16. 08s01 mysql_mysql报错 code:08S01,msg:SQLSTATE
  17. Dining (网络流)
  18. plc服务器作用,工业控制系统以及PLC的简单介绍
  19. 使用卷积神经网络进行实时面部表情检测
  20. 介绍计算机说明文,介绍电脑的说明文作文300字

热门文章

  1. 四旋翼无人机学习第6节--SPL06气压传感器和MPU9250九轴传感器电路分析
  2. Wparam与Lparam的区别(转)
  3. 深度linux没有硬盘,安装Deepin系统到硬盘分区部分没有发现硬盘数据的解决
  4. 雷军:为什么马云马化腾创业那么容易成功 自己却需要煎熬数年
  5. 打开 html 无地址栏,打开网页没有地址栏怎么办?
  6. MySQL事务及实现原理
  7. echarts 矩阵图用法
  8. 1、债权融资 - 打造企业上市系列文章
  9. php7不再把十六进制当数字,php7 参数、整形及字符串处理机制修改实例分析
  10. 审查元素html不能展开,爬取页面和审查元素获取的内容不一致