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

【经验分享】STM32,仿照LL库,编写FLASH的LL库(内有完成代码)(STM32F0)

[复制链接]
STMCU小助手 发布时间:2021-11-13 23:00
不知道为为什么,STM32 LL库并没有FLASH的库函数,于是决定写一个
7 T2 R: w% L5 a1 |; h
% d. z, [5 U. U- M5 m& JLL库的特色,就是一个函数,只占用一个指令周期,比如,设置GPIO输出的状态,就是LL_GPIO_SetOutputPin();
, }. B1 Y! e2 R, G) \: V/ q- ^, l& ?
  1. __STATIC_INLINE void LL_GPIO_SetOutputPin(GPIO_TypeDef *GPIOx, uint32_t PinMask)
    * K8 B6 [+ R# m6 \
  2. {
    * t4 Q, T& _/ J: v$ U- L4 [2 ~$ F
  3.   WRITE_REG(GPIOx->BSRR, PinMask);2 H$ K. N  I0 t' C
  4. }
复制代码
于是我根据这种风格,已经常用的操作写了一个.h和.c文件9 _5 |  z1 E5 D1 L" Z) O

  g6 m# C. v6 y( ~' i8 c# z头文件代码5 W) H% i2 M$ j
  1. #ifndef __STM32F0xx_LL_FLASH_EX_H1 J9 j: j% s$ Y8 I! \
  2. #define __STM32F0xx_LL_FLASH_EX_H+ s6 ?  }# m! M# c+ F6 k
  3. : G/ S  W6 ?+ ^! `. V: Q5 \
  4. #include "stm32f0xx.h"/ w' Z2 C3 I+ z
  5. ! ^" j. M8 J6 O/ P
  6. ( q$ |, x$ f0 y% U* T; ~
  7. #define FLASH_FLAG_BSY             FLASH_SR_BSY            /*!< FLASH Busy flag                           */ 6 d! |+ S2 G' {+ v$ U
  8. #define FLASH_FLAG_PGERR           FLASH_SR_PGERR          /*!< FLASH Programming error flag    */
    0 \1 \; V, e' @4 T; p1 \3 x7 |
  9. #define FLASH_FLAG_WRPERR          FLASH_SR_WRPERR         /*!< FLASH Write protected error flag          */
    9 h# T( _% }' Y% ?  r. }' A
  10. #define FLASH_FLAG_EOP             FLASH_SR_EOP            /*!< FLASH End of Operation flag               */$ y- k0 l0 p4 \1 v5 t0 J7 E6 N

  11. ) t, O. s- d. b- I0 D$ s
  12. #define FLASH_TYPEERASE_PAGES          FLASH_CR_PER         /*!< FLASH_CR_PER          */
    . A! Y4 P5 Z# z4 E6 C* B
  13. #define FLASH_TYPEERASE_MASSERASE      FLASH_CR_MER            /*!< MASSERASE              */  O$ M0 X! _1 l) [

  14. ! t/ R7 w* @" M/ M) {4 T/ j5 t5 R0 x

  15. 1 g. }% ^% p+ c* o5 S
  16. #if defined(STM32F030x6) || defined(STM32F030x8) || defined(STM32F031x6) || defined(STM32F038xx) \9 e$ o, g) `7 v" U& S9 U
  17. || defined(STM32F051x8) || defined(STM32F042x6) || defined(STM32F048xx) || defined(STM32F058xx) || defined(STM32F070x6)
    6 O6 w. _3 F4 `0 ~( d
  18. #define FLASH_PAGE_SIZE          0x400U
    9 ^" ]2 n4 `$ w
  19. #endif /* STM32F030x6 || STM32F030x8 || STM32F031x6 || STM32F051x8 || STM32F042x6 || STM32F048xx || STM32F058xx || STM32F070x6 */
    2 a! K0 i* }: y! b! W
  20. - _  B( L: J9 h3 S& N
  21. #if defined(STM32F071xB) || defined(STM32F072xB) || defined(STM32F078xx) || defined(STM32F070xB) \
    8 @) K. o' E' L2 k  n
  22. || defined(STM32F091xC) || defined(STM32F098xx) || defined(STM32F030xC)  i. d; w9 c; P: J6 `
  23. #define FLASH_PAGE_SIZE          0x800U
    5 Q. d( [2 t: m1 A; G; S
  24. #endif /* STM32F071xB || STM32F072xB || STM32F078xx || STM32F091xC || STM32F098xx || STM32F030xC */: o  Y3 ?6 B. e2 a
  25. 9 ^4 ?0 D! V& }3 V
  26. typedef enum {
    - e8 U4 {: z; h1 H( y& e
  27.         ProgaraType_DATA64,
    ; d% f5 ^/ q- i2 q& u; T( [: W
  28.         ProgaraType_DATA32,
    8 X# s9 U. E6 k
  29.         ProgaraType_DATA16
    ' Z* K; d; i& ]; N6 q+ J
  30. }ProgaramDataType;, U- v8 O9 E3 l7 R) D1 v( r% p

  31.   ^8 e" r- {( `  B) o4 W+ Z, B8 U
  32. typedef enum {\
    * G* b! C" W; C, t  z
  33.         FLASH_Lock=1U,Flash_Unlock=!FLASH_Lock\2 Q$ D6 \; F! V& ~: a
  34. }FlashStates;8 P! y9 \4 r. N- d* I' Y" C' b, Q" F
  35. 0 h. N# T, d. C
  36.   /* Set the OBL_Launch bit to launch the option byte loading */
    / |# r# {! u7 i1 a% G& M/ p
  37. __STATIC_INLINE void LL_FLASH_SET_OBL_Launch(FLASH_TypeDef *FLASHx)& _% y% ]: V1 G
  38. {
    , A3 G. O' M* }$ W$ ?  s0 O
  39.   SET_BIT(FLASHx->CR, FLASH_CR_OBL_LAUNCH);
    8 r3 B) Q6 t* V& [3 Q
  40. }+ W9 O9 U% B2 v& Q5 r7 d
  41. __STATIC_INLINE void LL_FLASH_Lock(FLASH_TypeDef *FLASHx): e8 L1 K8 a: Z; c, q1 ]
  42. {
    4 R1 c. [+ m# g0 \
  43.   SET_BIT(FLASHx->CR, FLASH_CR_LOCK);
    3 N* A( O' ^) ], ]$ v
  44. }) h' Y* ]+ T8 x$ ]0 |0 k7 f. P
  45. , q6 u9 n- Y5 t

  46. 3 {4 {4 i( p3 u* t0 @
  47.   /* @brief  Set flash erase type.
    ! l6 R0 r2 p& q% Y: s+ l
  48.   * @param  FLASH_TYPEERASE specifies the FLASH flags to clear.  _& _* d/ [7 y) D$ r' c) c
  49.   *          This parameter can be any combination of the following values:" j. {: S! X" @$ R  {2 V( q
  50.   *            @arg @ref FLASH_TYPEERASE_PAGES         PAGES Erase4 D8 p. `4 B/ Q1 U0 u
  51.   *            @arg @ref FLASH_TYPEERASE_MASSERASE      FLASH Write protected error flag . R: u; e/ f- ]6 ~' h
  52.   * @retval none*/4 U5 y$ J$ t; ?9 P) w

  53. 8 A/ d! t4 t: S
  54. __STATIC_INLINE void LL_FLASH_SetTypeErase(FLASH_TypeDef *FLASHx,uint32_t FLASH_TYPEERASE)
    : q$ `' X" ?2 m; T
  55. {
    " m- z( Z* V) K$ e$ }2 M
  56.   SET_BIT(FLASHx->CR, FLASH_TYPEERASE);
    * R- f# C: @- k$ k4 S
  57. }
    2 h) f+ t$ f  h" U: b& O) C
  58.   /* @brief  Set flash erase ADDR.! c% O2 k! s! j/ f, }
  59.   *          This parameter can be any combination of the following values:% y0 |3 g8 D0 [7 X  W7 X8 \
  60.   *            @arg @ref EraseADDR         uint32_t value/ X, P4 B  Y9 ]+ O" g
  61.   * @retval none*/
    3 U4 X6 [2 Z* w- x2 x0 S

  62. . }; n+ L% \1 G# x* Q4 V! ?
  63. __STATIC_INLINE void LL_FLASH_SetEraseADDR(FLASH_TypeDef *FLASHx,uint32_t EraseADDR): P, e. n2 b2 g1 @  O
  64. {+ [0 L, M  Z- [( P# c
  65.   WRITE_REG(FLASHx->AR, EraseADDR);
    . t3 [* o; e$ z% I
  66. }; ]; X7 ]4 h' @( w4 Q  n- u
  67.   /* @brief  Set flash erase ADDR.
    ' T( B& c6 N8 v' _
  68.   *          This parameter can be any combination of the following values:1 b9 t; l* d" H  U9 W
  69.   *            @arg @ref EraseADDR         uint32_t value$ N- D, l) U" o# T# t4 S( C
  70.   * @retval none*/
      O% Y" H# v* d! ~7 Q! D- T
  71. + o+ u1 f7 p( X. }
  72. __STATIC_INLINE void LL_FLASH_StartErase(FLASH_TypeDef *FLASHx)
    / r3 P- g4 m" n2 F
  73. {6 Y: D/ O# |& X' z0 A7 \  Y
  74.   SET_BIT(FLASHx->CR, FLASH_CR_STRT);7 m! d3 B- e. r* `7 }5 b
  75. }
    ! M  D. M. @4 B& K. i+ O
  76. " B! `( ]0 R5 K1 a+ N" V+ i
  77.   /* @brief  Clear the specified FLASH flag.5 ~1 H. Z& d: D5 P/ V. k/ q: P9 }
  78.   * @param  __FLAG__ specifies the FLASH flags to clear.
    , n2 z2 ~. G; v( I, P* I
  79.   *          This parameter can be any combination of the following values:( V4 L7 Y3 e: H: t3 Z, P$ t
  80.   *            @arg @ref FLASH_FLAG_EOP         FLASH End of Operation flag * {7 {9 F( q$ D# V# W6 ~  n
  81.   *            @arg @ref FLASH_FLAG_WRPERR      FLASH Write protected error flag
    5 T/ P; G+ D. m
  82.   *            @arg @ref FLASH_FLAG_PGERR       FLASH Programming error flag& g9 N- n) g. Z' [
  83.   * @retval none*/
    ! D$ h+ e, Y5 m- M

  84. # M2 h) ~9 [2 F1 ~. I, G7 n) j
  85. __STATIC_INLINE void LL_FLASH_ClearFlag(FLASH_TypeDef *FLASHx,uint32_t STATE_FLAG)! ^5 h, D) M) x0 Q) H1 V% z4 q& U
  86. {+ K5 k1 U; E) G+ ~1 m
  87.   WRITE_REG(FLASHx->SR, STATE_FLAG);
    & O% z1 l1 A) n* t% H" ?9 v
  88. }
    0 t" N9 X: O( {/ C, ~
  89. ) h! b7 D% s- h
  90.   /*get bit flash bsy*/
    ( ^* a' T2 n2 ^# w9 G; z* ?
  91. __STATIC_INLINE uint32_t LL_FLASH_IsActiveFlag_BSY(FLASH_TypeDef *FLASHx)
    ) _  a( Y2 j: @: w/ u' _# {
  92. {5 O% i! m! N1 _
  93.   return (READ_BIT(FLASHx->SR, FLASH_SR_BSY) == (FLASH_SR_BSY));$ U6 ]1 f) C. q( u9 [  C
  94. }
    - h2 ~7 a# W  Z" c
  95. /*get end of operation bilt*/
    * u. Y5 y# T! ~. v
  96. __STATIC_INLINE uint32_t LL_FLASH_IsActiveFlag_EOP(FLASH_TypeDef *FLASHx)$ I$ \, r, b9 D) y
  97. {8 X* l; G* ?; q# T# S1 ]8 l$ k
  98.   return (READ_BIT(FLASHx->SR, FLASH_SR_EOP) == (FLASH_SR_EOP));  d  G' B" j" D3 |. @! }0 g5 g3 M
  99. }
    4 n0 V0 B0 r% c: u; S2 Z
  100. /*clear end of operation bilt*/
    ' N% u! ~- ^9 Z# l
  101. __STATIC_INLINE void LL_FLASH_ClearFlag_EOP(FLASH_TypeDef *FLASHx)8 p& z- A2 @1 D% l2 f; a/ q8 n
  102. {8 y) E# l9 X( V  m& |& O
  103.   SET_BIT(FLASHx->SR, FLASH_SR_EOP);//EOP bit Set clear
    $ ~* o; k4 }# D+ \* [
  104. }
    $ ]6 g  r8 _  V
  105.   /* @brief  Set flash erase type., ?% P8 h' I( K" X5 c0 E" g6 l
  106.   * @param  FLASH_TYPEERASE specifies the FLASH flags to clear.
    ; [: @$ M, e4 G" f
  107.   *          This parameter can be any combination of the following values:6 P6 F# d! j  e
  108.   *            @arg @ref FLASH_TYPEERASE_PAGES         PAGES Erase6 \; @2 w! V" s
  109.   *            @arg @ref FLASH_TYPEERASE_MASSERASE      FLASH Write protected error flag
    # _  i% B' T7 e: B+ }! W
  110.   * @retval none*/: S  R3 P3 w# u
  111. __STATIC_INLINE void LL_FLASH_DisenableErase(FLASH_TypeDef *FLASHx,uint32_t FLASH_TYPEERASE)
    " u1 i; p* `8 i3 X
  112. {
    5 F/ I  F8 l3 j7 F! j1 }" e' A
  113.   CLEAR_BIT(FLASHx->CR, FLASH_TYPEERASE);* e4 K  ~! b' E4 {$ x8 b* ^
  114. }& i! w3 t) e5 f- Q" \

  115.   r$ c$ H: G7 f9 Y& r3 D1 F
  116. /*EnableProgram*/
    ' E. \! E" D: ?5 I
  117. __STATIC_INLINE void LL_FLASH_EnableProgram(FLASH_TypeDef *FLASHx)& I1 W5 @) L- Q& Z6 C
  118. {: }, H# ]# L8 \- E- T9 f- V
  119.   SET_BIT(FLASHx->CR,FLASH_CR_PG);1 O3 W4 x3 _  o7 |  i  h# u  F& V% L
  120. }
      i2 p3 J$ I7 m2 {
  121. /*DisenableProgram*/! N9 m+ `1 I) U  X, B" `
  122. __STATIC_INLINE void LL_FLASH_DisenableProgram(FLASH_TypeDef *FLASHx)
    * l4 u  U: }- ~" [% @( h5 D$ l
  123. {1 o. U9 q) R* a* ~
  124.   CLEAR_BIT(FLASHx->CR,FLASH_CR_PG);
    9 B5 z3 M/ X# S( t: C& n
  125. }
    3 C7 q1 t8 q; s$ t
  126. /*read flash's states of lock or unlock*/1 I' Q4 }1 r8 l/ Y0 O1 ]
  127. __STATIC_INLINE FlashStates LL_FLASH_LockState(FLASH_TypeDef *FLASHx)
    ) `$ h0 T+ @' ~  Y% P! f
  128. {9 `, P$ [5 z. ]& J0 @
  129.         return (FlashStates)(READ_BIT(FLASHx->CR,FLASH_CR_LOCK));
    4 a- u6 y, n$ X1 P6 B
  130. }
    4 W) e$ m5 j# H* R* r: J
  131. /*set key for flash*// f. N0 J" Q. Z% b3 V+ {
  132. __STATIC_INLINE void LL_FLASh_SetKey(FLASH_TypeDef *FLASHx,uint32_t key)/ H* L4 F$ F6 h, f7 j+ p
  133. {! s8 f1 r2 G# j5 M$ h
  134.         WRITE_REG(FLASH->KEYR,key);
    7 Z. E: X6 Z4 b! E( y  C
  135. }
    8 r7 a; ?% }! b0 y& z& M  N

  136. + i3 d, v/ f- P! Z

  137. + X& M, X( K: R; f
  138. LL_StatusTypeDef LL_Flash_Unlock(void);; ]  d8 d1 n; R& o
  139. LL_StatusTypeDef LL_Flash_PageErase(uint32_t page_addr,uint16_t NbPages);
    - h# U- t% u9 K7 O1 t8 G
  140. LL_StatusTypeDef LL_FLASH_Program(ProgaramDataType ProgramType,uint32_t flash_addr,uint64_t data);
    % P% [, C# Q3 t
  141. #endif
复制代码

& s# T$ @5 \3 Z& I; z" AC文件代码- a! d( a$ o' P; t9 w7 N
  1. #include "stm32f0xx_ll_flash_ex.h"3 G- f- e2 O5 _. K

  2. % g2 n& o2 k2 U4 O1 B2 D" t' H
  3. 0 h. D" e; K. Z( N
  4. void static LL_FLASH_Program_TwoBtye(uint32_t flash_addr,uint16_t data)  m' |# o* y- t4 W" p  i
  5. {
    ' B5 c4 g. E$ p
  6.         LL_FLASH_EnableProgram(FLASH);% i  |" [: U* V
  7.         *(__IO uint16_t*)(flash_addr) = data;5 W4 \, Z. G, z! |1 c4 j  L+ g
  8. }1 m" `9 u( d) j9 u/ d# u

  9. - Y9 g" S- q, o& t2 R
  10. LL_StatusTypeDef LL_Flash_Unlock(void)
    7 n3 Q5 K; T, G# G# J% i! E
  11. {% _  l, H& Y. _; N3 ~
  12.         while (LL_FLASH_IsActiveFlag_BSY(FLASH))  
    ( i+ T  T& E: N% h. p
  13.         {
    2 K1 y1 m- I5 l( U% s* o
  14.         }
    - g. N7 X$ @4 F% ^5 s
  15.         if (LL_FLASH_LockState(FLASH)) ! a# g9 x* S8 u' L
  16.         {
    ; |1 P8 X5 X# A# S5 h
  17.                 LL_FLASh_SetKey(FLASH,FLASH_KEY1);% b* E! V1 X; r( U
  18.                 LL_FLASh_SetKey(FLASH,FLASH_KEY2);
    ' z' [/ G. l& Q2 z
  19.         }
    # J6 d$ N3 e  i  w8 r5 W6 N
  20.         return LL_OK;
    3 z! a6 j8 s( h5 ?& R/ e
  21. }, B' J. U$ ]4 x1 D- x) `

  22. , p: o  H6 R8 x8 Z- ^7 ?/ \
  23. LL_StatusTypeDef LL_Flash_PageErase(uint32_t page_addr,uint16_t Nb)8 G+ c+ N1 d1 b4 {. a1 W! n
  24. {
      K! \3 T7 ?: w! Y6 G
  25.         uint32_t End_addr =  10* FLASH_PAGE_SIZE +page_addr;
    , g! v% ], q) l/ w2 L$ I+ r3 E
  26.         uint32_t Start_addr = page_addr;6 c2 @( g/ ]8 n: w0 P" O
  27.         for(;Start_addr < End_addr;(Start_addr += FLASH_PAGE_SIZE))5 c: d* k; V% p0 o
  28.     {9 H: u/ s4 G" c6 u2 t
  29.         LL_FLASH_SetTypeErase(FLASH,FLASH_TYPEERASE_PAGES);
    7 x* |# V- R* B6 K: [
  30.                 LL_FLASH_SetEraseADDR(FLASH,Start_addr);' u8 F) s2 J$ M2 ~  b
  31.                 LL_FLASH_StartErase(FLASH);
    ( S8 j% C8 P4 j; f
  32.                 while (LL_FLASH_IsActiveFlag_BSY(FLASH))
    ) t2 O; S8 C# I0 \2 I: |8 J+ t
  33.                 {
    + t. w9 K' _+ K* n- n. `( {5 F
  34.                 }
    ( \! ]' j) ^' K9 Z
  35.                 if (LL_FLASH_IsActiveFlag_EOP(FLASH)) ; R7 ~3 E$ d" `) K7 [5 V
  36.                 {
    . q5 y0 y& y8 c$ ]
  37.                         LL_FLASH_ClearFlag_EOP(FLASH);;
    ) W0 g; `/ o, U# z
  38.                 }
    3 t$ \3 q4 W- h3 a0 ~
  39.                 else
      n9 S* T* ^* T
  40.                 { % ^% i1 Y, D/ V$ j# g* y" w" ?
  41.                         return LL_ERROR;
    7 [1 m+ ?; K  B" J
  42.                 }
    3 z1 ~; b7 M) U* w4 [
  43.                 LL_FLASH_DisenableErase(FLASH,FLASH_TYPEERASE_PAGES);2 c* c, c: U+ N+ E! ]
  44.     }
    8 H2 k) B3 g* {/ }0 L' r  ?" x8 L+ A
  45.         return LL_OK;: @/ w2 a& B. N* ~8 {
  46. }
    , B! S' }& W9 n. s5 _  o3 d
  47. ( ]% g- G) z7 f1 G/ j: [9 U
  48. LL_StatusTypeDef LL_FLASH_Program(ProgaramDataType ProgramType,uint32_t flash_addr,uint64_t data)
    , V4 h0 ?2 Z7 p1 Y) N
  49. {
    % Y0 y- J7 [' y" _5 O: ^
  50.         
    9 q- R: M9 d. E% U! D5 ?9 B+ D5 u
  51.         uint8_t index = 0U;5 B  `; B2 m! x) v- N
  52.         uint8_t nbiterations = 0U;+ x1 C) a$ `& U6 P% ~) L) }: K7 l- S
  53.         : L3 r) _" q2 k0 G6 X' s6 ?/ S
  54.         if(ProgramType == ProgaraType_DATA16)
    * Y* P9 B: b) I' I5 V
  55.                 nbiterations = 1U;- w4 H8 f. a/ a2 w) L; m
  56.         else if(ProgramType == ProgaraType_DATA32)3 g1 e+ T! m5 L# ]& q( F7 j  o
  57.                 nbiterations = 2U;
    ) _! O/ ~0 B# ?. u+ o! ]
  58.         else1 z7 K& I9 U3 k& ]2 c  Y' |
  59.                 nbiterations = 4U;% a. R2 p9 o# S
  60.         for(index = 0U; index < nbiterations; index++)
    7 F0 C4 b) F0 @- ~# v" \
  61.         {
    ) C7 ?! `& n+ t& Q
  62.                  LL_FLASH_Program_TwoBtye((flash_addr + (2U*index)), (uint16_t)(data >> (16U*index)));
    2 w+ U# F$ j3 g# ~, o* i
  63.         }+ G( H' f  Q( r* P2 \
  64.         6 t" w) ]  j! J. x2 I
  65.         while (LL_FLASH_IsActiveFlag_BSY(FLASH)) # Q* a+ J; s$ P0 U
  66.         {
    7 Z( y9 @) O3 }7 R9 C* G
  67.         }9 P/ r) m# G7 R8 A1 e+ Z; _
  68.         if (LL_FLASH_IsActiveFlag_EOP(FLASH))        
    9 t* d" |: m0 D+ N9 C
  69.         {
    " W7 Q6 ]2 L( d/ V7 c3 y& h
  70.                 LL_FLASH_ClearFlag_EOP(FLASH);
    / r% ~0 l: s8 e. u  S; E
  71.         }) ~+ q% m6 R/ |9 I5 P0 H
  72.         else
    3 J. e" L( o9 t
  73.         {% H$ r; C- |, d) P) R, l1 H$ X0 {
  74.                 return LL_ERROR;: w1 d# v) U! n8 \
  75.         }
    / U! o" f( r! B) ]. i
  76.         LL_FLASH_DisenableProgram(FLASH);4 _+ Z. q* M" y9 j
  77.         return LL_OK;
    * T2 ], J" h, A( D" A- f
  78. }
    9 n6 u# N2 f1 a/ b% w
复制代码

8 O2 w. f/ z5 p; Z( m# M" q: F# F# R( z& ?- ~) q1 B
收藏 评论0 发布时间:2021-11-13 23:00

举报

0个回答

所属标签

关于
我们是谁
投资者关系
意法半导体可持续发展举措
创新与技术
意法半导体官网
联系我们
联系ST分支机构
寻找销售人员和分销渠道
社区
媒体中心
活动与培训
隐私策略
隐私策略
Cookies管理
行使您的权利
官方最新发布
STM32Cube扩展软件包
意法半导体边缘AI套件
ST - 理想汽车豪华SUV案例
ST意法半导体智能家居案例
STM32 ARM Cortex 32位微控制器
关注我们
st-img 微信公众号
st-img 手机版