fal_flash_stm32f1_port.c 4.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174
  1. /*
  2. * Copyright (c) 2020, Armink, <armink.ztl@gmail.com>
  3. *
  4. * SPDX-License-Identifier: Apache-2.0
  5. */
  6. #include <string.h>
  7. #include <fal.h>
  8. #include "iwdg.h"
  9. #include <stm32f1xx.h>
  10. #if defined(STM32F103xE)
  11. #define PAGE_SIZE 2048
  12. #else
  13. #define PAGE_SIZE 1024
  14. #endif
  15. /*
  16. STM32F1会因容量不同而不同
  17. 小容量和中容量产品主存储块128KB以下, 每页1KB。
  18. 大容量和互联型产品主存储块256KB以上, 每页2KB。
  19. GD32 会因容量不同而不同
  20. 1. Low-density Products Flash容量从 16KB到 32KB的产品
  21. 2. Medium-density Products Flash容量从 64KB到 128KB的产品
  22. 全是1K
  23. 3. High-density Products Flash容量从256KB到 512KB的产品
  24. 全是2K
  25. 4. XL-density Products Flash容量从768KB到3072KB的产品
  26. <512K 是2K
  27. >512K 是4K
  28. 雅特力
  29. 全是2K
  30. STM32F4
  31. STM32F4的flash页尺寸不一样,低地址16KB,高地址32KB或128KB.
  32. */
  33. static int init(void)
  34. {
  35. /* do nothing now */
  36. return 1;
  37. }
  38. static int ef_err_port_cnt = 0;
  39. int on_ic_read_cnt = 0;
  40. int on_ic_write_cnt = 0;
  41. void feed_dog(void)
  42. {
  43. HAL_IWDG_Refresh(&hiwdg);
  44. }
  45. static int read(long offset, uint8_t *buf, size_t size)
  46. {
  47. size_t i;
  48. uint32_t addr = stm32_onchip_flash.addr + offset;
  49. if( addr%4 != 0)
  50. ef_err_port_cnt++;
  51. for (i = 0; i < size; i++, addr++, buf++)
  52. {
  53. *buf = *(uint8_t *) addr;
  54. }
  55. on_ic_read_cnt++;
  56. return size;
  57. }
  58. static int write(long offset, const uint8_t *buf, size_t size)
  59. {
  60. size_t i;
  61. uint32_t addr = stm32_onchip_flash.addr + offset;
  62. __ALIGN_BEGIN uint32_t write_data __ALIGN_END;
  63. __ALIGN_BEGIN uint32_t read_data __ALIGN_END;
  64. if(addr%4 != 0)
  65. ef_err_port_cnt++;
  66. /*
  67. if((int)buf%4 != 0)
  68. ef_err_port_cnt++;
  69. */
  70. HAL_FLASH_Unlock();
  71. for (i = 0; i < size; i += 4, buf+=4, addr += 4) {
  72. memcpy(&write_data, buf, 4); //用以保证HAL_FLASH_Program的第三个参数是内存首地址对齐
  73. HAL_FLASH_Program(FLASH_TYPEPROGRAM_WORD, addr, write_data);
  74. read_data = *(uint32_t *)addr;
  75. /* You can add your code under here. */
  76. if (read_data != write_data) {
  77. HAL_FLASH_Lock();
  78. return -1;
  79. }
  80. else{
  81. //FLash操作可能非常耗时,如果有看门狗需要喂狗,以下代码由用户实现
  82. feed_dog();
  83. }
  84. }
  85. HAL_FLASH_Lock();
  86. on_ic_write_cnt++;
  87. return size;
  88. }
  89. static int erase(long offset, size_t size)
  90. {
  91. uint32_t addr = stm32_onchip_flash.addr + offset;
  92. HAL_StatusTypeDef flash_status;
  93. size_t erase_pages, i;
  94. uint32_t PAGEError = 0;
  95. erase_pages = size / PAGE_SIZE;
  96. if (size % PAGE_SIZE != 0) {
  97. erase_pages++;
  98. }
  99. FLASH_EraseInitTypeDef EraseInitStruct;
  100. EraseInitStruct.TypeErase = FLASH_TYPEERASE_PAGES;
  101. EraseInitStruct.NbPages = 1; //一次擦出一个扇区, 以执行一次喂狗,防止超时
  102. HAL_FLASH_Unlock();
  103. for (i = 0; i < erase_pages; i++) {
  104. EraseInitStruct.PageAddress = addr + (FLASH_PAGE_SIZE * i);
  105. flash_status = HAL_FLASHEx_Erase(&EraseInitStruct, &PAGEError);
  106. if (flash_status != HAL_OK) {
  107. HAL_FLASH_Lock();
  108. return -1;
  109. }
  110. else{
  111. //FLash操作可能非常耗时,如果有看门狗需要喂狗,以下代码由用户实现
  112. feed_dog();
  113. }
  114. }
  115. HAL_FLASH_Lock();
  116. return size;
  117. }
  118. /*
  119. "stm32_onchip" : Flash 设备的名字。
  120. 0x08000000: 对 Flash 操作的起始地址。
  121. 1024*1024:Flash 的总大小(1MB)。
  122. 128*1024:Flash 块/扇区大小(因为 STM32F2 各块大小不均匀,所以擦除粒度为最大块的大小:128K)。
  123. {init, read, write, erase} :Flash 的操作函数。 如果没有 init 初始化过程,第一个操作函数位置可以置空。
  124. 8 : 设置写粒度,单位 bit, 0 表示未生效(默认值为 0 ),该成员是 fal 版本大于 0.4.0 的新增成员。各个 flash 写入粒度不尽相同,可通过该成员进行设置,以下列举几种常见 Flash 写粒度:
  125. nor flash: 1 bit
  126. stm32f2/f4: 8 bit
  127. stm32f1: 32 bit
  128. stm32l4: 64 bit
  129. */
  130. //1.定义 flash 设备
  131. const struct fal_flash_dev stm32_onchip_flash =
  132. {
  133. .name = "stm32_onchip",
  134. .addr = 0x08000000,
  135. .len = 256*1024,
  136. .blk_size = 2*1024,
  137. .ops = {init, read, write, erase},
  138. .write_gran = 32
  139. };