drv_nor_flash.c 3.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118
  1. /*
  2. * Copyright (c) 2006-2022, Synwit Technology Co.,Ltd.
  3. *
  4. * SPDX-License-Identifier: Apache-2.0
  5. *
  6. * Change Logs:
  7. * Date Author Notes
  8. * 2018-05-31 ZYH first version
  9. * 2018-12-10 Zohar_Lee format file
  10. * 2020-07-10 lik rewrite
  11. */
  12. #include "drv_nor_flash.h"
  13. #ifdef BSP_USING_NOR_FLASH
  14. #define DRV_DEBUG
  15. #define LOG_TAG "drv.norflash"
  16. #include <drv_log.h>
  17. #define BLOCK_SIZE (64 * 1024)
  18. #define FLASH_SIZE (BSP_NOR_FLASH_SIZE)
  19. #define BLOCK_COUNTER (FLASH_SIZE / BLOCK_SIZE)
  20. static struct rt_mutex flash_lock;
  21. /* RT-Thread MTD device interface */
  22. static long swm_norflash_read_id(struct rt_mtd_nor_device *device)
  23. {
  24. return 0xdeadbeef;
  25. }
  26. static rt_ssize_t swm_norflash_read(struct rt_mtd_nor_device *device,
  27. rt_off_t position,
  28. rt_uint8_t *data,
  29. rt_uint32_t size)
  30. {
  31. rt_mutex_take(&flash_lock, RT_WAITING_FOREVER);
  32. memcpy(data, ((const void *)(NORFLM_BASE + position)), size);
  33. rt_mutex_release(&flash_lock);
  34. return size;
  35. }
  36. static rt_ssize_t swm_norflash_write(struct rt_mtd_nor_device *device,
  37. rt_off_t position,
  38. const rt_uint8_t *data,
  39. rt_uint32_t size)
  40. {
  41. rt_size_t i;
  42. const rt_uint16_t *hwdata = (const rt_uint16_t *)data;
  43. rt_mutex_take(&flash_lock, RT_WAITING_FOREVER);
  44. for (i = 0; i < size / 2; i++)
  45. {
  46. NORFL_Write(position, hwdata[i]);
  47. position += 2;
  48. }
  49. rt_mutex_release(&flash_lock);
  50. return size;
  51. }
  52. static rt_err_t swm_norflash_erase_block(struct rt_mtd_nor_device *device,
  53. rt_off_t offset,
  54. rt_uint32_t length)
  55. {
  56. rt_mutex_take(&flash_lock, RT_WAITING_FOREVER);
  57. NORFL_SectorErase(offset);
  58. rt_mutex_release(&flash_lock);
  59. return RT_EOK;
  60. }
  61. const static struct rt_mtd_nor_driver_ops swm_mtd_ops =
  62. {
  63. swm_norflash_read_id,
  64. swm_norflash_read,
  65. swm_norflash_write,
  66. swm_norflash_erase_block};
  67. static struct rt_mtd_nor_device mtd_device;
  68. int swm_norflash_init(void)
  69. {
  70. NORFL_InitStructure NORFL_InitStruct;
  71. PORT->PORTP_SEL0 = 0xAAAAAAAA; //PP0-23 => ADDR0-23
  72. PORT->PORTP_SEL1 = 0xAAAA;
  73. PORT->PORTM_SEL0 = 0xAAAAAAAA; //PM0-15 => DATA15-0
  74. PORT->PORTM_INEN = 0xFFFF;
  75. PORT->PORTM_SEL1 = 0xAAA; //PM16 => OEN、PM17 => WEN、PM18 => NORFL_CSN、PM19 => SDRAM_CSN、PM20 => SRAM_CSN、PM21 => SDRAM_CKE
  76. NORFL_InitStruct.DataWidth = 16;
  77. NORFL_InitStruct.WELowPulseTime = 5;
  78. NORFL_InitStruct.OEPreValidTime = 12;
  79. NORFL_InitStruct.OperFinishIEn = 0;
  80. NORFL_InitStruct.OperTimeoutIEn = 0;
  81. NORFL_Init(&NORFL_InitStruct);
  82. /* set page size and block size */
  83. mtd_device.block_size = BLOCK_SIZE; /* 64kByte */
  84. mtd_device.ops = &swm_mtd_ops;
  85. /* initialize mutex */
  86. if (rt_mutex_init(&flash_lock, "nor", RT_IPC_FLAG_PRIO) != RT_EOK)
  87. {
  88. rt_kprintf("init sd lock mutex failed\n");
  89. return -RT_ERROR;
  90. }
  91. mtd_device.block_start = 0;
  92. mtd_device.block_end = BLOCK_COUNTER;
  93. /* register MTD device */
  94. rt_mtd_nor_register_device("nor", &mtd_device);
  95. return RT_EOK;
  96. }
  97. INIT_DEVICE_EXPORT(swm_norflash_init);
  98. #endif /* BSP_USING_NOR_FLASH */