你的浏览器版本过低,可能导致网站不能正常访问!
为了你能正常使用网站功能,请使用这些浏览器。

【经验分享】STM32F1x系列——Flash 模拟 EEPROM

[复制链接]
STMCU小助手 发布时间:2021-11-29 22:02
STM32F10x芯片本身没有集成EEPROM,替代方案是用片上Flash来模拟EEPROM。Flash与EEPROM的区别主要是:一、EEPROM可以按位擦写,而Flash只能按块(页)擦除;二、Flash的擦除寿命约1 万次,较EEPROM低一个量级。ST网站有个Flash模拟EEPROM的范例:AN2594: EEPROM emulation in STM32F10x microcontrollers(包括源码和文档)。范例在保存修改的数据时,以写入新数据来替代对原数据的修改,并使用两个页面轮流写入,单页写满后进行数据迁移,再一次性擦除旧页面。这个策略可以有效降低Flash擦除次数。
1 h& t; [8 G0 F" E4 Y6 J# @
; e* \/ ~* `8 n0 H; `7 d5 _. \  不过,范例代码只能保存固定大小的数据(16bits),虽然容易改成不同的固定大小,但实际用起来还是很不方便。我改写了一下,新的特性包括:7 S1 ?/ e6 b' F/ O' O
+ c3 q( z( A6 G, }" r
支持不同大小数据(字符数组、结构体等)的混合存储;# s# l, A. y9 F5 I
增加对数据的校验和(Checksum)检查。
8 p' Y! Q9 p& W% q  附件提供了源码。使用方法很简单,比如要保存一个字符数组 title 和一个 point 结构体:- Z5 G  ?; d6 I, a: @: Q
  1. #include "eeprom.h"
    " r7 U, ~& r1 v4 S: s# Z4 e
  2. 6 |3 S6 U$ {  A* ~" X
  3. #define TITLE_SIZE    80" [  ~! K" _" r* F* D; U1 i3 s
  4. #define TITLE_KEY     1
    ' q( V/ Y" N) v# u' v
  5. #define POINT_KEY     23 e! ]0 p) X8 G' a7 W

  6.   J+ S# p$ K; p- @: U
  7. typedef struct {0 t/ \  p2 N- [  d
  8.     float x;; z) O& m. {, e' X: g. |$ q# B
  9.     float y;
    3 u1 M  b* K8 q# y/ h
  10.     float z;1 X! p2 m4 N9 O" z4 w
  11. } Point;
    8 ^, Q0 _4 `, t! z7 ]8 [

  12. 8 g& j' _! n. K) [
  13. char title[TITLE_SIZE] = "eeprom test string.";
    5 k# k6 U* c7 W4 y  N: y  ]
  14. Point point;
复制代码

( J7 Z3 e9 F! G: g0 }执行必要的初始化操作后,就可以进行写入和读取:7 X! L( G+ K3 S( T: l: F5 w
  1. uint16_t result = 0;8 a' i; O2 W1 J8 @: o
  2. * u% E" A1 L. E! ?' C
  3. FLASH_Unlock();# u7 |$ {. y( n! s3 w  {
  4. # {) t2 x9 m+ q
  5. EE_Init();
    * x+ }( `8 H+ s
  6. . ?$ ~- ?% y( ^; J6 ~) ~9 j
  7. result = memcpy_to_eeprom_with_checksum(TITLE_KEY, title, TITLE_SIZE);* V+ o8 j* C- v& ]* Q, {
  8. result = memcpy_to_eeprom_with_checksum(POINT_KEY, &point, sizeof(point));' S. v8 M% i# t5 t

  9. 0 h& y# T8 I  k' n# K/ P
  10. result = memcpy_from_eeprom_with_checksum(title, TITLE_KEY, TITLE_SIZE);
    1 O) y% L8 _6 d6 n7 c6 v: d1 M% i: J
  11. result = memcpy_from_eeprom_with_checksum(&point, POINT_KEY, sizeof(point));
复制代码
  D+ T' S+ c; C
实现混合存储的办法,是给每个变量附加8字节的控制信息。因此,在存储小数据时会有较大的空间损耗,而在存储较大的数据结构时空间利用率更高(相对于范例)。代码是针对STM32F103VE的实现。不同芯片需要对应修改头文件中 EEPROM_START_ADDRESS 的定义:
  Y2 w  n1 I7 x# V0 A+ M
  1. #define EEPROM_START_ADDRESS    ((uint32_t)0x0807F000)
复制代码
9 H- M9 L& a! N1 v& g4 F

, P" ?: I- N# y; e7 E7 W3 {, s& Q! E  l% m3 I' O, A9 j! x
赞 收藏 评论0 发布时间:2021-11-29 22:02

举报

0个回答

所属标签

相似技术帖

关于
我们是谁
投资者关系
意法半导体可持续发展举措
创新与技术
意法半导体官网
联系我们
联系ST分支机构
寻找销售人员和分销渠道
社区
媒体中心
活动与培训
隐私策略
隐私策略
Cookies管理
行使您的权利
官方最新发布
人形机器人运动控制、感知与智能配电
半导体创新技术与应用方向
EE架构与软件定义汽车
12V/48V 汽车智能配电(SPD)
区域控制单元(ZCU)与分区架构
关注我们
st-img 微信公众号
st-img 手机版