STM32学习笔记01—STM32F103环境搭建 1.1 STM32F103单片机概述
ARM公司在ARM11以后的产品改用Cortex命名,主要分为三种,Cortex-M系列,Cortex-R系列和Cortex-A系列,Cortex系列属于ARMv7架构,这是2010年为止ARM公司最新的指令集架构,其中Cortex-M主要用于低端的嵌入式控制系统中,Cortex-R主要用于实时系统中,Cortex-A系列则是用于操作系统,智能设备和移动电话等领域,比如常见的Cortex-A15(用于Android,Ubuntu等系统中)。
意法半导体(ST公司)开发的STM32就属于Cortex-M架构,该架构细分又可以分为M0,M0+,M3,H7等,以最常见的STM32F103为例,该芯片属于Cortex-M3架构,CPU主频72MHz,内置高精度ADC,USART,CAN,USB,SDIO等模块,极大的便于产品的设计。
以STM32F103ZET6为例,该芯片封装为LQFP-144,内置资源如下所示:
(1)1组17通道高精度ADC,1组15通道ADC,1组13通道ADC,转换速度可达1us;
(2)1组2路DAC输出;
(3)8组高级定时器(可以做电容捕捉,PWM输出,基本定时等功能);
(4)高精度RTC模块,2路时钟可选;
(5)1组CAN,支持任意波特率;
(6)2组硬件IIC;
(7)3组硬件SPI;
(8)5组串口
(9)1组SDIO模块,用于外接SD卡通信;
(10)1组USB模块,可做主机,可做从机;
(11)2组I2S模块,用于I2S通信;
(12)1组CRC模块;
(13)2组看门狗模块;
(14)1组DMA模块;
STM32F103ZET6实物图片如下图所示。
1.2 STM32F103ZET6最小系统
1.2.1 原理图
STM32F103的最小系统由备用电源,下载接口,滤波电容,启动端子和时钟电路组成,其中滤波电容主要用于稳定CPU电源端口电压,由于CPU电源端口有12组,所以利用12个100nF电容来稳定每个端口的电压,布线的时候,每个电容离着供电端口越近越好。
1.2.2 时钟电路
单片机最小系统有两个晶体振荡器,其中8MHz提供主系统工作时钟脉冲,即CPU内核,系统总线和除RTC时钟外其他外设的工作时钟,32.768KHz时钟专用于CPU内部RTC时钟脉冲。
1.2.3 复位电路
由于STM32F103属于低电平复位,所以设计了如上图所示电路进行复位,初始状态电容两端电压为0,相当于低电平,上电后,电容开始充电,随着充电时间的上升,电容两端电压呈现指数上升(电路分析中专门讲解过这部分内容),随着电容充满电,电容两端理论电压逐渐达到3.3V,此时复位结束,如果想要不断电复位,只需要按一下按键S1,按下按键后,电容对地放电,放完电后达到低电平,此时开始复位,然后重复上电复位的过程。
1.2.4 启动选择端口
STM32有三种启动方式,通过BOOT0和BOOT1的电平选择,具体分配如下表所示。
一般启动程序都在FLASH中启动,如果出现芯片进入低功耗模式或者禁用了调试端口,那么串口激活是唯一的办法,所以建议设计产品的时候,BOOT0和BOOT1两个引脚用0Ω电阻引出来。
1.2.5 VBAT供电
VBAT供电主要用于RTC和备份区域数据不丢失使用,当外部3.3V断电之后,二极管D1处于截止状态,此时D2负极处于电平,二极管D2正向导通,通过3V纽扣电池给VBAT供电,防止RTC和备份区域的数据丢失。
1.2.6 串口下载与SW仿真
STM32下载程序有两种方式,一种是传统的串口模式,通过BOOT0和BOOT1启动系统存储器,然后将程序烧写进FLASH中,然后断电,设置FLASH启动后就可以启动程序,还有一种特殊的方式,就是SW模式,SW模式一种单线FLASH烧写模式,通过CLK和DATA两根线,将程序直接烧写进FLASH,并且通过这两根线进行在线仿真,可以直接将CPU中所有寄存器的值全部实时读取,用于简化调试过程。这个功能是51单片机不会有的。
1.2.7 电源电路
STM32F103采用3.3V电源进行供电,但是一般USB接口或者充电宝都是输出DC5V,这就需要一个LDO来进行电压变换,将5V电压转换为3.3V电压供STM32使用。
1.3 STM32工程创建
STM32的程序也是可以使用51的IDE编写的,KEIL作为集成开发环境,现在已经可以大多数主流CPU,比如之前的51系列,这次的ST系列,还有NXP公司的iMX系列等,下面来说明如何使用KEIL来创建STM32程序。
STM32的工程不同于51的工程,需要好几个文件来支持,由于这次创建的是空白工程,所以只需要创建主函数的c文件,启动汇编文件,和STM32寄存器文件。
(1)安装ARM版本的KEIL,从KEIL官网或者文中附带的链接下载安装包,安装时记住不能有中文路径,直接安装即可。
链接:https://pan.baidu.com/s/1cdk69c-CKiF6PfebpbNTAw
提取码:1p94
(2)安装STM32F1系列固件库,从KEIL官网找到安装包,下载后安装(注:KEIL版本必须是ARM版本的,C51版本安装不上)。
链接:https://pan.baidu.com/s/173qByEAwwrsPMwzvkxDrLA
提取码:lryg
下载固件库之后,双击安装即可。
(3)在工程文件夹中创建四个子文件夹,HEADERWARE,OBJECT,USER和SYSTEM,各文件夹内容如下所示。
USER:存放工程文件,汇编启动文件与主函数的c文件
SYSTEM:存放系统文件,串口1文件和滴答时钟文件
HEADERWARE:存放其他的驱动文件
OBJECT:存放编译过程的链接文件以及最终的HEX文件
(4)新建工程,输入工程保存路径后点击保存。
(5)选择目标芯片型号,我们使用的芯片型号是STM32F103ZET6
(6)点击工程设置,添加系统文件夹
点击红框选中的位置来新建文件夹,双击新建的文件夹修改名称,创建和步骤3目录一样的文件夹,如下图所示。
(7)创建启动汇编文件
点击保存,输入文件名stm32f103x.s后保存进User文件夹。
输入以下代码,由于以下代码是固定的,所以可以直接复制
- Stack_Size EQU 0x00000400
- AREA STACK, NOINIT, READWRITE, ALIGN=3
- Stack_Mem SPACE Stack_Size
- __initial_sp
- Heap_Size EQU 0x00000200
- AREA HEAP, NOINIT, READWRITE, ALIGN=3
- __heap_base
- Heap_Mem SPACE Heap_Size
- __heap_limit
- PRESERVE8
- THUMB
- ; Vector Table Mapped to Address 0 at Reset
- AREA RESET, DATA, READONLY
- EXPORT __Vectors
- EXPORT __Vectors_End
- EXPORT __Vectors_Size
- __Vectors DCD __initial_sp ; Top of Stack
- DCD Reset_Handler ; Reset Handler
- DCD NMI_Handler ; NMI Handler
- DCD HardFault_Handler ; Hard Fault Handler
- DCD MemManage_Handler ; MPU Fault Handler
- DCD BusFault_Handler ; Bus Fault Handler
- DCD UsageFault_Handler ; Usage Fault Handler
- DCD 0 ; Reserved
- DCD 0 ; Reserved
- DCD 0 ; Reserved
- DCD 0 ; Reserved
- DCD SVC_Handler ; SVCall Handler
- DCD DebugMon_Handler ; Debug Monitor Handler
- DCD 0 ; Reserved
- DCD PendSV_Handler ; PendSV Handler
- DCD SysTick_Handler ; SysTick Handler
- ; External Interrupts
- DCD WWDG_IRQHandler ; Window Watchdog
- DCD PVD_IRQHandler ; PVD through EXTI Line detect
- DCD TAMPER_IRQHandler ; Tamper
- DCD RTC_IRQHandler ; RTC
- DCD FLASH_IRQHandler ; Flash
- DCD RCC_IRQHandler ; RCC
- DCD EXTI0_IRQHandler ; EXTI Line 0
- DCD EXTI1_IRQHandler ; EXTI Line 1
- DCD EXTI2_IRQHandler ; EXTI Line 2
- DCD EXTI3_IRQHandler ; EXTI Line 3
- DCD EXTI4_IRQHandler ; EXTI Line 4
- DCD DMA1_Channel1_IRQHandler ; DMA1 Channel 1
- DCD DMA1_Channel2_IRQHandler ; DMA1 Channel 2
- DCD DMA1_Channel3_IRQHandler ; DMA1 Channel 3
- DCD DMA1_Channel4_IRQHandler ; DMA1 Channel 4
- DCD DMA1_Channel5_IRQHandler ; DMA1 Channel 5
- DCD DMA1_Channel6_IRQHandler ; DMA1 Channel 6
- DCD DMA1_Channel7_IRQHandler ; DMA1 Channel 7
- DCD ADC1_2_IRQHandler ; ADC1 & ADC2
- DCD USB_HP_CAN1_TX_IRQHandler ; USB High Priority or CAN1 TX
- DCD USB_LP_CAN1_RX0_IRQHandler ; USB Low Priority or CAN1 RX0
- DCD CAN1_RX1_IRQHandler ; CAN1 RX1
- DCD CAN1_SCE_IRQHandler ; CAN1 SCE
- DCD EXTI9_5_IRQHandler ; EXTI Line 9..5
- DCD TIM1_BRK_IRQHandler ; TIM1 Break
- DCD TIM1_UP_IRQHandler ; TIM1 Update
- DCD TIM1_TRG_COM_IRQHandler ; TIM1 Trigger and Commutation
- DCD TIM1_CC_IRQHandler ; TIM1 Capture Compare
- DCD TIM2_IRQHandler ; TIM2
- DCD TIM3_IRQHandler ; TIM3
- DCD TIM4_IRQHandler ; TIM4
- DCD I2C1_EV_IRQHandler ; I2C1 Event
- DCD I2C1_ER_IRQHandler ; I2C1 Error
- DCD I2C2_EV_IRQHandler ; I2C2 Event
- DCD I2C2_ER_IRQHandler ; I2C2 Error
- DCD SPI1_IRQHandler ; SPI1
- DCD SPI2_IRQHandler ; SPI2
- DCD USART1_IRQHandler ; USART1
- DCD USART2_IRQHandler ; USART2
- DCD USART3_IRQHandler ; USART3
- DCD EXTI15_10_IRQHandler ; EXTI Line 15..10
- DCD RTCAlarm_IRQHandler ; RTC Alarm through EXTI Line
- DCD USBWakeUp_IRQHandler ; USB Wakeup from suspend
- DCD TIM8_BRK_IRQHandler ; TIM8 Break
- DCD TIM8_UP_IRQHandler ; TIM8 Update
- DCD TIM8_TRG_COM_IRQHandler ; TIM8 Trigger and Commutation
- DCD TIM8_CC_IRQHandler ; TIM8 Capture Compare
- DCD ADC3_IRQHandler ; ADC3
- DCD FSMC_IRQHandler ; FSMC
- DCD SDIO_IRQHandler ; SDIO
- DCD TIM5_IRQHandler ; TIM5
- DCD SPI3_IRQHandler ; SPI3
- DCD UART4_IRQHandler ; UART4
- DCD UART5_IRQHandler ; UART5
- DCD TIM6_IRQHandler ; TIM6
- DCD TIM7_IRQHandler ; TIM7
- DCD DMA2_Channel1_IRQHandler ; DMA2 Channel1
- DCD DMA2_Channel2_IRQHandler ; DMA2 Channel2
- DCD DMA2_Channel3_IRQHandler ; DMA2 Channel3
- DCD DMA2_Channel4_5_IRQHandler ; DMA2 Channel4 & Channel5
- __Vectors_End
- __Vectors_Size EQU __Vectors_End - __Vectors
- AREA |.text|, CODE, READONLY
- ; Reset handler
- Reset_Handler PROC
- EXPORT Reset_Handler [WEAK]
- IMPORT __main
- LDR R0, =__main
- BX R0
- ENDP
- ; Dummy Exception Handlers (infinite loops which can be modified)
- NMI_Handler PROC
- EXPORT NMI_Handler [WEAK]
- B .
- ENDP
- HardFault_Handler\
- PROC
- EXPORT HardFault_Handler [WEAK]
- B .
- ENDP
- MemManage_Handler\
- PROC
- EXPORT MemManage_Handler [WEAK]
- B .
- ENDP
- BusFault_Handler\
- PROC
- EXPORT BusFault_Handler [WEAK]
- B .
- ENDP
- UsageFault_Handler\
- PROC
- EXPORT UsageFault_Handler [WEAK]
- B .
- ENDP
- SVC_Handler PROC
- EXPORT SVC_Handler [WEAK]
- B .
- ENDP
- DebugMon_Handler\
- PROC
- EXPORT DebugMon_Handler [WEAK]
- B .
- ENDP
- PendSV_Handler PROC
- EXPORT PendSV_Handler [WEAK]
- B .
- ENDP
- SysTick_Handler PROC
- EXPORT SysTick_Handler [WEAK]
- B .
- ENDP
- Default_Handler PROC
- EXPORT WWDG_IRQHandler [WEAK]
- EXPORT PVD_IRQHandler [WEAK]
- EXPORT TAMPER_IRQHandler [WEAK]
- EXPORT RTC_IRQHandler [WEAK]
- EXPORT FLASH_IRQHandler [WEAK]
- EXPORT RCC_IRQHandler [WEAK]
- EXPORT EXTI0_IRQHandler [WEAK]
- EXPORT EXTI1_IRQHandler [WEAK]
- EXPORT EXTI2_IRQHandler [WEAK]
- EXPORT EXTI3_IRQHandler [WEAK]
- EXPORT EXTI4_IRQHandler [WEAK]
- EXPORT DMA1_Channel1_IRQHandler [WEAK]
- EXPORT DMA1_Channel2_IRQHandler [WEAK]
- EXPORT DMA1_Channel3_IRQHandler [WEAK]
- EXPORT DMA1_Channel4_IRQHandler [WEAK]
- EXPORT DMA1_Channel5_IRQHandler [WEAK]
- EXPORT DMA1_Channel6_IRQHandler [WEAK]
- EXPORT DMA1_Channel7_IRQHandler [WEAK]
- EXPORT ADC1_2_IRQHandler [WEAK]
- EXPORT USB_HP_CAN1_TX_IRQHandler [WEAK]
- EXPORT USB_LP_CAN1_RX0_IRQHandler [WEAK]
- EXPORT CAN1_RX1_IRQHandler [WEAK]
- EXPORT CAN1_SCE_IRQHandler [WEAK]
- EXPORT EXTI9_5_IRQHandler [WEAK]
- EXPORT TIM1_BRK_IRQHandler [WEAK]
- EXPORT TIM1_UP_IRQHandler [WEAK]
- EXPORT TIM1_TRG_COM_IRQHandler [WEAK]
- EXPORT TIM1_CC_IRQHandler [WEAK]
- EXPORT TIM2_IRQHandler [WEAK]
- EXPORT TIM3_IRQHandler [WEAK]
- EXPORT TIM4_IRQHandler [WEAK]
- EXPORT I2C1_EV_IRQHandler [WEAK]
- EXPORT I2C1_ER_IRQHandler [WEAK]
- EXPORT I2C2_EV_IRQHandler [WEAK]
- EXPORT I2C2_ER_IRQHandler [WEAK]
- EXPORT SPI1_IRQHandler [WEAK]
- EXPORT SPI2_IRQHandler [WEAK]
- EXPORT USART1_IRQHandler [WEAK]
- EXPORT USART2_IRQHandler [WEAK]
- EXPORT USART3_IRQHandler [WEAK]
- EXPORT EXTI15_10_IRQHandler [WEAK]
- EXPORT RTCAlarm_IRQHandler [WEAK]
- EXPORT USBWakeUp_IRQHandler [WEAK]
- EXPORT TIM8_BRK_IRQHandler [WEAK]
- EXPORT TIM8_UP_IRQHandler [WEAK]
- EXPORT TIM8_TRG_COM_IRQHandler [WEAK]
- EXPORT TIM8_CC_IRQHandler [WEAK]
- EXPORT ADC3_IRQHandler [WEAK]
- EXPORT FSMC_IRQHandler [WEAK]
- EXPORT SDIO_IRQHandler [WEAK]
- EXPORT TIM5_IRQHandler [WEAK]
- EXPORT SPI3_IRQHandler [WEAK]
- EXPORT UART4_IRQHandler [WEAK]
- EXPORT UART5_IRQHandler [WEAK]
- EXPORT TIM6_IRQHandler [WEAK]
- EXPORT TIM7_IRQHandler [WEAK]
- EXPORT DMA2_Channel1_IRQHandler [WEAK]
- EXPORT DMA2_Channel2_IRQHandler [WEAK]
- EXPORT DMA2_Channel3_IRQHandler [WEAK]
- EXPORT DMA2_Channel4_5_IRQHandler [WEAK]
- WWDG_IRQHandler
- PVD_IRQHandler
- TAMPER_IRQHandler
- RTC_IRQHandler
- FLASH_IRQHandler
- RCC_IRQHandler
- EXTI0_IRQHandler
- EXTI1_IRQHandler
- EXTI2_IRQHandler
- EXTI3_IRQHandler
- EXTI4_IRQHandler
- DMA1_Channel1_IRQHandler
- DMA1_Channel2_IRQHandler
- DMA1_Channel3_IRQHandler
- DMA1_Channel4_IRQHandler
- DMA1_Channel5_IRQHandler
- DMA1_Channel6_IRQHandler
- DMA1_Channel7_IRQHandler
- ADC1_2_IRQHandler
- USB_HP_CAN1_TX_IRQHandler
- USB_LP_CAN1_RX0_IRQHandler
- CAN1_RX1_IRQHandler
- CAN1_SCE_IRQHandler
- EXTI9_5_IRQHandler
- TIM1_BRK_IRQHandler
- TIM1_UP_IRQHandler
- TIM1_TRG_COM_IRQHandler
- TIM1_CC_IRQHandler
- TIM2_IRQHandler
- TIM3_IRQHandler
- TIM4_IRQHandler
- I2C1_EV_IRQHandler
- I2C1_ER_IRQHandler
- I2C2_EV_IRQHandler
- I2C2_ER_IRQHandler
- SPI1_IRQHandler
- SPI2_IRQHandler
- USART1_IRQHandler
- USART2_IRQHandler
- USART3_IRQHandler
- EXTI15_10_IRQHandler
- RTCAlarm_IRQHandler
- USBWakeUp_IRQHandler
- TIM8_BRK_IRQHandler
- TIM8_UP_IRQHandler
- TIM8_TRG_COM_IRQHandler
- TIM8_CC_IRQHandler
- ADC3_IRQHandler
- FSMC_IRQHandler
- SDIO_IRQHandler
- TIM5_IRQHandler
- SPI3_IRQHandler
- UART4_IRQHandler
- UART5_IRQHandler
- TIM6_IRQHandler
- TIM7_IRQHandler
- DMA2_Channel1_IRQHandler
- DMA2_Channel2_IRQHandler
- DMA2_Channel3_IRQHandler
- DMA2_Channel4_5_IRQHandler
- B .
- ENDP
- ALIGN
- ; User Stack and Heap initialization
- IF :DEF:__MICROLIB
- EXPORT __initial_sp
- EXPORT __heap_base
- EXPORT __heap_limit
- ELSE
- IMPORT __use_two_region_memory
- EXPORT __user_initial_stackheap
- __user_initial_stackheap
- LDR R0, = Heap_Mem
- LDR R1, =(Stack_Mem + Stack_Size)
- LDR R2, = (Heap_Mem + Heap_Size)
- LDR R3, = Stack_Mem
- BX LR
- ALIGN
- ENDIF
- END
复制代码
(8)修改链接文件与HEX文件的保存路径
修改HEX的保存路径
修改链接文件的保存路径
(9)创建主函数的c文件,创建步骤与步骤7一样,只不过保存的时候,文件后缀变为c,例如1.c。将主函数的c文件保存到User目录下
(10)在c文件下输入如下代码
- #include <stdio.h>
- int main()
- {
- while( 1 )
- {
-
- }
- }
复制代码
(11)将刚才创建的2个文件添加进工程
|