单片机FLASH和RAM内存分布

STM32内置有Flash和RAM(Flash分为Nor Flash和Nand Flash,STM32 M3、M4内核的单片机内为Nor Flash,程序可以直接在其运行;RAM分为SRAM和DRAM,STM32内为SRAM),硬件上他们是不同的设备存储器、属于两个器件,但这两个存储器的寄存器输入输出端口被组织在同一个虚拟线性地址空间内,也称存储器的地址映射。

单片机FLASH和RAM内存分布_第1张图片

1、MDK预处理、编译、汇编、链接后编译窗口会显示如下一段关于程序和数据大小的信息:

在这里插入图片描述

Code:代码所占字节大小;

RO-data(Read Only-Data):程序只读的变量,也就是带const的,和已初始化的字符串等;

RW-data(Read Write-Data):已初始化的可读写全局/静态变量;

ZI-data(Zero Initialize-Data):未初始化的可读写全局/静态变量;

在主存储器占用的空间大小=Code(可细分为中断向量表+代码)+RO data+RW data = 生成的.bin文件大小。
如下图,Text包含可执行代码 (Executable Code)和常量 (Literal Value),在Text之后就是只读数据区域 (Read Only Data),当然并不是所有架构的单片机都满足这样一个排布规律,这里只针对Cortex-M3 M4内核单片机,只读数据段后面接着的就是数据复制段 (Copy of Data Section),第一次遇到这个概念的朋友看到数据复制可能会有所疑惑,其实这个段充当的作用是存放程序中初始化为非 0 值的全局变量的初始值,之所以要将初始值存放到这里,是因为全局变量是存放在 RAM 上的,RAM 上的值掉电便丢失,每次上电后这些变量是要进行重新赋值的,而重新赋的值就存放在这里。那为什么不存放初始化为 0 的全局变量初始值呢,原因也很简单,既然是初始化为 0,那么在上电后统一对存放初始化为 0 的全局变量的那块区域(BSS段)清0就好了。

单片机FLASH和RAM内存分布_第2张图片

程序在SRAM存储器占用的空间大小RW data+ZI data。

Cortex-M内核的stm32上电后会把可以进行修改的变量复制到SRAM上,如RW data、ZI data,而对于不需要修改的数据如Code、RO-data不用复制到SRAM中,未初始化的变量ZI-data不会真正占用Flash的空间,处理器只会把未初始化的变量需要占用的字节个数存放在Flash,并不会真正为其分配空间,复制到SRAM时才会为他分配空间,并且初始化为0。SRAM中包含全局\静态区(地址从低到高分为已经初始化的数据data段、未进行初始化的数据bss段)、堆(Heap)、栈(Stack)。堆和栈的大小已经在启动文件startup.s里声明。

2、SRAM内存按地址由低到高分为四个区:

代码区(text段)、全局\静态区(地址从低到高分为文字常量区、已经初始化的数据data段、未进行初始化的数据BSS段)、堆(Heap)、栈(Stack)

对于栈区:由编译器自动释放,存放函数的形参、局部变量等。每当一个函数被调用时,该函数的返回类型和一些调用的信息被存放到栈中,然后这个被调用的函数再为它的变量(如局部变量)在栈上分配空间,每调用一个函数一个新的栈就会被使用。局部变量的生命周期也是有区别的,静态局部变量的生命周期是从程序开始到程序结束,而非静态局部变量在函数结束后被回收销毁。栈区存放数据是从高地址位向低地址位存放的,也就是栈顶(地址在栈区里最低)存放最新数据,栈底(地址在栈区里最高)存放第一个数据,是一块连续的内存区域,最大容量是由系统预先定义好的,申请的栈空间超过这个界限时会提示溢出,用户能从栈中获取的空间较小。
栈采用后进先出(LIFO) 策略,就像一杯倒立的水杯,杯底(也就是栈底)的水是最后倒出的也是最先倒进去的,杯顶(也就是栈顶)的水是最先倒出的也是最后倒进去的。
这里讲到变量的生命周期,那就回顾生命周期、作用域的意思。
生命周期:指的是程序执行过程中该变量存在的时间长短;
作用域:指的是变量可以在哪儿用,如只能在本函数调用、只能在本文件调用、可以被其他文件调用;

对于堆区:用于动态内存分配,位于BSS段和栈中间的地址区域,由程序员手动申请分配(malloc)和释放(free)。堆是从低地址位向高地址位增长,采用链式存储结构。频繁的使用malloc/free函数可能造成内存空间的不连续,产生碎片。当申请堆空间时库函数是按照一定的算法搜索可用的足够大的空间,因此堆的效率比栈要低的多。

对于代码区:不同单片机分布还不一样,部分单片机的RAM中并没有代码区。
下方是代码直接在Nor Flash运行的单片机中RAM的内存分布:

单片机FLASH和RAM内存分布_第3张图片
下方是单片机上电后需要将Flash中的代码复制到RAM中运行的单片机中RAM的内存分布,如Cortex-A7内核的单片机:
单片机FLASH和RAM内存分布_第4张图片

你可能感兴趣的:(stm32,嵌入式,单片机,stm32)