358 lines
10 KiB
C
358 lines
10 KiB
C
/*
|
|
ChibiOS - Copyright (C) 2006,2007,2008,2009,2010,2011,2012,2013,2014,
|
|
2015,2016,2017,2018,2019,2020,2021 Giovanni Di Sirio.
|
|
|
|
This file is part of ChibiOS.
|
|
|
|
ChibiOS is free software; you can redistribute it and/or modify
|
|
it under the terms of the GNU General Public License as published by
|
|
the Free Software Foundation version 3 of the License.
|
|
|
|
ChibiOS is distributed in the hope that it will be useful,
|
|
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
GNU General Public License for more details.
|
|
|
|
You should have received a copy of the GNU General Public License
|
|
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|
*/
|
|
|
|
/**
|
|
* @file vfs/src/vfs.c
|
|
* @brief VFS API code.
|
|
*
|
|
* @addtogroup VFS
|
|
* @{
|
|
*/
|
|
|
|
#include "vfs.h"
|
|
|
|
/*===========================================================================*/
|
|
/* Module local definitions. */
|
|
/*===========================================================================*/
|
|
|
|
/*===========================================================================*/
|
|
/* Module exported variables. */
|
|
/*===========================================================================*/
|
|
|
|
/*===========================================================================*/
|
|
/* Module local types. */
|
|
/*===========================================================================*/
|
|
|
|
/*===========================================================================*/
|
|
/* Module local variables. */
|
|
/*===========================================================================*/
|
|
|
|
/*===========================================================================*/
|
|
/* Module local functions. */
|
|
/*===========================================================================*/
|
|
|
|
/*===========================================================================*/
|
|
/* Module exported functions. */
|
|
/*===========================================================================*/
|
|
|
|
/**
|
|
* @brief VFS initialization.
|
|
*
|
|
* @init
|
|
*/
|
|
void vfsInit(void) {
|
|
|
|
/* Shared buffers manager initialization.*/
|
|
__vfs_buffers_init();
|
|
|
|
#if VFS_CFG_ENABLE_DRV_OVERLAY == TRUE
|
|
__drv_overlay_init();
|
|
#endif
|
|
|
|
#if VFS_CFG_ENABLE_DRV_STREAMS == TRUE
|
|
__drv_streams_init();
|
|
#endif
|
|
|
|
#if VFS_CFG_ENABLE_DRV_FATFS == TRUE
|
|
__drv_fatfs_init();
|
|
#endif
|
|
}
|
|
|
|
/**
|
|
* @brief Returns the current file size.
|
|
*.
|
|
* @param[in] np Pointer to the @p vfs_node_c object
|
|
* @param[out] sp Pointer to a @p vfs_stat_t structure.
|
|
* @return The operation result.
|
|
*
|
|
* @api
|
|
*/
|
|
msg_t vfsGetStat(vfs_node_c *np, vfs_stat_t *sp) {
|
|
|
|
chDbgAssert(np->references > 0U, "zero count");
|
|
|
|
return np->vmt->node_stat((void *)np, sp);
|
|
}
|
|
|
|
/**
|
|
* @brief Changes the current VFS directory.
|
|
*
|
|
* @param[in] path Path of the new current directory.
|
|
* @return The operation result.
|
|
*
|
|
* @api
|
|
*/
|
|
msg_t vfsChangeCurrentDirectory(const char *path) {
|
|
|
|
return vfsDrvChangeCurrentDirectory(vfs_root, path);
|
|
}
|
|
|
|
/**
|
|
* @brief Returns the current VFS directory.
|
|
*
|
|
* @param[out] buf Buffer for the path string.
|
|
* @param[in] size Size of the buffer.
|
|
* @return The operation result.
|
|
*
|
|
* @api
|
|
*/
|
|
msg_t vfsGetCurrentDirectory(char *buf, size_t size) {
|
|
|
|
return vfsDrvGetCurrentDirectory(vfs_root, buf, size);
|
|
}
|
|
|
|
/**
|
|
* @brief Opens a VFS file or directory.
|
|
*
|
|
* @param[in] path Absolute path of the node to be opened.
|
|
* @param[in] flags Open flags.
|
|
* @param[out] vnpp Pointer to the pointer to the instantiated
|
|
* @p vfs_node_c object.
|
|
* @return The operation result.
|
|
*
|
|
* @api
|
|
*/
|
|
msg_t vfsOpen(const char *path, int flags, vfs_node_c **vnpp) {
|
|
|
|
return vfsDrvOpen(vfs_root, path, flags, vnpp);
|
|
}
|
|
|
|
/**
|
|
* @brief Opens a VFS directory.
|
|
*
|
|
* @param[in] path Absolute path of the directory to be opened.
|
|
* @param[out] vdnpp Pointer to the pointer to the instantiated
|
|
* @p vfs_directory_node_c object.
|
|
* @return The operation result.
|
|
*
|
|
* @api
|
|
*/
|
|
msg_t vfsOpenDirectory(const char *path, vfs_directory_node_c **vdnpp) {
|
|
|
|
return vfsDrvOpenDirectory(vfs_root, path, vdnpp);
|
|
}
|
|
|
|
/**
|
|
* @brief Opens a VFS file.
|
|
*
|
|
* @param[in] path Path of the file to be opened.
|
|
* @param[in] flags File open flags.
|
|
* @param[out] vdnpp Pointer to the pointer to the instantiated
|
|
* @p vfs_file_node_c object.
|
|
* @return The operation result.
|
|
*
|
|
* @api
|
|
*/
|
|
msg_t vfsOpenFile(const char *path, int flags, vfs_file_node_c **vfnpp) {
|
|
|
|
return vfsDrvOpenFile(vfs_root, path, flags, vfnpp);
|
|
}
|
|
|
|
/**
|
|
* @brief Unlinks and possibly deletes a file.
|
|
*
|
|
* @param[in] path Path of the file to be unlinked.
|
|
* @return The operation result.
|
|
*
|
|
* @api
|
|
*/
|
|
static inline msg_t vfsUnlink(const char *path) {
|
|
|
|
return vfsDrvUnlink(vfs_root, path);
|
|
}
|
|
|
|
/**
|
|
* @brief Renames a file or directory.
|
|
*
|
|
* @param[in] oldpath Path of the file to be renamed.
|
|
* @param[in] oldpath New path of the renamed file.
|
|
* @return The operation result.
|
|
*
|
|
* @api
|
|
*/
|
|
static inline msg_t vfsRename(const char *oldpath, const char *newpath) {
|
|
|
|
return vfsDrvRename(vfs_root, oldpath, newpath);
|
|
}
|
|
|
|
/**
|
|
* @brief Creates a directory.
|
|
*
|
|
* @param[in] path Path of the directory to be created.
|
|
* @return The operation result.
|
|
*
|
|
* @api
|
|
*/
|
|
static inline msg_t vfsMkdir(const char *path) {
|
|
|
|
return vfsDrvMkdir(vfs_root, path);
|
|
}
|
|
|
|
/**
|
|
* @brief Removes a directory.
|
|
*
|
|
* @param[in] path Path of the directory to be removed.
|
|
* @return The operation result.
|
|
*
|
|
* @api
|
|
*/
|
|
static inline msg_t vfsRmdir(const char *path) {
|
|
|
|
return vfsDrvRmdir(vfs_root, path);
|
|
}
|
|
|
|
/**
|
|
* @brief Releases a @p vfs_node_c or descendant object.
|
|
*
|
|
* @param[in] vnp Pointer to the @p vfs_node_c object to be released.
|
|
*
|
|
* @api
|
|
*/
|
|
void vfsClose(vfs_node_c *vnp) {
|
|
|
|
chDbgAssert(vnp->references > 0U, "zero count");
|
|
|
|
vnp->vmt->release((void *)vnp);
|
|
}
|
|
|
|
/**
|
|
* @brief First directory entry.
|
|
*
|
|
* @param[in] vdnp Pointer to the @p vfs_directory_node_c object.
|
|
* @param[out] dip Pointer to a @p vfs_direntry_info_t structure.
|
|
* @return The operation result.
|
|
* @retval 0 Zero entries read, end-of-directory condition.
|
|
* @retval 1 One directory entry read.
|
|
*
|
|
* @api
|
|
*/
|
|
msg_t vfsReadDirectoryFirst(vfs_directory_node_c *vdnp,
|
|
vfs_direntry_info_t *dip) {
|
|
|
|
chDbgAssert(vdnp->references > 0U, "zero count");
|
|
|
|
return vdnp->vmt->dir_first((void *)vdnp, dip);
|
|
}
|
|
|
|
/**
|
|
* @brief Next directory entry.
|
|
*
|
|
* @param[in] vdnp Pointer to the @p vfs_directory_node_c object.
|
|
* @param[out] dip Pointer to a @p vfs_direntry_info_t structure.
|
|
* @return The operation result.
|
|
* @retval 0 Zero entries read, end-of-directory condition.
|
|
* @retval 1 One directory entry read.
|
|
*
|
|
* @api
|
|
*/
|
|
msg_t vfsReadDirectoryNext(vfs_directory_node_c *vdnp,
|
|
vfs_direntry_info_t *dip) {
|
|
|
|
chDbgAssert(vdnp->references > 0U, "zero count");
|
|
|
|
return vdnp->vmt->dir_next((void *)vdnp, dip);
|
|
}
|
|
|
|
/**
|
|
* @brief File node read.
|
|
* @details The function reads data from a file node into a buffer.
|
|
*
|
|
* @param[in] vfnp Pointer to the @p vfs_file_node_c object.
|
|
* @param[out] buf Pointer to the data buffer.
|
|
* @param[in] n Maximum amount of data to be transferred.
|
|
* @return The transferred number of bytes or an error.
|
|
*
|
|
* @api
|
|
*/
|
|
ssize_t vfsReadFile(vfs_file_node_c *vfnp, uint8_t *buf, size_t n) {
|
|
|
|
chDbgAssert(vfnp->references > 0U, "zero count");
|
|
|
|
return vfnp->vmt->file_read((void *)vfnp, buf, n);
|
|
}
|
|
|
|
/**
|
|
* @brief File node write.
|
|
* @details The function writes data from a buffer to a file node.
|
|
*
|
|
* @param[in] vfnp Pointer to the @p vfs_file_node_c object.
|
|
* @param[out] buf Pointer to the data buffer.
|
|
* @param[in] n Maximum amount of data to be transferred.
|
|
* @return The transferred number of bytes or an error.
|
|
*
|
|
* @api
|
|
*/
|
|
ssize_t vfsWriteFile(vfs_file_node_c *vfnp, const uint8_t *buf, size_t n) {
|
|
|
|
chDbgAssert(vfnp->references > 0U, "zero count");
|
|
|
|
return vfnp->vmt->file_write((void *)vfnp, buf, n);
|
|
}
|
|
|
|
/**
|
|
* @brief Changes the current file position.
|
|
*
|
|
* @param[in] vfnp Pointer to the @p vfs_file_node_c object.
|
|
* @param[in] offset New absolute position.
|
|
* @param[in] whence Seek mode to be used.
|
|
* @return The operation result.
|
|
*
|
|
* @api
|
|
*/
|
|
msg_t vfsSetFilePosition(vfs_file_node_c *vfnp,
|
|
vfs_offset_t offset,
|
|
vfs_seekmode_t whence) {
|
|
|
|
chDbgAssert(vfnp->references > 0U, "zero count");
|
|
|
|
return vfnp->vmt->file_setpos((void *)vfnp, offset, whence);
|
|
}
|
|
|
|
/**
|
|
* @brief Returns the current file position.
|
|
*
|
|
* @param[in] vfnp Pointer to the @p vfs_file_node_c object.
|
|
* @return The current file position.
|
|
*
|
|
* @api
|
|
*/
|
|
vfs_offset_t vfsGetFilePosition(vfs_file_node_c *vfnp) {
|
|
|
|
chDbgAssert(vfnp->references > 0U, "zero count");
|
|
|
|
return vfnp->vmt->file_getpos((void *)vfnp);
|
|
}
|
|
|
|
/**
|
|
* @brief Returns the inner stream associated to the file.
|
|
*
|
|
* @param[in] vfnp Pointer to the @p vfs_file_node_c object.
|
|
* @return The current file size.
|
|
*
|
|
* @api
|
|
*/
|
|
BaseSequentialStream *vfsGetFileStream(vfs_file_node_c *vfnp) {
|
|
|
|
chDbgAssert(vfnp->references > 0U, "zero count");
|
|
|
|
return vfnp->vmt->file_get_stream((void *)vfnp);
|
|
}
|
|
|
|
/** @} */
|