1
0

mnt.c 6.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268
  1. /**************************************************************************//**
  2. *
  3. * @copyright (C) 2019 Nuvoton Technology Corp. All rights reserved.
  4. *
  5. * SPDX-License-Identifier: Apache-2.0
  6. *
  7. * Change Logs:
  8. * Date Author Notes
  9. * 2020-12-12 Wayne First version
  10. *
  11. ******************************************************************************/
  12. #include "rtconfig.h"
  13. #include <rtthread.h>
  14. #define LOG_TAG "mnt"
  15. #define DBG_ENABLE
  16. #define DBG_SECTION_NAME "mnt"
  17. #define DBG_LEVEL DBG_ERROR
  18. #define DBG_COLOR
  19. #include <rtdbg.h>
  20. #include <dfs_fs.h>
  21. #include <dfs_file.h>
  22. #include <unistd.h>
  23. #include <stdio.h>
  24. #include <sys/stat.h>
  25. #include <sys/statfs.h>
  26. #if defined(RT_USING_FAL)
  27. #include <fal.h>
  28. #endif
  29. #if defined(PKG_USING_RAMDISK)
  30. #define RAMDISK_NAME "ramdisk0"
  31. #define RAMDISK_UDC "ramdisk1"
  32. #define MOUNT_POINT_RAMDISK0 "/"
  33. #endif
  34. #if defined(BOARD_USING_STORAGE_SPIFLASH)
  35. #define PARTITION_NAME_FILESYSTEM "filesystem"
  36. #define MOUNT_POINT_SPIFLASH0 "/mnt/"PARTITION_NAME_FILESYSTEM
  37. #endif
  38. #ifdef RT_USING_DFS_MNTTABLE
  39. /*
  40. const char *device_name;
  41. const char *path;
  42. const char *filesystemtype;
  43. unsigned long rwflag;
  44. const void *data;
  45. */
  46. const struct dfs_mount_tbl mount_table[] =
  47. {
  48. #if defined(PKG_USING_RAMDISK)
  49. { RAMDISK_UDC, "/mnt/ram_usbd", "elm", 0, RT_NULL },
  50. #endif
  51. #if defined(PKG_USING_DFS_YAFFS)
  52. { "nand1", "/mnt/filesystem", "yaffs", 0, RT_NULL },
  53. #elif defined(RT_USING_DFS_UFFS)
  54. { "nand1", "/mnt/filesystem", "uffs", 0, RT_NULL },
  55. #endif
  56. {0},
  57. };
  58. #endif
  59. #if defined(PKG_USING_RAMDISK)
  60. extern rt_err_t ramdisk_init(const char *dev_name, rt_uint8_t *disk_addr, rt_size_t block_size, rt_size_t num_block);
  61. int ramdisk_device_init(void)
  62. {
  63. rt_err_t result = RT_EOK;
  64. /* Create a 8MB RAMDISK */
  65. result = ramdisk_init(RAMDISK_NAME, NULL, 512, 2 * 8192);
  66. RT_ASSERT(result == RT_EOK);
  67. /* Create a 4MB RAMDISK */
  68. result = ramdisk_init(RAMDISK_UDC, NULL, 512, 2 * 4096);
  69. RT_ASSERT(result == RT_EOK);
  70. return 0;
  71. }
  72. INIT_DEVICE_EXPORT(ramdisk_device_init);
  73. /* Recursive mkdir */
  74. static int mkdir_p(const char *dir, const mode_t mode)
  75. {
  76. int ret = -1;
  77. char *tmp = NULL;
  78. char *p = NULL;
  79. struct stat sb;
  80. rt_size_t len;
  81. if (!dir)
  82. goto exit_mkdir_p;
  83. /* Copy path */
  84. /* Get the string length */
  85. len = strlen(dir);
  86. tmp = rt_strdup(dir);
  87. /* Remove trailing slash */
  88. if (tmp[len - 1] == '/')
  89. {
  90. tmp[len - 1] = '\0';
  91. len--;
  92. }
  93. /* check if path exists and is a directory */
  94. if (stat(tmp, &sb) == 0)
  95. {
  96. if (S_ISDIR(sb.st_mode))
  97. {
  98. ret = 0;
  99. goto exit_mkdir_p;
  100. }
  101. }
  102. /* Recursive mkdir */
  103. for (p = tmp + 1; p - tmp <= len; p++)
  104. {
  105. if ((*p == '/') || (p - tmp == len))
  106. {
  107. *p = 0;
  108. /* Test path */
  109. if (stat(tmp, &sb) != 0)
  110. {
  111. /* Path does not exist - create directory */
  112. if (mkdir(tmp, mode) < 0)
  113. {
  114. goto exit_mkdir_p;
  115. }
  116. }
  117. else if (!S_ISDIR(sb.st_mode))
  118. {
  119. /* Not a directory */
  120. goto exit_mkdir_p;
  121. }
  122. if (p - tmp != len)
  123. *p = '/';
  124. }
  125. }
  126. ret = 0;
  127. exit_mkdir_p:
  128. if (tmp)
  129. rt_free(tmp);
  130. return ret;
  131. }
  132. /* Initialize the filesystem */
  133. int filesystem_init(void)
  134. {
  135. rt_err_t result = RT_EOK;
  136. // ramdisk as root
  137. if (!rt_device_find(RAMDISK_NAME))
  138. {
  139. LOG_E("cannot find %s device", RAMDISK_NAME);
  140. goto exit_filesystem_init;
  141. }
  142. else
  143. {
  144. /* Format these ramdisk */
  145. result = (rt_err_t)dfs_mkfs("elm", RAMDISK_NAME);
  146. RT_ASSERT(result == RT_EOK);
  147. /* mount ramdisk0 as root directory */
  148. if (dfs_mount(RAMDISK_NAME, "/", "elm", 0, RT_NULL) == 0)
  149. {
  150. LOG_I("ramdisk mounted on \"/\".");
  151. /* now you can create dir dynamically. */
  152. mkdir_p("/mnt", 0x777);
  153. mkdir_p("/cache", 0x777);
  154. mkdir_p("/download", 0x777);
  155. mkdir_p("/mnt/ram_usbd", 0x777);
  156. mkdir_p("/mnt/filesystem", 0x777);
  157. #if defined(RT_USBH_MSTORAGE) && defined(UDISK_MOUNTPOINT)
  158. mkdir_p(UDISK_MOUNTPOINT, 0x777);
  159. #endif
  160. }
  161. else
  162. {
  163. LOG_E("root folder creation failed!\n");
  164. goto exit_filesystem_init;
  165. }
  166. }
  167. if (!rt_device_find(RAMDISK_UDC))
  168. {
  169. LOG_E("cannot find %s device", RAMDISK_UDC);
  170. goto exit_filesystem_init;
  171. }
  172. else
  173. {
  174. /* Format these ramdisk */
  175. result = (rt_err_t)dfs_mkfs("elm", RAMDISK_UDC);
  176. RT_ASSERT(result == RT_EOK);
  177. }
  178. exit_filesystem_init:
  179. return -result;
  180. }
  181. INIT_ENV_EXPORT(filesystem_init);
  182. #endif
  183. #if defined(PKG_USING_DFS_YAFFS) && defined(RT_USING_DFS_MNTTABLE)
  184. #include "yaffs_guts.h"
  185. int yaffs_dev_init(void)
  186. {
  187. int i;
  188. for (i=0; i<sizeof(mount_table)/sizeof(struct dfs_mount_tbl);i++)
  189. {
  190. if ( mount_table[i].filesystemtype && !rt_strcmp( mount_table[i].filesystemtype, "yaffs") )
  191. {
  192. struct rt_mtd_nand_device* psMtdNandDev = RT_MTD_NAND_DEVICE(rt_device_find(mount_table[i].device_name));
  193. if ( psMtdNandDev )
  194. {
  195. yaffs_start_up(psMtdNandDev, (const char*)mount_table[i].path);
  196. }
  197. }
  198. }
  199. return 0;
  200. }
  201. INIT_ENV_EXPORT(yaffs_dev_init);
  202. #endif
  203. #if defined(BOARD_USING_STORAGE_SPIFLASH)
  204. int mnt_init_spiflash0(void)
  205. {
  206. #if defined(RT_USING_FAL)
  207. extern int fal_init_check(void);
  208. if (!fal_init_check())
  209. fal_init();
  210. #endif
  211. struct rt_device *psNorFlash = fal_blk_device_create(PARTITION_NAME_FILESYSTEM);
  212. if (!psNorFlash)
  213. {
  214. rt_kprintf("Failed to create block device for %s.\n", PARTITION_NAME_FILESYSTEM);
  215. goto exit_mnt_init_spiflash0;
  216. }
  217. else if (dfs_mount(psNorFlash->parent.name, MOUNT_POINT_SPIFLASH0, "elm", 0, 0) != 0)
  218. {
  219. rt_kprintf("Failed to mount elm on %s.\n", MOUNT_POINT_SPIFLASH0);
  220. rt_kprintf("Try to execute 'mkfs -t elm %s' first, then reboot.\n", PARTITION_NAME_FILESYSTEM);
  221. goto exit_mnt_init_spiflash0;
  222. }
  223. rt_kprintf("mount %s with elmfat type: ok\n", PARTITION_NAME_FILESYSTEM);
  224. exit_mnt_init_spiflash0:
  225. return 0;
  226. }
  227. INIT_APP_EXPORT(mnt_init_spiflash0);
  228. #endif