drv_qspi_flash.c 3.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153
  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. * 2020-04-29 supperthomas first version
  9. *
  10. */
  11. #include <stdint.h>
  12. #include "board.h"
  13. #include "nrfx_qspi.h"
  14. #if defined(RT_USING_FAL)
  15. #include <fal.h>
  16. //log
  17. #include <rtdbg.h>
  18. #define LOG_TAG "drv.qspiflash"
  19. #define WAIT_FOR_PERIPH() do { \
  20. while (!m_finished) {} \
  21. m_finished = false; \
  22. } while (0)
  23. static volatile bool m_finished = false;
  24. static void qspi_handler(nrfx_qspi_evt_t event, void *p_context)
  25. {
  26. m_finished = true;
  27. }
  28. static void configure_memory()
  29. {
  30. #define QSPI_STD_CMD_WRSR 0x01
  31. #define QSPI_STD_CMD_RSTEN 0x66
  32. #define QSPI_STD_CMD_RST 0x99
  33. uint8_t temporary = 0x40;
  34. uint32_t err_code;
  35. nrf_qspi_cinstr_conf_t cinstr_cfg =
  36. {
  37. .opcode = QSPI_STD_CMD_RSTEN,
  38. .length = NRF_QSPI_CINSTR_LEN_1B,
  39. .io2_level = true,
  40. .io3_level = true,
  41. .wipwait = true,
  42. .wren = true
  43. };
  44. // Send reset enable
  45. err_code = nrfx_qspi_cinstr_xfer(&cinstr_cfg, NULL, NULL);
  46. if (NRFX_SUCCESS != err_code)
  47. {
  48. LOG_E("\r\n ERROR: QSPI_STD_CMD_RSTEN:0x%x\n", err_code);
  49. return ;
  50. }
  51. // Send reset command
  52. cinstr_cfg.opcode = QSPI_STD_CMD_RST;
  53. err_code = nrfx_qspi_cinstr_xfer(&cinstr_cfg, NULL, NULL);
  54. if (NRFX_SUCCESS != err_code)
  55. {
  56. LOG_E("\r\n ERROR: QSPI_STD_CMD_RST:0x%x\n", err_code);
  57. return ;
  58. }
  59. // Switch to qspi mode
  60. cinstr_cfg.opcode = QSPI_STD_CMD_WRSR;
  61. cinstr_cfg.length = NRF_QSPI_CINSTR_LEN_2B;
  62. err_code = nrfx_qspi_cinstr_xfer(&cinstr_cfg, &temporary, NULL);
  63. if (NRFX_SUCCESS != err_code)
  64. {
  65. LOG_E("\r\n ERROR: QSPI_STD_CMD_WRSR:0x%x\n", err_code);
  66. return;
  67. }
  68. }
  69. static int init(void)
  70. {
  71. uint32_t err_code;
  72. nrfx_qspi_config_t config = NRFX_QSPI_DEFAULT_CONFIG(BSP_QSPI_SCK_PIN, BSP_QSPI_CSN_PIN,
  73. BSP_QSPI_IO0_PIN, BSP_QSPI_IO1_PIN, BSP_QSPI_IO2_PIN, BSP_QSPI_IO3_PIN);
  74. err_code = nrfx_qspi_init(&config, qspi_handler, NULL);
  75. if (NRFX_SUCCESS != err_code)
  76. {
  77. LOG_E("\r\n ERROR: QSPI_init:0x%x\n", err_code);
  78. return -1;
  79. }
  80. configure_memory();
  81. return 0;
  82. }
  83. static int read(long offset, uint8_t *buf, size_t size)
  84. {
  85. uint32_t err_code;
  86. m_finished = false;
  87. err_code = nrfx_qspi_read(buf, size, offset);
  88. WAIT_FOR_PERIPH();
  89. if (NRFX_SUCCESS == err_code)
  90. {
  91. return size;
  92. }
  93. else
  94. {
  95. LOG_E("\r\n ERROR: read:0x%x\n", err_code);
  96. return -1;
  97. }
  98. }
  99. static int write(long offset, const uint8_t *buf, size_t size)
  100. {
  101. uint32_t err_code;
  102. m_finished = false;
  103. err_code = nrfx_qspi_write(buf, size, offset);
  104. WAIT_FOR_PERIPH();
  105. if (NRFX_SUCCESS == err_code)
  106. {
  107. return size;
  108. }
  109. else
  110. {
  111. LOG_E("\r\n ERROR: write:0x%x\n", err_code);
  112. return -1;
  113. }
  114. }
  115. static int erase(long offset, size_t size)
  116. {
  117. uint32_t err_code;
  118. m_finished = false;
  119. err_code = nrfx_qspi_erase(NRF_QSPI_ERASE_LEN_64KB, offset);
  120. WAIT_FOR_PERIPH();
  121. if (NRFX_SUCCESS == err_code)
  122. {
  123. return size;
  124. }
  125. else
  126. {
  127. LOG_E("\r\n ERROR: erase:0x%x\n", err_code);
  128. return -1;
  129. }
  130. }
  131. struct fal_flash_dev nor_flash0 =
  132. {
  133. .name = NOR_FLASH_DEV_NAME,
  134. .addr = 0,
  135. .len = QSPI_FLASH_SIZE_KB * 1024,
  136. .blk_size = 4096,
  137. .ops = {init, read, write, erase},
  138. .write_gran = 1
  139. };
  140. #endif