IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> 嵌入式 -> 02_STM32启动文件详解 -> 正文阅读

[嵌入式]02_STM32启动文件详解

目录

介绍

一、Stack-栈(使用的是RAM的内存)

二、Heap-推(使用的是RAM的内存)

三、中断向量表(使用的是flash)

四、复位函数

五、中断服务函数地址


六、堆和栈的初始化


介绍

启动文件是以.s后缀的汇编编写的,启动文件的作用:

1.初始化推栈指针SP ?

2.初初始化PC指针,指向复位程序

3.初始化中断向量表

4.配置系统时钟

5.调用C库函数_main,最终进入c语言编写的代码

一、Stack-栈(使用的是RAM的内存)

作用:用于局部变量、函数调用、函数形参的开销

汇编指令讲解:

EQU:宏定义的伪指令,相当于等于,类似于C语言中的宏定义define

AREA: 告诉汇编器汇编一个新的代码段或者数据段

SPACE:用于分配一定大小的内存空间,单位字节

Stack_Size      EQU     0x00000400

                AREA    STACK, NOINIT, READWRITE, ALIGN=3
Stack_Mem       SPACE   Stack_Size
__initial_sp

Stack_Size ?????EQU ????0x00000400

Stack_Size?等于 0x00000400(1kb)的空间

AREA ???STACK, NOINIT, READWRITE, ALIGN=3

定义栈空间 ?命名为STACK,NOINIT表示不初始化,READWRITE表示可读可写,ALIGN=3表示2的3次方(8个字节)对齐开辟。

Stack_Mem ??????SPACE ??Stack_Size

分配内存为Stack_Size大小的空间单位字节

__initial_sp

初始化栈指针就是指向栈顶地址(栈使用的时候栈顶先出依次到栈底,先进后出)

标号__initial_sp紧挨着SPACE语句放置,表示栈的结束地址,即栈顶地址,栈是由高向低生长的。

二、Heap-推(使用的是RAM的内存)

作用:用于动态内存的分配,malloc函数

EQU:宏定义的伪指令,相当于等于,类似于C语言中的宏定义define

AREA: 告诉汇编器汇编一个新的代码段或者数据段

SPACE:用于分配一定大小的内存空间,单位字节

Heap_Size       EQU     0x00000400

                AREA    HEAP, NOINIT, READWRITE, ALIGN=3
__heap_base
Heap_Mem        SPACE   Heap_Size
__heap_limit

Heap_Size ??????EQU ????0x00000400

Heap_Size?等于 0x00000400(1kb)的空间

AREA ???STACK, NOINIT, READWRITE, ALIGN=3

定义栈空间 ?命名为HEAP,NOINIT表示不初始化,READWRITE表示可读可写,ALIGN=3表示2的3次方(8个字节)对齐开辟。

__heap_base

表示堆的起始地址

Heap_Mem ???????SPACE ??Heap_Size

分配内存为Heap_Size大小的空间单位字节

__heap_limit

初始化推指针

标号__initial_sp紧挨着SPACE语句放置,表示推的结束地址,堆是由低向高生长的(于栈相反)。

                PRESERVE8
                THUMB

PRESERVE8表示指定当前文件的推栈按照8字节对齐

THUMB表示后面指令位THUMB指令

三、中断向量表(使用的是flash)

AREA: 告诉汇编器汇编一个新的代码段或者数据段

EXPORT:声明一个标号具有全局属性,类似于C中的extem功能

DCD:分配一个或者多个以字节为单位的内存,以四字节对齐,并要求初始化这些内存。在向量表中,DCD分配了一推内存,并且以ESR的入口地址初始化它们。

AREA: 告诉汇编器汇编一个新的代码段或者数据段

1.向量表实际上是一个32位的整形数组,一个元素对应一个异常(ESR:中断程序服务地址),数组元素存的就是ESR的入口地址。

2.向量表在复位后从FLASH的0地址开始,具体的初始化值查询参考手册的中断章节。

                AREA    RESET, DATA, READONLY
                EXPORT  __Vectors
                EXPORT  __Vectors_End
                EXPORT  __Vectors_Size

AREA ???RESET, DATA, READONLY

定义一个数据段 命名为RESET,DATA表示数据, READONLY表示可读

EXPORT ?__Vectors

表示向量表的开始地址(全局属性)

EXPORT ?__Vectors_End

表示向量表的结束地址(全局属性)

EXPORT ?__Vectors_Size

表示向量表的大小(全局属性)

__Vectors       DCD     __initial_sp
               DCD     Reset_Handler 
等等很多
               DCD     SysTick_Handler 
               DCD     WWDGT_IRQHandler  
等等很多
               DCD     USBFS_IRQHandler
__Vectors_End

__Vectors_Size  EQU     __Vectors_End - __Vectors

                AREA    |.text|, CODE, READONLY

__Vectors ??????DCD ????__initial_sp ?????????????????????

中断向量表的第一个字节存放的是__initial_sp栈顶的指针

???????????????DCD ????Reset_Handler

中断向量表的第二个字节存放的是Reset_Handler函数入口地址

??????????????DCD ????SysTick_Handler

SysTick_Handler以上是内核使用的

DCD ????WWDGT_IRQHandler

从 WWDGT_IRQHandler到USBFS_IRQHandler,都是用户使用的。

__Vectors_End

表示向量表结束

__Vectors_Size ?EQU ????__Vectors_End - __Vectors

表示量表的大小 ??__Vectors_Size=Vectors结束地址-Vectors开始地址

AREA ???|.text|, CODE, READONLY

定义一个代码段 ??命名text, CODE表示代码段,READONLY只读

四、复位函数

PROC:表示子程序的开始

EXPORT:声明一个标号具有全局属性,类似于C中的extem功能

WEAK:表示弱定义,如果外部文件优先定义了该标号则首先引用该标号,如果外部文件没有声明也不会出错。这里表示复位子程序可以有程序用户在其他文件重新实现,这里并不是唯一的。

IMPORT:表示该标号来自外部文件,跟C语言中的extern关键字类似。

LDR:从存储器中加载字到一个寄存器中

BLX:跳转到有寄存器给出的地址,并根据寄存器的LES确定处理器的状态,还要吧跳转钱的下一条指令地址保存到LR

BX:跳转到有寄存器/标号给出的地址,不用返回

ENDP:表示子程序的结束

Reset_Handler   PROC
                EXPORT  Reset_Handler                     [WEAK]
                IMPORT  SystemInit
                IMPORT  __main
                LDR     R0, =SystemInit
                BLX     R0
                LDR     R0, =__main
                BX      R0
                ENDP

Reset_Handler ??PROC

表示复位子程序开始

???????????????EXPORT ?Reset_Handler ????????????????????[WEAK]

表示用户可在其他地方定义全局函数

????????????????IMPORT ?SystemInit

外部的一个函数SystemInit:主要初始化系统时钟

????????????????IMPORT ?__main

外部的一个函数

LDR ????R0, =SystemInit

把SystemInit函数入口地址加载到R0寄存器中

BLX ????R0

跳转到R0寄存器去执行里面的函数,执行完返回。

????????????????LDR ????R0, =__main

把__main函数入口地址加载到R0寄存器中。

(注意这里的_main不是我们写程序的main,这里的_main是外部导入进来的,是C库里面的,执行这个_main后最后会道我们写程序的main里面)

_main的作用:1.初始化程序里面的局部变量全局变量由C库完成2.调用我们写程序的mai函数

????????????????BX ?????R0

执行完不用返回

????????????????ENDP

子程序结束

五、中断服务函数地址

PROC:表示子程序的开始

EXPORT:声明一个标号具有全局属性,类似于C中的extem功能

WEAK:表示弱定义,如果外部文件优先定义了该标号则首先引用该标号,如果外部文件没有声明也不会出错。这里表示复位子程序可以有程序用户在其他文件重新实现,这里并不是唯一的。

B .:表示无限循环

用汇编全写好了,在三章中断向量表初化函数__initial_sp用到

NMI_Handler     PROC
                EXPORT  NMI_Handler                       [WEAK]
                B       .
                ENDP

NMI_Handler ????PROC

表示子程序的开始

????????????????EXPORT ?NMI_Handler ??????????????????????[WEAK]

表示用户可在其他地方定义全局函数

????????????????B ??????.

表示无限循环

????????????????ENDP

子程序结束

六、堆和栈的初始化

上面我们只是开辟了空间没有初始化

EXPORT:声明一个标号具有全局属性,类似于C中的extem功能

IMPORT:表示该标号来自外部文件,跟C语言中的extern关键字类似。

IF、ELSE:和C语言的if、else一样


                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 PROC
                LDR     R0, =  Heap_Mem
                LDR     R1, =(Stack_Mem + Stack_Size)
                LDR     R2, = (Heap_Mem +  Heap_Size)
                LDR     R3, = Stack_Mem
                BX      LR
                ENDP

                ALIGN

                ENDIF

                END

如果DEF:__MICROLIB成立就把__heap_limit、__heap_base、__initial_sp声明为全局文件

如果没定义会执行__user_initial_stackheap PROC这段代码来初始化(我们都是会定义DEF:__MICROLIB这个的所以不会跑去执行下面这段代码区执行)

  嵌入式 最新文章
基于高精度单片机开发红外测温仪方案
89C51单片机与DAC0832
基于51单片机宠物自动投料喂食器控制系统仿
《痞子衡嵌入式半月刊》 第 68 期
多思计组实验实验七 简单模型机实验
CSC7720
启明智显分享| ESP32学习笔记参考--PWM(脉冲
STM32初探
STM32 总结
【STM32】CubeMX例程四---定时器中断(附工
上一篇文章      下一篇文章      查看所有文章
加:2022-10-17 12:50:48  更:2022-10-17 12:53:57 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年5日历 -2024/5/19 19:22:06-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码