对于stm32的启动过程一直心存疑惑。今天找了很多资料,进行了一个大致的分析。

1.cortex M3的复位过程(来自官方资料)

上述开机启动流程比较详细,内容较为全面,但部分步骤可以省略(红字可省略标出),因为对于某些初始化,我们可能会在main函数中重新配置。

2.复位程序的详细跟踪分析(重点)

此次分析基于单步跟踪stm32从复位到main()函数的汇编代码。
 

1.stm32复位程序

; Reset handler
Reset_Handler PROC
EXPORT Reset_Handler [WEAK]
IMPORT __main
IMPORT SystemInit
LDR R0, =SystemInit
BLX R0
LDR R0, =__main
BX R0
ENDP
这个程序的可以大致分解为以下两个函数的调用
SystemInit();
__main();
 
 

2.SystemInit()

功能:初始化时钟(SYSCLK, HCLK, PCLK2 and PCLK1 prescalers)、配置中断向量表(中断向量表的定位是在flash还是SRAM)。
void SystemInit (void)
{
/* Reset the RCC clock configuration to the default reset state(for debug purpose) */
/* Set HSION bit */
RCC->CR |= (uint32_t)0x00000001; /* Reset SW, HPRE, PPRE1, PPRE2, ADCPRE and MCO bits */
#ifndef STM32F10X_CL
RCC->CFGR &= (uint32_t)0xF8FF0000;
#else
RCC->CFGR &= (uint32_t)0xF0FF0000;
#endif /* STM32F10X_CL */ /* Reset HSEON, CSSON and PLLON bits */
RCC->CR &= (uint32_t)0xFEF6FFFF; /* Reset HSEBYP bit */
RCC->CR &= (uint32_t)0xFFFBFFFF; /* Reset PLLSRC, PLLXTPRE, PLLMUL and USBPRE/OTGFSPRE bits */
RCC->CFGR &= (uint32_t)0xFF80FFFF; #ifdef STM32F10X_CL
/* Reset PLL2ON and PLL3ON bits */
RCC->CR &= (uint32_t)0xEBFFFFFF; /* Disable all interrupts and clear pending bits */
RCC->CIR = 0x00FF0000; /* Reset CFGR2 register */
RCC->CFGR2 = 0x00000000;
#elif defined (STM32F10X_LD_VL) || defined (STM32F10X_MD_VL) || (defined STM32F10X_HD_VL)
/* Disable all interrupts and clear pending bits */
RCC->CIR = 0x009F0000; /* Reset CFGR2 register */
RCC->CFGR2 = 0x00000000;
#else
/* Disable all interrupts and clear pending bits */
RCC->CIR = 0x009F0000;
#endif /* STM32F10X_CL */ #if defined (STM32F10X_HD) || (defined STM32F10X_XL) || (defined STM32F10X_HD_VL)
#ifdef DATA_IN_ExtSRAM
SystemInit_ExtMemCtl();
#endif /* DATA_IN_ExtSRAM */
#endif /* Configure the System clock frequency, HCLK, PCLK2 and PCLK1 prescalers */
/* Configure the Flash Latency cycles and enable prefetch buffer */
SetSysClock(); #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
}

3.__main();重点

该函数属于C/C++库函数。
该函数的作用是
1.完成全局/静态变量的初始化工作
2.初始化堆栈
3.库函数的初始化
4.程序的跳转,进入main()函数。
 

1.加载_main()函数的相应汇编代码

2._main()函数的汇编代码

功能:跳转进入__scatterload_rt2函数。

3.__scatterload_rt2函数汇编代码(C库函数)

该函数的作用是设置四个寄存器为后续__scatterload_cpy()函数服务的。
设置待copy内容(静态变量、全局变量、常量)的的加载域和运行域,设置待copy内容的大小,跳转进入__scatterload_cpy函数
4.__scatterload_cpy函数(C库函数)
完成静态变量、全局变量、常量的从flash到SRAM的加载以及程序的跳转进入__scatterload_zeroinit函数
 
5.__scatterload_zeroinit函数(C库函数)
 
 
功能:未初始化的全局变量的初始化,跳转进入__user_steup_stackheap函数
 
6.__user_steup_stackheap函数(C库函数)
 
功能:实现用户的堆栈的配置
__user_steup_stackheap函数包含了以下函数的调用:
a.__user_libspace------------------------__user_libspace为C库保持了静态数据。这是一个96字节,0初始化的数据块,该块由C库创建。在C库初始化期间可以用来当做临时栈。
b.__user_initial_stackheap-------------------------------------------------用户的初始化堆栈函数
 
 
7._fp_init和__rt_fp_status_addr(C库函数)------------------------------------------------------两个函数调用实现浮点运算的支持
 
 
调用结束跳转进入main()函数
 
8.main()函数
 
 
 

STM32的启动过程分析的更多相关文章

  1. ASP.Net Core MVC6 RC2 启动过程分析[偏源码分析]

    入口程序 如果做过Web之外开发的人,应该记得这个是标准的Console或者Winform的入口.为什么会这样呢? .NET Web Development and Tools Blog ASP.NE ...

  2. 开机SystemServer到ActivityManagerService启动过程分析

    开机SystemServer到ActivityManagerService启动过程 一 从Systemserver到AMS zygote-> systemserver:java入层口: /** ...

  3. Neutron分析(2)——neutron-server启动过程分析

    neutron-server启动过程分析 1. /etc/init.d/neutron-server DAEMON=/usr/bin/neutron-server DAEMON_ARGS=" ...

  4. linux视频学习7(ssh, linux启动过程分析,加解压缩,java网络编程)

    回顾数据库mysql的备份和恢复: show databases; user spdb1; show tables; 在mysql/bin目录下 执行备份: ./mysqldump -u root - ...

  5. Activity启动过程分析

    Android的四大组件中除了BroadCastReceiver以外,其他三种组件都必须在AndroidManifest中注册,对于BroadCastReceiver来说,它既可以在AndroidMa ...

  6. Spark Streaming应用启动过程分析

    本文为SparkStreaming源码剖析的第三篇,主要分析SparkStreaming启动过程. 在调用StreamingContext.start方法后,进入JobScheduler.start方 ...

  7. ActivityManagerService启动过程分析

    之前讲Android的View的绘制原理和流程的时候,讲到过在Android调用setContentView之后,Android调用了一个prepreTravle的方法,这里面就提到了Activity ...

  8. Disconf源码分析之启动过程分析下(2)

    接上文,下面是第二次扫描的XML配置. <bean id="disconfMgrBean2" class="com.baidu.disconf.client.Dis ...

  9. Service启动过程分析

    Service是一种计算型组件,用于在后台执行一系列的计算任务.由于工作在后台,因此用户是无法直接感知到它的存在.Service组件和Activity组件略有不同,Activity组件只有一种运行模式 ...

随机推荐

  1. Highcharts 配置语法;Highcharts 配置选项详细说明

    Highcharts 配置语法 本章节我们将为大家介绍使用 Highcharts 生成图表的一些配置. 第一步:创建 HTML 页面 创建一个 HTML 页面,引入 jQuery 和 Highchar ...

  2. python 黑客书籍 ——扫描+暴力破解

    https://legacy.gitbook.com/book/germey/net-security/details 网络安全 介绍 构建一个端口扫描器 利用Pexpect模拟SSH连接 利用Pxs ...

  3. BGP&RIP

    策略路由是2000之前 如果不通检查是否有相互影响的策略 BGP 25端 查看 25是上端起lan 地址是172.100.1.254 互联158是下端起wan 172.100.1.158   25的内 ...

  4. Vue.directive使用注意

    首先,Vue.directive要在实例初始化之前,不然会报错,还有,定义的指令不支持驼峰式写法,也会报下面同样的错,虽然在源码中没有找到在哪里统一处理大小写,但是在有关directive的方法中捕捉 ...

  5. python之阶乘的小例子

    现在自己写阶乘是这个样子的 def f(x): return x * f(x-1) if x >1 else 1 后来无意中看到耗子的一篇<Python程序员的进化>的文章, 感脚这 ...

  6. PHP Socket(套接字连接)扩展简介和使用方法

    PHP socket扩展是基于流行的BSD sockets,实现了和socket通讯功能的底层接口,它可以和客户端一样当做一个socket服务器. 使用这些函数时请注意,虽然他们中有很多和C函数同名的 ...

  7. 【LeetCode 100_二叉树_遍历】Same Tree

    解法一:递归 bool isSameTree(TreeNode* p, TreeNode* q) { if (p == NULL && q == NULL) return true; ...

  8. 【LeetCode 110_二叉树_遍历】Balanced Binary Tree

    解法一:From top to bottom int treeHeight(TreeNode *T) { if (T == NULL) ; ; } bool isBalanced(TreeNode* ...

  9. Android Studio真机测试失败-----''No target device found" (转)

    参考文章: https://blog.csdn.net/chang_sir/article/details/51755572 今天想用真机测试一个程序,却报出这样一个Error"No tar ...

  10. linux远程win7教程

    http://jingyan.baidu.com/article/c275f6bacd2227e33c756754.html 1 在ubuntu下搜索Remmina(超级方便,应该也可以控制linux ...