通过keil编译明白自己的程序占用的内存大小。堆栈大小分配,32单片机片内存储flash的使用。

1.通过keil编译程序,得到自己代码需要单片机的flash和RAM大小

在这里插入图片描述
1、Code 是代码占用的空间,存在ROM(flash)里。
2、RO-data是 Read Only 只读常量的大小,如const型,存在ROM(flash)里。
3、RW-data是(Read Write) RW是可读可写变量,就是初始化时候就已经赋值了的,个存在两个地方,初始化量存在ROM/FLASH中,由于还要对其进行“写”操作 所以RAM中也要占用相应的空间。
4、ZI-data是(Zero Initialize) 没有初始化的可读写变量的大小,就是程序中用到的变量并且被系统初始化为0的变量的字节数,keil编译器默认是把你没有初始化的变量都赋值一个0,这个显然也是存在RAM中。给堆栈分配的内存也在这里。

所以本工程要求单片机
ROM(FLASH) > code+RO-data+RW-data
RAM > RW-data+ZI-data

2.在程序中调整堆栈的大小

对于堆栈大小的调整
在这里插入图片描述
在程序中调用堆栈,对堆栈大小的挑战才是有意义的,例如在程序中没有申请动态内存,那么不论给堆多大的内存,在程序编译时都不会占用单片机flash。可以尝试,分别在用/不用 动态内存时调整堆给堆分配的空间,编译后观察ZI-data大小的变化。栈区方法相同,可以尝试不定义任何形参和 局部变量观察ZI-data大小的变化。

3.单片机片内flash的使用

在这里插入图片描述
我们说的flash就是上图中程序的主存储快,stm32c8,有64kB,stm32cB,有128kB,在生产时原料相同生产方法相同,stm32cB中质量不好的按stm32c8来卖。在出售前厂家会测试stm32cB的128KB存储空间,只测试stm32c8的前64KB存储空间,所以大多数stm32c8单片机也可以和stm32cb一样使用128kb的flash,只是厂家只保证前64KB的存储空间不会出问题,后面的空间厂家也没测,能不能用都靠运气。但是生产工艺一直在进步,所以大多数stm32c8单片机后面没测试的存储空间也能使用。

FLASH擦除是按照扇区擦的,所以这个很重要,在工程中全局搜索 FLASH_PAGE_SIZE 宏就可以查看该芯片的页(扇区)大小,改宏在 stm32xxx_hal_flash.h中有定义
F1和F4系列的芯片FLASH在擦除后会是0xFFFFFFFF,而L1系列的芯片FLASH在擦除后是0x00000000!!!
L1芯片内部FLASH编程速度比F1慢50倍!!!所以在使用L1芯片写入数据时相对于F1慢是正常的

STM32闪存的编程每次必须写入16位,任何不是半字的操作都会造成错误。


#include "FLSH.h"

 uint16_t EEPROM_data[20] = {0} ;  //flash等待存储的数据 
 
void WriteFlsh2B( uint16_t  page, uint16_t * EEPROM_Data,uint16_t  flash_byte)
{
	
	uint32_t  EEPROM_ADD = 0x08000000 + page * FLASH_PAGE_SIZE ;
	//1、解锁FLASH
	HAL_FLASH_Unlock();
	//2、擦除FLASH
	//初始化FLASH_EraseInitTypeDef
	FLASH_EraseInitTypeDef f;
	f.TypeErase = FLASH_TYPEERASE_PAGES;
	f.PageAddress = EEPROM_ADD;
	f.NbPages = 1;
	//设置PageError
	uint32_t PageError = 0;
	//调用擦除函数
	HAL_FLASHEx_Erase(&f, &PageError);
	for(short fo_i = 0 ; fo_i < flash_byte/2  ; fo_i ++)
	{
	  	//3、对FLASH烧写
     HAL_FLASH_Program(FLASH_TYPEPROGRAM_HALFWORD, EEPROM_ADD+fo_i*2 , *(EEPROM_Data+fo_i ));
 	}
 
	//4、锁住FLASH
 	HAL_FLASH_Lock();
}

//FLASH读取数据测试
void ReadFlash2B(  uint16_t  page, uint16_t * EEPROM_Data,uint16_t  flash_byte)
{
	 uint32_t  EEPROM_ADD = 0x08000000 + page * FLASH_PAGE_SIZE ;

 	for(short fo_i = 0 ; fo_i < flash_byte/2   ; fo_i ++)
	{
	//3、对FLASH烧写
     *(EEPROM_Data+fo_i  ) = *(__IO uint16_t*)(EEPROM_ADD+fo_i *2 );
 
	}
	
	
	
	
}

链接:stm32单片机内部flash闪存源码 百度云提取码 1111

参考了以下两个PDF

STM32F10xxx编程参考手册2010(中文)的第 2.3.3 嵌入式闪存
野火第45章 读写内部 FLASH

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值