100-12-mtd-mtk-snand-add-NMBM-support-for-SPL.patch 3.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173
  1. From 9e8ac4fc7125795ac5e8834aaf454fd45b99c580 Mon Sep 17 00:00:00 2001
  2. From: Weijie Gao <[email protected]>
  3. Date: Mon, 25 Jul 2022 10:53:03 +0800
  4. Subject: [PATCH 46/71] mtd: mtk-snand: add NMBM support for SPL
  5. Add NMBM support for mtk-snand SPL loader
  6. Signed-off-by: Weijie Gao <[email protected]>
  7. ---
  8. drivers/mtd/mtk-snand/mtk-snand-spl.c | 127 ++++++++++++++++++++++++++
  9. 1 file changed, 127 insertions(+)
  10. --- a/drivers/mtd/mtk-snand/mtk-snand-spl.c
  11. +++ b/drivers/mtd/mtk-snand/mtk-snand-spl.c
  12. @@ -13,12 +13,134 @@
  13. #include <mtd.h>
  14. #include <watchdog.h>
  15. +#include <nmbm/nmbm.h>
  16. +
  17. #include "mtk-snand.h"
  18. static struct mtk_snand *snf;
  19. static struct mtk_snand_chip_info cinfo;
  20. static u32 oobavail;
  21. +#ifdef CONFIG_ENABLE_NAND_NMBM
  22. +static struct nmbm_instance *ni;
  23. +
  24. +static int nmbm_lower_read_page(void *arg, uint64_t addr, void *buf, void *oob,
  25. + enum nmbm_oob_mode mode)
  26. +{
  27. + int ret;
  28. + bool raw = mode == NMBM_MODE_RAW ? true : false;
  29. +
  30. + if (mode == NMBM_MODE_AUTO_OOB) {
  31. + ret = mtk_snand_read_page_auto_oob(snf, addr, buf, oob,
  32. + oobavail, NULL, false);
  33. + } else {
  34. + ret = mtk_snand_read_page(snf, addr, buf, oob, raw);
  35. + }
  36. +
  37. + if (ret == -EBADMSG)
  38. + return 1;
  39. + else if (ret >= 0)
  40. + return 0;
  41. +
  42. + return ret;
  43. +}
  44. +
  45. +static int nmbm_lower_write_page(void *arg, uint64_t addr, const void *buf,
  46. + const void *oob, enum nmbm_oob_mode mode)
  47. +{
  48. + bool raw = mode == NMBM_MODE_RAW ? true : false;
  49. +
  50. + if (mode == NMBM_MODE_AUTO_OOB) {
  51. + return mtk_snand_write_page_auto_oob(snf, addr, buf, oob,
  52. + oobavail, NULL, false);
  53. + }
  54. +
  55. + return mtk_snand_write_page(snf, addr, buf, oob, raw);
  56. +}
  57. +
  58. +static int nmbm_lower_erase_block(void *arg, uint64_t addr)
  59. +{
  60. + return mtk_snand_erase_block(snf, addr);
  61. +}
  62. +
  63. +static int nmbm_lower_is_bad_block(void *arg, uint64_t addr)
  64. +{
  65. + return mtk_snand_block_isbad(snf, addr);
  66. +}
  67. +
  68. +static int nmbm_lower_mark_bad_block(void *arg, uint64_t addr)
  69. +{
  70. + return mtk_snand_block_markbad(snf, addr);
  71. +}
  72. +
  73. +static void nmbm_lower_log(void *arg, enum nmbm_log_category level,
  74. + const char *fmt, va_list ap)
  75. +{
  76. + vprintf(fmt, ap);
  77. +}
  78. +
  79. +static int nmbm_init(void)
  80. +{
  81. + struct nmbm_lower_device nld;
  82. + size_t ni_size;
  83. + int ret;
  84. +
  85. + memset(&nld, 0, sizeof(nld));
  86. +
  87. + nld.flags = NMBM_F_CREATE;
  88. + nld.max_ratio = CONFIG_NMBM_MAX_RATIO;
  89. + nld.max_reserved_blocks = CONFIG_NMBM_MAX_BLOCKS;
  90. +
  91. + nld.size = cinfo.chipsize;
  92. + nld.erasesize = cinfo.blocksize;
  93. + nld.writesize = cinfo.pagesize;
  94. + nld.oobsize = cinfo.sparesize;
  95. + nld.oobavail = oobavail;
  96. +
  97. + nld.read_page = nmbm_lower_read_page;
  98. + nld.write_page = nmbm_lower_write_page;
  99. + nld.erase_block = nmbm_lower_erase_block;
  100. + nld.is_bad_block = nmbm_lower_is_bad_block;
  101. + nld.mark_bad_block = nmbm_lower_mark_bad_block;
  102. +
  103. + nld.logprint = nmbm_lower_log;
  104. +
  105. + ni_size = nmbm_calc_structure_size(&nld);
  106. + ni = malloc(ni_size);
  107. + if (!ni) {
  108. + printf("Failed to allocate memory (0x%u) for NMBM instance\n",
  109. + ni_size);
  110. + return -ENOMEM;
  111. + }
  112. +
  113. + memset(ni, 0, ni_size);
  114. +
  115. + printf("Initializing NMBM ...\n");
  116. +
  117. + ret = nmbm_attach(&nld, ni);
  118. + if (ret) {
  119. + ni = NULL;
  120. + return ret;
  121. + }
  122. +
  123. + return 0;
  124. +}
  125. +
  126. +int nand_spl_load_image(uint32_t offs, unsigned int size, void *dst)
  127. +{
  128. + size_t retlen;
  129. +
  130. + if (!ni)
  131. + return -ENODEV;
  132. +
  133. + nmbm_read_range(ni, offs, size, dst, NMBM_MODE_PLACE_OOB, &retlen);
  134. + if (retlen != size)
  135. + return -EIO;
  136. +
  137. + return 0;
  138. +}
  139. +
  140. +#else
  141. static u8 *page_cache;
  142. int nand_spl_load_image(uint32_t offs, unsigned int size, void *dst)
  143. @@ -60,6 +182,7 @@ int nand_spl_load_image(uint32_t offs, u
  144. return ret;
  145. }
  146. +#endif
  147. void nand_init(void)
  148. {
  149. @@ -105,11 +228,15 @@ void nand_init(void)
  150. printf("SPI-NAND: %s (%uMB)\n", cinfo.model,
  151. (u32)(cinfo.chipsize >> 20));
  152. +#ifdef CONFIG_ENABLE_NAND_NMBM
  153. + nmbm_init();
  154. +#else
  155. page_cache = malloc(cinfo.pagesize + cinfo.sparesize);
  156. if (!page_cache) {
  157. mtk_snand_cleanup(snf);
  158. printf("mtk-snand-spl: failed to allocate page cache\n");
  159. }
  160. +#endif
  161. }
  162. void nand_deselect(void)