一、介绍/ S$ G9 Q- g* |0 q$ c5 @6 {" Q
1.1 片上eeprom介绍2 |: K8 o2 R9 k4 T# L6 m' l
L0的片上eeprom特性主要用来存储系统的配置信息,f103如果需要存储配置信息,还需要额外的一颗eeprom芯片,片上eeprom的机制也符合这系列的低功耗的属性。
: M3 D) Q' b3 k; P6 n6 p
+ I" d& d/ M; c1.2 写eeprom操作
! B9 G O8 Q- u0 a3 J( t# Z此操作旨在将字或字的一部分写入数据EEPROM。用户必须在正确的地址和大小写正确的值。内存接口在必要时自动执行擦除操作(如果所有位当前都设置为0,则无需在写入之前删除旧内容)。类似地,如果要写入的数据为0,则只执行擦除操作。当只执行写操作或擦除操作时,持续时间为Tprog(3.2 ms);如果两者都执行,则持续时间为2 x Tprog(6.4 ms)。每次擦除和写入操作都将FIX标志设置为1时,可以强制内存接口执行。( F: k4 j8 {1 Q0 s/ ~1 b
注意的是7 V* U6 s }. W( j( T. C
一般flash擦除后是0xff,而片上eeprom擦除后是0x00
; T( G- g0 @" x. _* X. b, ?$ n一般flash在编程前需要先擦除,而stm32的内存接口自动的执行了擦除操作,无需用户执行额外的擦除指令。5 d7 V# D( n* W P9 @' }& b) A: ]
/ g7 M, g% o. X @# }二、编程1 V/ d" V% x0 v& q$ j! D
- //eeprom地址3 i( b5 e2 ?1 {2 z& F
- #define EEPROM_BASE_ADDR 0x08080000/ s; \! c$ g& ]
- //向偏移地址写入len个字节
3 N$ ~' o1 j5 _2 |; A, @' [ - void eeprom_write(uint16_t BiasAddress, uint8_t *Data, uint16_t len)
$ \" Q# X0 U. ?2 { - {- y: R8 w g7 \+ j( b+ x
- uint16_t i;
& x, E0 t0 Q8 U* ~' N! \ - HAL_StatusTypeDef status = HAL_OK;
& W, M5 k( s( a2 ]) m" e1 V - 6 L* ?' W6 P) j7 C6 f! }2 ^# n9 X( P
- HAL_FLASHEx_DATAEEPROM_Unlock();1 i! K L# s+ z5 Q
- for(i=0;i<len;i++)7 a' z6 t) U* ~8 V. y+ T
- {
0 r6 |4 ^3 J- o! A7 T - status +=HAL_FLASHEx_DATAEEPROM_Program(FLASH_TYPEPROGRAMDATA_BYTE, EEPROM_BASE_ADDR+BiasAddress+i, *Data);& C8 \) F, m4 N) M* n. F" b
- Data++;
% ?; `6 L6 N4 ^( ^5 Q - }; x( z% n* ~* S! r6 X+ T
- HAL_FLASHEx_DATAEEPROM_Lock();
" ~, @8 r: [- S$ E$ {$ p - }
' z" N# _3 l( |4 E, C4 R - //向偏移地址读取len个字节; a3 ^4 z9 w1 S$ e- N
- void eeprom_read(uint16_t BiasAddress,uint8_t *Buffer,uint16_t Len)
( c8 [, ~3 t- I ? - {
( i; R6 T, o9 G! C - uint8_t *wAddr;; Z" L) T r1 p
- wAddr=(uint8_t *)(EEPROM_BASE_ADDR+BiasAddress);; ^' d6 K5 J. |6 w
- while(Len--)
! m' q4 A& M4 S% I1 T7 q \3 c8 f - {" J8 t: i& k5 G5 K8 ^; `. v8 s
- *Buffer++=*wAddr++;
8 m! q% p% X; r9 J - }
9 B2 g N1 ]* b+ z& C2 w3 F' n - }
复制代码 4 q5 n$ f/ b! m9 W
; W a k! B# ]
三、测试
! ^$ A. N5 B$ _7 M3.1 测试代码
* V' u; S! K+ N8 k/ R- //测试
- l9 N2 D: F! w' r - printf("开始测试\r\n");/ @* R ~* |7 e0 ?" y
- printf("写入eeprom数据:[0]:%x [1]:%x\r\n",eeprom_write_data[0],eeprom_write_data[1]);7 ^* A( I& a8 E8 J& R* C+ e
- eeprom_write(0,eeprom_write_data,2);8 f5 B" Q) J/ s- t
- HAL_Delay(10);
2 \: y2 U9 S, K2 p# l$ b- | - eeprom_read(0,eeprom_read_data,2);' Y6 }; V! X; p2 g y: c
- printf("读取的eeprom数据:[0]:%x [1]:%x\r\n",eeprom_read_data[0],eeprom_read_data[1]);
. r) Z1 p) @$ X3 n' T, [ - printf("片上eeprom测试完成\r\n");
复制代码
# E+ R, D6 O' l3 M+ W0 o# J- {3.2测试结果
8 [/ {. J# j% q% k7 ~$ P4 j% W0 F8 f向0x08080000写入两个字节和从改该地址读取两个的内容一致,测试成功。
/ P* S& B; ~7 d( r1 H2 P0 ~- I2 Q! {8 h! B* o% J+ }3 M
, V: \/ {! w/ r( |" v$ L" J
) c* \1 E$ C( F9 s% O' T8 ^
3 L& q8 X7 K+ b8 s4 i; O; d! ]0 ] |