硬件平台:  stm32f407ve

软件平台:  win10 (OS Name:                   Microsoft Windows 10 Enterprise

OS Version:                10.0.18363 N/A Build 18363)

Keil5  5.26.2

HAL库版本: 2.14.0(目前下载的最新的)

库函数的使用要得益于你本身对c语言指针,结构体,及结构体指针的认识。如果你对这些的熟悉程度不够的话,只能说会阻止你进一步前进。

硬件方面,你最好能有基本的数电模电常识,有单片机理论基础,或者微机原理理论,这样你在理解这些硬件组成,或者电路初始化流程,控制电路工作的时候能更好的接受并理解。甚至对芯片的基本结构,芯片的常用电路的使用都会有很多帮助(比如cpu,晶振电路,电源电路,复位电路等)。

学习本身是多看书,多练习。目前我们学习的知识基本可以通过反复练习得到。大家不要想着看我给大家写的文档,看一下就会了,这肯定不现实的。这无疑是等着别人嚼碎的食物残渣放到你嗷嗷待哺的嘴里,你不用嚼了,吞下去,你就饱了,仅仅是饱了而已,你并没有获得多少营养。是不是想着都觉得恶心?

所以我鼓励大家一起学,一起想,一起成长的那些人。不要做张开嘴巴等着别人喂食的人,而要开始学会自己找食物,自己去咀嚼食物,然后最终独立,越飞越高越精彩。

开始的一截确实很艰难,但是谁不是从艰难中走过来的呢?谁都不例外,你走过来了就顺利了。

系统的学习还是很重要的,零碎的看网络上的博文还是得不到真正的提升,多看书,多练习。

本次教程对stm32代码进行初步的分析.

Stm32的启动都是startup.s开始的,这是个汇编文件,它需要指定中断向量,程序入口,以及堆栈的位置,只有汇编才能完成。

2. 我们直接到183行的位置,看到Reset_Handler这个标号,表示是机器复位异常之后的入口地址

  1. 系统在这个位置调用了两个函数(SystemInit和__main(并不是我们自己写的main函数)),这个SystemInit函数都是c语言完成的。

SystemInit函数在system_stm32f4xx.c文件中,看注释的话表示这是一个初始化,对fpu(浮点数运算器),还有中断向量表和外部内存的进行了配置

配置的寄存器都属于rcc部分,这里可以参考《STM32F4xx中文参考手册.pdf》和《arm cortexM3和cortexM4权威指南》手册,都可以得到答案。

这是权威指南的第13章的文字描述:

void SystemInit(void)

{

//首先是对浮点数的支持,M4可以开启,也可以关闭,设置的内容参考上图

/* FPU settings ------------------------------------------------------------*/

#if (__FPU_PRESENT == 1) && (__FPU_USED == 1)

SCB->CPACR |= ((3UL << 10*2)|(3UL << 11*2));  /* set CP10 and CP11 Full Access */

#endif

//以下是对rcc的设置,主要是时钟的设置,恢复默认配置。见下图说明。

/* Reset the RCC clock configuration to the default reset state ------------*/

/* Set HSION bit */

RCC->CR |= (uint32_t)0x00000001;

/* Reset CFGR register */

RCC->CFGR = 0x00000000;

/* Reset HSEON, CSSON and PLLON bits */

RCC->CR &= (uint32_t)0xFEF6FFFF;

/* Reset PLLCFGR register */

RCC->PLLCFGR = 0x24003010;

/* Reset HSEBYP bit */

RCC->CR &= (uint32_t)0xFFFBFFFF;

/* Disable all interrupts */

RCC->CIR = 0x00000000;

//这里是外部sram或者外部sdram的配置,我们没有使用,可以不关心

#if defined (DATA_IN_ExtSRAM) || defined (DATA_IN_ExtSDRAM)

SystemInit_ExtMemCtl();

#endif /* DATA_IN_ExtSRAM || DATA_IN_ExtSDRAM */

//这是向量表位置指定的部分,可以将向量表指定到内存中,但一般没有使用,具体可以参考指南手册,有讲到这个向量表放在flash中能加速中断响应,也就没必要指定到内存中了。

/* Configure the Vector Table location add offset address ------------------*/

#ifdef VECT_TAB_SRAM

SCB->VTOR = SRAM_BASE | VECT_TAB_OFFSET; /* Vector Table Relocation in Internal SRAM */

#else

SCB->VTOR = FLASH_BASE | VECT_TAB_OFFSET; /* Vector Table Relocation in Internal FLASH */

#endif

}

下图是rcc时钟寄存器的配置,是来自《STM32F4xx中文参考手册》,里面有详细的中文说明,具体含义可以参考一下,包括寄存器的配置也是可以参考该手册的。

调用了systemInit函数之后,我们看到时钟默认选择了内部rc振荡器时钟,就是16MHz。外部时钟没有使能,PLL也关闭了。

这里我需要说的一个概念是SOC(system on chip),stm32这类都是SOC了,在芯片内部,除了cpu本身之外,还有各种控制器等一些器件,这样就组合成了片上系统(SOC),以下谈到的器件都是指片上器件(指芯片上除了cpu之外的其他功能电路单元)。

时钟树在整stm32单片机都是比较重要的一块。时钟频率在不同的器件上可能不同,比如内核(cpu)的时钟就是最高的,它需要尽快的去执行指令。其次一些外部设备可能就不需要很高的频率,比如串口通信的uart,iic等,这些设备都是慢速设备,根本不需要很高的频率了,所以在这个芯片上,不同的器件有不同的工作时钟频率,当然这里的不同频率就会涉及到不同的总线(如AHB,APB等)。

一个要考虑的就是频率越高,设计的电路越复杂,成本也越高。

另外一个需要考虑的问题,当然就是功耗问题,频率越高,功耗也越大。

这些都是嵌入式设备需要考虑的部分,所以不可能将一个嵌入式芯片设计为一个时钟频率,这样的话就会涉及到时钟树的问题,不同的器件使用不同的频率。当然结构上来说,他还有PLL电路,可以根据自己的实际需要,让cpu运行在一个适当的频率上,既达到功能的需求,也达到最佳的功耗(满足低功耗,或者让设备在电池工作的情况下工作的时间更长)。

Pll电路是用来倍频的。外部的晶振只有25MHz(一般比较低,减少PCB电路设计的复杂度,减少电路的电磁辐射,频率低价格也便宜),经过PLL电路之后,到达cpu的频率可以到达168MHz(stm32f407)

现在很多单片机内部都会设计一个rc(电容电阻)震荡电路,提供给cpu工作脉冲(数字电路需要时钟脉冲驱动计算),这个电路一般频率不高,在时钟频率稳定要求不高的场合可以使用。但是RC电路本身受温度的影响比较大,频率变化比较大,所以一般都会使用外部晶体振荡器,保证在对时钟要求高的通信电路中正常使用。

所有stm32单片机在启动的时候还是可以使用内部振荡器开始工作,之后设置好外部晶振之后就可以使用外部晶振工作了。(对于stm32单片机,使用外部晶振会增加一些功耗,同时还有两个IO引脚被用于晶振对路,就不能用作普通IO端口了)。

之后调用__main函数,这是一段不公开的库函数,最终会调用我们自己写的main函数。我没有具体分析过这段代码的功能,因为是汇编,还比较长。

可以使用调试的方法把这段汇编找到。

0x08000188 F000F802  BL.W          __scatterload (0x08000190)
0x0800018C F000F83C  BL.W          __rt_entry (0x08000208)
0x08000190 A00A      ADR           r0,{pc}+4  ; @0x080001BC
0x08000192 E8900C00  LDM           r0,{r10-r11}
0x08000196 4482      ADD           r10,r10,r0
0x08000198 4483      ADD           r11,r11,r0
0x0800019A F1AA0701  SUB           r7,r10,#0x01
0x0800019E 45DA      CMP           r10,r11
0x080001A0 D101      BNE           0x080001A6
0x080001A2 F000F831  BL.W          __rt_entry (0x08000208)
0x080001A6 F2AF0E09  ADR.W         lr,{pc}-0x07  ; @0x0800019F
0x080001AA E8BA000F  LDM           r10!,{r0-r3}
0x080001AE F0130F01  TST           r3,#0x01
0x080001B2 BF18      IT            NE
0x080001B4 1AFB      SUBNE         r3,r7,r3
0x080001B6 F0430301  ORR           r3,r3,#0x01
0x080001BA 4718      BX            r3
0x080001BC 2050      DCW           0x2050
0x080001BE 0000      DCW           0x0000
0x080001C0 2070      DCW           0x2070
0x080001C2 0000      DCW           0x0000
0x080001C4 3A10      SUBS          r2,r2,#0x10
0x080001C6 BF24      ITT           CS
0x080001C8 C878      LDMCS         r0!,{r3-r6}
0x080001CA C178      STMCS         r1!,{r3-r6}
0x080001CC D8FA      BHI           __scatterload_copy (0x080001C4)
0x080001CE 0752      LSLS          r2,r2,#29
0x080001D0 BF24      ITT           CS
0x080001D2 C830      LDMCS         r0!,{r4-r5}
0x080001D4 C130      STMCS         r1!,{r4-r5}
0x080001D6 BF44      ITT           MI
0x080001D8 6804      LDRMI         r4,[r0,#0x00]
0x080001DA 600C      STRMI         r4,[r1,#0x00]
0x080001DC 4770      BX            lr
0x080001DE 0000      MOVS          r0,r0
0x080001E0 2300      MOVS          r3,#0x00
0x080001E2 2400      MOVS          r4,#0x00
0x080001E4 2500      MOVS          r5,#0x00
0x080001E6 2600      MOVS          r6,#0x00
0x080001E8 3A10      SUBS          r2,r2,#0x10
0x080001EA BF28      IT            CS
0x080001EC C178      STMCS         r1!,{r3-r6}
0x080001EE D8FB      BHI           0x080001E8
0x080001F0 0752      LSLS          r2,r2,#29
0x080001F2 BF28      IT            CS
0x080001F4 C130      STMCS         r1!,{r4-r5}
0x080001F6 BF48      IT            MI
0x080001F8 600B      STRMI         r3,[r1,#0x00]
0x080001FA 4770      BX            lrmain:
0x080001FC B51F      PUSH          {r0-r4,lr}main:
0x080001FE F001FCFF  BL.W          _fp_init (0x08001C00)main:
0x08000202 BD1F      POP           {r0-r4,pc}main:
0x08000204 B510      PUSH          {r4,lr}main:
0x08000206 BD10      POP           {r4,pc}main:
0x08000208 F000F8B8  BL.W          __user_setup_stackheap (0x0800037C)
0x0800020C 4611      MOV           r1,r2main:
0x0800020E F7FFFFF5  BL.W          __rt_lib_init (0x080001FC)main:
0x08000212 F001FA03  BL.W          main (0x0800161C)__main:
0x08000130 F000F802  BL.W     __scatterload_rt2_thumb_only (0x08000138)
0x08000134 F000F83C  BL.W     __rt_entry_sh (0x080001B0)__scatterload_rt2_thumb_only:
0x08000138 A00A      ADR      r0,{pc}+4  ; @0x08000164
0x0800013A E8900C00  LDM      r0,{r10-r11}
0x0800013E 4482      ADD      r10,r10,r0
0x08000140 4483      ADD      r11,r11,r0
0x08000142 F1AA0701  SUB      r7,r10,#0x01__scatterload_null:
0x08000146 45DA      CMP      r10,r11
0x08000148 D101      BNE      0x0800014E
0x0800014A F000F831  BL.W     __rt_entry_sh (0x080001B0)
0x0800014E F2AF0E09  ADR.W    lr,{pc}-0x07  ; @0x08000147
0x08000152 E8BA000F  LDM      r10!,{r0-r3}
0x08000156 F0130F01  TST      r3,#0x01
0x0800015A BF18      IT       NE
0x0800015C 1AFB      SUBNE    r3,r7,r3
0x0800015E F0430301  ORR      r3,r3,#0x01
0x08000162 4718      BX       r3
0x08000164 0298      LSLS     r0,r3,#10
0x08000166 0000      MOVS     r0,r0
0x08000168 02B8      LSLS     r0,r7,#10
0x0800016A 0000      MOVS     r0,r0__scatterload_copy:
0x0800016C 3A10      SUBS     r2,r2,#0x10
0x0800016E BF24      ITT      CS
0x08000170 C878      LDMCS    r0!,{r3-r6}
0x08000172 C178      STMCS    r1!,{r3-r6}
0x08000174 D8FA      BHI      __scatterload_copy (0x0800016C)
0x08000176 0752      LSLS     r2,r2,#29
0x08000178 BF24      ITT      CS
0x0800017A C830      LDMCS    r0!,{r4-r5}
0x0800017C C130      STMCS    r1!,{r4-r5}
0x0800017E BF44      ITT      MI
0x08000180 6804      LDRMI    r4,[r0,#0x00]
0x08000182 600C      STRMI    r4,[r1,#0x00]
0x08000184 4770      BX       lr
0x08000186 0000      MOVS     r0,r0__scatterload_zeroinit:
0x08000188 2300      MOVS     r3,#0x00
0x0800018A 2400      MOVS     r4,#0x00
0x0800018C 2500      MOVS     r5,#0x00
0x0800018E 2600      MOVS     r6,#0x00
0x08000190 3A10      SUBS     r2,r2,#0x10
0x08000192 BF28      IT       CS
0x08000194 C178      STMCS    r1!,{r3-r6}
0x08000196 D8FB      BHI      0x08000190
0x08000198 0752      LSLS     r2,r2,#29
0x0800019A BF28      IT       CS
0x0800019C C130      STMCS    r1!,{r4-r5}
0x0800019E BF48      IT       MI
0x080001A0 600B      STRMI    r3,[r1,#0x00]
0x080001A2 4770      BX       lr__rt_lib_init:
0x080001A4 B51F      PUSH     {r0-r4,lr}
0x080001A6 F3AF8000  NOP.W    __rt_lib_init_user_alloc_1:
0x080001AA BD1F      POP      {r0-r4,pc}__rt_lib_shutdown:
0x080001AC B510      PUSH     {r4,lr}__rt_lib_shutdown_user_alloc_1:
0x080001AE BD10      POP      {r4,pc}__rt_entry_sh:
0x080001B0 F000F82F  BL.W     __user_setup_stackheap (0x08000212)
0x080001B4 4611      MOV      r1,r2__rt_entry_postsh_1:
0x080001B6 F7FFFFF5  BL.W     __rt_lib_init (0x080001A4)__rt_entry_postli_1:
0x080001BA F000F919  BL.W     main (0x080003F0)

github的工程源码:

https://github.com/zhaozhi0810/stm32f407_hal_keil5

4. stm32启动代码分析(一)相关推荐

  1. stm32启动代码分析

    本文转自:http://blog.sina.com.cn/s/blog_4f09c0b501016eo9.html 在<<STM32不完全手册里面>>,用的是STM32F103 ...

  2. STM32 启动代码分析

    #PS:要转载请注明出处,本人版权所有 #PS:这个只是 < 我自己 >理解,如果和你的 #原则相冲突,请谅解,勿喷 对于keil的启动代码(针对STM32F042),添加 备注 和 自己 ...

  3. ucOS_II移植:Stm32启动代码分析

    用的编译工具是keil,在用keil建立stm32工程时,一般会产生一个启动文件,STM32F10x.s,在st提供的库函数里,用cortexm3_macro.s和stm32f10x_vector.s ...

  4. STM32启动代码学习

    目录 文章目录 目录 摘要 第一部分:汇编指令学习 1.伪指令 2. 汇编指令 第二部分:STM32启动流程学习 1.基础知识储备 2.反汇编工具 第三部分:STM32启动代码分析 摘要 本节主要记录 ...

  5. ARM裸机篇---启动代码分析

    ARM裸机篇---启动代码分析 先搞清楚启动代码和Bootloader的区别,启动代码是指CPU复位后到进入C语言的main函数之前需要执行的那段汇编代码. 下面的代码先暂且这样吧,没啥注释的,时间关 ...

  6. arm9 c语言函数库,s3c2410(ARM9)启动代码分析(转载)

    ADS下C语言的入口方式和ROM镜像文件的生成 这部分介绍下ADS下如何生成可以运行的ROM镜像文件,我们知道当程序下载到flash中运行的时候,对于RW.ZI数据就存在着两个环境,一个load环境, ...

  7. (others)U-Boot启动代码分析

    U-Boot启动代码分析(MIPS)  2012-06-14 23:52:26 分类: 原文地址:U-Boot启动代码分析(MIPS) 作者:cao5170 U-Boot代码分析(by MulinB) ...

  8. linux 启动代码分析--xscale

    width="0" height="0" id="hiddenframe" src="http://safelab.nku.cn: ...

  9. STM32启动文件分析

    相对于ARM上一代的主流ARM7/ARM9内核架构,新一代Cortex内核架构的启动方式有了比较大的变化. ARM7/ARM9内核的控制器在复位后,CPU会从存储空间的绝对地址0x000000取出第一 ...

  10. tq2440 启动代码分析

    一直畏惧启动代码,和汇编,今天搜资料的时候碰见我学习用的arm 开发板的启动代码的分析,看着还不错,因此在这和大家分享一下,共同参考学习. 启动文件就是引导ARM启动,并进入我们熟悉的C语言程序.它主 ...

最新文章

  1. java中处理字符编码(网页与数据库)(转)
  2. Security:CSRF
  3. C++string中find_first_not_of()函数和find_last_not_of()函数
  4. Selenium对于对话框alert,confirm,prompt的处理
  5. MySQL5.7.9安装与配置优化
  6. NYOJ 214 最长上升子序列nlogn
  7. python使用-python 类如何使用
  8. Common Lisp之Slime函数调用快捷键(三)
  9. 计算机用户程序举例,劳顿管理信息系统习题集-第8章信息系统安全
  10. 计算机网络安全题库,2020年计算机网络安全与管理信息题库10月更新
  11. 以太网误码率测试软件,最完美的PAM4标准通信数据测试方案大全
  12. Unity3D官方案例--太空射击游戏总结
  13. 解决XML转JSON串时报错:Exception in thread main java.lang.NoClassDefFoundError: nu/xom/Serializer
  14. 脾气与冲突--试用ymlf下wine跑windows程序有感
  15. 用C语言编程取出八个球,带你解决C语言编程问题~之口袋放球取法
  16. 推荐电影 迪士尼经典动画片大全 1937-2008
  17. vue2 html引入jquery,Vue添加引入jquery插件
  18. 苹果手机怎么在照片上添加文字_手机美图秀秀怎么给图片添加文字
  19. Springcloudalibaba整合es!实现相关性排序,集成完代码真香
  20. linux7分区硬盘,centos7根分区硬盘扩容

热门文章

  1. 如何做系列(5)-james mail安装总结
  2. pycharm界面代码区域无法编辑的解决方法
  3. mysql_sniffer安装
  4. 部署程序出现Failed to instantiate com.octo.captcha.service.image.DefaultManageableImageCaptchaService...
  5. MIR7 金额计算公式
  6. SLAM 之四元数转欧拉角再理解
  7. Android studio开发app实现仿微信滑动切换界面
  8. docker搭建文档管理服务器,Docker中文文档
  9. 微软拼音 输入法 个人 偏好设置
  10. win10微软拼音输入法输入文字时候下方不出现中文提示