flash.c 3.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137
  1. /*
  2. * Copyright (c) 2006-2021, RT-Thread Development Team
  3. *
  4. * SPDX-License-Identifier: Apache-2.0
  5. *
  6. * Change Logs:
  7. * Date Author Notes
  8. * 2017-12-04 Haley the first version
  9. */
  10. #include <rtthread.h>
  11. #include <rtdevice.h>
  12. #include "am_mcu_apollo.h"
  13. #include "flash.h"
  14. /* RT-Thread device interface */
  15. static rt_err_t rt_flash_init(rt_device_t dev)
  16. {
  17. return RT_EOK;
  18. }
  19. static rt_err_t rt_flash_open(rt_device_t dev, rt_uint16_t oflag)
  20. {
  21. return RT_EOK;
  22. }
  23. static rt_err_t rt_flash_close(rt_device_t dev)
  24. {
  25. return RT_EOK;
  26. }
  27. static rt_err_t rt_flash_control(rt_device_t dev, int cmd, void *args)
  28. {
  29. uint32_t ui32Critical, i;
  30. uint32_t ui32CurrentPage, ui32CurrentBlock;
  31. if (cmd == RT_DEVICE_CTRL_BLK_GETGEOME)
  32. {
  33. struct rt_device_blk_geometry *geometry;
  34. geometry = (struct rt_device_blk_geometry *)args;
  35. if (geometry == RT_NULL)
  36. return -RT_ERROR;
  37. geometry->bytes_per_sector = 8192;
  38. geometry->sector_count = 8192;
  39. geometry->block_size = 8192;
  40. }
  41. else if(cmd == RT_DEVICE_CTRL_BLK_ERASE)
  42. {
  43. struct rom_control_erase *erase;
  44. erase = (struct rom_control_erase *)args;
  45. // Start a critical section.
  46. ui32Critical = am_hal_interrupt_master_disable();
  47. if (erase->type == 0x01)
  48. {
  49. for(i = 0; i < erase->pagenums; i++)
  50. {
  51. // Figure out what page and block we're working on.
  52. ui32CurrentPage = AM_HAL_FLASH_ADDR2PAGE(erase->addrstart);
  53. ui32CurrentBlock = AM_HAL_FLASH_ADDR2INST(erase->addrstart);
  54. am_hal_flash_page_erase(AM_HAL_FLASH_PROGRAM_KEY, ui32CurrentBlock, ui32CurrentPage); //单扇区擦除命令
  55. erase->addrstart += 8192;
  56. }
  57. }
  58. // Exit the critical section.
  59. am_hal_interrupt_master_set(ui32Critical);
  60. }
  61. return RT_EOK;
  62. }
  63. static rt_size_t rt_flash_read(rt_device_t dev,
  64. rt_off_t pos,
  65. void* buffer,
  66. rt_size_t size)
  67. {
  68. rt_memcpy((uint8_t *)buffer, (uint8_t *)pos, size);
  69. return size;
  70. }
  71. static rt_size_t rt_flash_write(rt_device_t dev,
  72. rt_off_t pos,
  73. const void* buffer,
  74. rt_size_t size)
  75. {
  76. uint32_t ui32Critical;
  77. uint32_t ui32WordsInBuffer;
  78. ui32WordsInBuffer = (size + 3)/ 4;
  79. // Start a critical section.
  80. ui32Critical = am_hal_interrupt_master_disable();
  81. // Program the flash page with the data we just received.
  82. am_hal_flash_program_main(AM_HAL_FLASH_PROGRAM_KEY, (uint32_t *)buffer, (uint32_t *)pos, ui32WordsInBuffer);
  83. // Exit the critical section.
  84. am_hal_interrupt_master_set(ui32Critical);
  85. return size;
  86. }
  87. int rt_hw_rom_init(void)
  88. {
  89. static struct rt_device device;
  90. /* register device */
  91. device.type = RT_Device_Class_Block;
  92. device.init = rt_flash_init;
  93. device.open = rt_flash_open;
  94. device.close = rt_flash_close;
  95. device.read = rt_flash_read;
  96. device.write = rt_flash_write;
  97. device.control = rt_flash_control;
  98. /* no private */
  99. device.user_data = RT_NULL;
  100. /* register the device */
  101. rt_device_register(&device, "rom", RT_DEVICE_FLAG_RDWR);
  102. //rt_kprintf("register device rom!\r\n");
  103. return 0;
  104. }
  105. #ifdef RT_USING_COMPONENTS_INIT
  106. INIT_DEVICE_EXPORT(rt_hw_rom_init);
  107. #endif
  108. /*@}*/