stm32 G030F6P6拥有32kbFlash 8kbSRAM
下述功能可实现掉电不丢失
该芯片拥有16个扇区,每个扇区内存大小为2kb,如下图所示每个扇区地址
读:读取该地址半字
/*****
*
* 读地址的字
*
* ****************************/
uint16_t MyFLASH_ReadHalfWord(uint32_t Address)//读-----0x08000000
{
return *((__IO uint16_t *)(Address)); //使用指针访问指定地址下的数据并返回
}
写:G030只支持64位(双字节)写入
/**********
*
* 写数据
* uint32_t page_address 写页面地址 第15页:((uint32_t)0x08007800)
* uint64_t DATA_64 把两个字写到对应页数
*
* *********************************/
void FLASH_programword(uint32_t page_address,uint64_t DATA_64)
{
HAL_FLASH_Unlock();
HAL_FLASH_Program(FLASH_TYPEPROGRAM_DOUBLEWORD, page_address, DATA_64);
HAL_FLASH_Lock();
}
擦除:
注:尽量少擦除flash 避免擦除过多引起扇区损坏(扇区支持擦除1000次)
扇区擦除只能整页擦:整页擦出函数,需要自己定义一下结构体
HAL_StatusTypeDef HAL_FLASHEx_Erase(FLASH_EraseInitTypeDef *pEraseInit, uint32_t *PageError)
/************
*
* 擦除(只擦除一页)
* BANK1
* uint8_t Addr 0-15页 stm32G030F6P6 32K的flash 一页是2KB
*
* ********************************/
int FLASH_ErasePage(uint8_t Addr)//擦除页
{
HAL_FLASH_Unlock(); // 解锁Flash
FLASH_EraseInitTypeDef EraseInitStruct;
uint32_t PageError=0;//擦除错误地址
EraseInitStruct.TypeErase = FLASH_TYPEERASE_PAGES;//仅擦除页
EraseInitStruct.Banks = FLASH_BANK_1;
EraseInitStruct.Page = Addr;//注:该page为0-15页
EraseInitStruct.NbPages = 1;//擦除一页
if(HAL_FLASHEx_Erase(&EraseInitStruct, &PageError) != HAL_OK)
{
return 1;
}
return 0;
HAL_FLASH_Lock();
}
上述擦除,写入,读取功能了解后开始实现掉电不丢失,可借鉴江科大视频
初始化第15页扇区、保存数据、清空flash:
uint64_t FLASH_data[2];
void store_init()
{
//————————————查看需要写入地址是否有数据,无数据写入标志位和0————————————————————
if( MyFLASH_ReadHalfWord( ((uint32_t)0x08007800) ) != 0x1234)
{
FLASH_ErasePage(15);
FLASH_programword(FLASH_15_address,((uint64_t)0x1234123412341234));
for(uint16_t i =4;i < 2 ; i++)
{
FLASH_programword(((uint32_t)0x08007800) + i*8,0x0000000000000000);//整页0
}
}
//-----------上电后将地址0x08007800FLASH数据放到FLASH_data[]-----------------
FLASH_data[0]=((uint64_t)0x1234123412341234);
for(uint16_t i = 1; i < 2; i ++)
{
FLASH_data[i] = MyFLASH_ReadHalfWord( ((uint32_t)0x08007800)+ i*8 );
}
}
void store_save()//写入数据然后调用函数进行保存
{
FLASH_ErasePage(15);
for(uint16_t i =0;i < 2 ; i++)//----FLASH_data[i]数据备份到FLASH中---------
{
FLASH_programword(((uint32_t)0x08007800) + i*8,FLASH_data[i]);
}
}
void store_clear()
{
for(uint16_t i =1;i < 256 ; i++)//----数据备份到闪存中---------
{
FLASH_data[i]=0x0000000000000000;
}
store_save();
}
示例:
我实现的功能是擦除最后扇区,将数据保存在第15页扇区,上电读取扇区内容再将接收到的数据保存。
store_init();//初始化所需扇区,可加形参,稍作修改
/* USER CODE END 2 */
FLASH_data[1]=0x1234567812126789;
store_save();//保存FLASH_data[1]到flash