[components][dfs]add some comments and fix some former comments error for dfs v1.

This commit is contained in:
ligr 2024-12-03 10:14:41 +08:00 committed by Meco Man
parent 294e441a75
commit 1cf97d8565
3 changed files with 169 additions and 17 deletions

View File

@ -1,5 +1,5 @@
/* /*
* Copyright (c) 2006-2022, RT-Thread Development Team * Copyright (c) 2006-2024 RT-Thread Development Team
* *
* SPDX-License-Identifier: Apache-2.0 * SPDX-License-Identifier: Apache-2.0
* *
@ -107,7 +107,8 @@ int dfs_init(void)
INIT_PREV_EXPORT(dfs_init); INIT_PREV_EXPORT(dfs_init);
/** /**
* this function will lock device file system. * @brief this function will lock device file system.
* this lock (fslock) is used for protecting filesystem_operation_table and filesystem_table.
* *
* @note please don't invoke it on ISR. * @note please don't invoke it on ISR.
*/ */
@ -126,6 +127,12 @@ void dfs_lock(void)
} }
} }
/**
* @brief this function will lock file descriptors.
* this lock (fdlock) is used for protecting fd table (_fdtab).
*
* @note please don't invoke it on ISR.
*/
void dfs_file_lock(void) void dfs_file_lock(void)
{ {
rt_err_t result = -RT_EBUSY; rt_err_t result = -RT_EBUSY;
@ -142,7 +149,7 @@ void dfs_file_lock(void)
} }
/** /**
* this function will lock device file system. * @brief this function will unlock device file system.
* *
* @note please don't invoke it on ISR. * @note please don't invoke it on ISR.
*/ */
@ -151,33 +158,56 @@ void dfs_unlock(void)
rt_mutex_release(&fslock); rt_mutex_release(&fslock);
} }
#ifdef DFS_USING_POSIX /**
* @brief this function will unlock fd table.
*/
void dfs_file_unlock(void) void dfs_file_unlock(void)
{ {
rt_mutex_release(&fdlock); rt_mutex_release(&fdlock);
} }
#ifdef DFS_USING_POSIX
/**
* @brief Expand the file descriptor table to accommodate a specific file descriptor.
*
* This function ensures that the file descriptor table in the given `dfs_fdtable` structure
* has sufficient capacity to include the specified file descriptor `fd`. If the table
* needs to be expanded, it reallocates memory and initializes new slots to `NULL`.
*
* @param fdt Pointer to the `dfs_fdtable` structure representing the file descriptor table.
* @param fd The file descriptor that the table must accommodate.
* @return int
* - The input file descriptor `fd` if it is within the current or newly expanded table's capacity.
* - `-1` if the requested file descriptor exceeds `DFS_FD_MAX` or memory allocation fails.
*/
static int fd_slot_expand(struct dfs_fdtable *fdt, int fd) static int fd_slot_expand(struct dfs_fdtable *fdt, int fd)
{ {
int nr; int nr;
int index; int index;
struct dfs_file **fds = NULL; struct dfs_file **fds = NULL;
/* If the file descriptor is already within the current capacity, no expansion is needed.*/
if (fd < fdt->maxfd) if (fd < fdt->maxfd)
{ {
return fd; return fd;
} }
/* If the file descriptor exceeds the maximum allowable limit, return an error.*/
if (fd >= DFS_FD_MAX) if (fd >= DFS_FD_MAX)
{ {
return -1; return -1;
} }
/* Calculate the new capacity, rounding up to the nearest multiple of 4.*/
nr = ((fd + 4) & ~3); nr = ((fd + 4) & ~3);
/* Ensure the new capacity does not exceed the maximum limit.*/
if (nr > DFS_FD_MAX) if (nr > DFS_FD_MAX)
{ {
nr = DFS_FD_MAX; nr = DFS_FD_MAX;
} }
/* Attempt to reallocate the file descriptor table to the new capacity.*/
fds = (struct dfs_file **)rt_realloc(fdt->fds, nr * sizeof(struct dfs_file *)); fds = (struct dfs_file **)rt_realloc(fdt->fds, nr * sizeof(struct dfs_file *));
if (!fds) if (!fds)
{ {
@ -189,12 +219,23 @@ static int fd_slot_expand(struct dfs_fdtable *fdt, int fd)
{ {
fds[index] = NULL; fds[index] = NULL;
} }
/* Update the file descriptor table and its capacity.*/
fdt->fds = fds; fdt->fds = fds;
fdt->maxfd = nr; fdt->maxfd = nr;
return fd; return fd;
} }
/**
* @brief Allocate a file descriptor slot starting from a specified index.
*
* @param fdt fdt Pointer to the `dfs_fdtable` structure representing the file descriptor table.
* @param startfd The starting index for the search for an empty slot.
* @return int
* - The index of the first available slot if successful.
* - `-1` if no slot is available or if table expansion fails
*/
static int fd_slot_alloc(struct dfs_fdtable *fdt, int startfd) static int fd_slot_alloc(struct dfs_fdtable *fdt, int startfd)
{ {
int idx; int idx;
@ -219,6 +260,17 @@ static int fd_slot_alloc(struct dfs_fdtable *fdt, int startfd)
} }
return idx; return idx;
} }
/**
* @brief Allocate a new file descriptor and associate it with a newly allocated `struct dfs_file`.
*
* @param fdt Pointer to the `dfs_fdtable` structure representing the file descriptor table.
* @param startfd The starting index for searching an available file descriptor slot.
*
* @return
* - The index of the allocated file descriptor if successful.
* - `-1` if no slot is available or memory allocation fails.
*/
static int fd_alloc(struct dfs_fdtable *fdt, int startfd) static int fd_alloc(struct dfs_fdtable *fdt, int startfd)
{ {
int idx; int idx;
@ -323,7 +375,11 @@ struct dfs_file *fd_get(int fd)
/** /**
* @ingroup Fd * @ingroup Fd
* *
* This function will put the file descriptor. * @brief This function will release the file descriptor.
*
* This function releases a file descriptor slot in the file descriptor table, decrements reference
* counts, and cleans up resources associated with the `dfs_file` and `dfs_vnode` structures when applicable.
*
*/ */
void fdt_fd_release(struct dfs_fdtable* fdt, int fd) void fdt_fd_release(struct dfs_fdtable* fdt, int fd)
{ {
@ -378,6 +434,20 @@ void fd_release(int fd)
fdt_fd_release(fdt, fd); fdt_fd_release(fdt, fd);
} }
/**
* @brief Duplicates a file descriptor.
*
* This function duplicates an existing file descriptor (`oldfd`) and returns
* a new file descriptor that refers to the same underlying file object.
*
* @param oldfd The file descriptor to duplicate. It must be a valid file
* descriptor within the range of allocated descriptors.
*
* @return The new file descriptor if successful, or a negative value
* (e.g., -1) if an error occurs.
*
* @see sys_dup2()
*/
rt_err_t sys_dup(int oldfd) rt_err_t sys_dup(int oldfd)
{ {
int newfd = -1; int newfd = -1;
@ -470,6 +540,23 @@ int fd_is_open(const char *pathname)
return -1; return -1;
} }
/**
* @brief Duplicates a file descriptor to a specified file descriptor.
*
* This function duplicates an existing file descriptor (`oldfd`) and assigns it
* to the specified file descriptor (`newfd`).
*
* @param oldfd The file descriptor to duplicate. It must be a valid and open file
* descriptor within the range of allocated descriptors.
* @param newfd The target file descriptor. If `newfd` is already in use, it will
* be closed before duplication. If `newfd` exceeds the current file
* descriptor table size, the table will be expanded to accommodate it.
*
* @return The value of `newfd` on success, or a negative value (e.g., -1) if an
* error occurs.
*
* @see sys_dup()
*/
rt_err_t sys_dup2(int oldfd, int newfd) rt_err_t sys_dup2(int oldfd, int newfd)
{ {
struct dfs_fdtable *fdt = NULL; struct dfs_fdtable *fdt = NULL;
@ -550,6 +637,10 @@ static int fd_get_fd_index_form_fdt(struct dfs_fdtable *fdt, struct dfs_file *fi
return fd; return fd;
} }
/**
* @brief get fd (index) by dfs file object.
*
*/
int fd_get_fd_index(struct dfs_file *file) int fd_get_fd_index(struct dfs_file *file)
{ {
struct dfs_fdtable *fdt; struct dfs_fdtable *fdt;
@ -558,6 +649,21 @@ int fd_get_fd_index(struct dfs_file *file)
return fd_get_fd_index_form_fdt(fdt, file); return fd_get_fd_index_form_fdt(fdt, file);
} }
/**
* @brief Associates a file descriptor with a file object.
*
* This function associates a given file descriptor (`fd`) with a specified
* file object (`file`) in the file descriptor table (`fdt`).
*
* @param fdt The file descriptor table to operate on. It must be a valid
* and initialized `dfs_fdtable` structure.
* @param fd The file descriptor to associate. It must be within the range
* of allocated file descriptors and currently unoccupied.
* @param file The file object to associate with the file descriptor. It must
* be a valid and initialized `dfs_file` structure.
*
* @return The value of `fd` on success, or -1 if an error occurs.
*/
int fd_associate(struct dfs_fdtable *fdt, int fd, struct dfs_file *file) int fd_associate(struct dfs_fdtable *fdt, int fd, struct dfs_file *file)
{ {
int retfd = -1; int retfd = -1;
@ -591,6 +697,10 @@ exit:
return retfd; return retfd;
} }
/**
* @brief initialize a dfs file object.
*
*/
void fd_init(struct dfs_file *fd) void fd_init(struct dfs_file *fd)
{ {
if (fd) if (fd)

View File

@ -1,5 +1,5 @@
/* /*
* Copyright (c) 2006-2021, RT-Thread Development Team * Copyright (c) 2006-2024 RT-Thread Development Team
* *
* SPDX-License-Identifier: Apache-2.0 * SPDX-License-Identifier: Apache-2.0
* *
@ -18,10 +18,12 @@
#define DFS_VNODE_HASH_NR 128 #define DFS_VNODE_HASH_NR 128
/*dfs vnode manager, for saving and searching vnodes.*/
struct dfs_vnode_mgr struct dfs_vnode_mgr
{ {
struct rt_mutex lock; struct rt_mutex lock; /* mutex for protecting dfs vnode lists */
rt_list_t head[DFS_VNODE_HASH_NR]; rt_list_t head[DFS_VNODE_HASH_NR]; /* a group of dfs vnode lists, the dfs vnode is inserted to one of the lists
according to path string's hash-value mod DFS_VNODE_HASH_NR. */
}; };
static struct dfs_vnode_mgr dfs_fm; static struct dfs_vnode_mgr dfs_fm;
@ -36,6 +38,10 @@ void dfs_fm_unlock(void)
rt_mutex_release(&dfs_fm.lock); rt_mutex_release(&dfs_fm.lock);
} }
/**
* @brief Initialize dfs vnode manager structure, including a lock and hash tables for vnode.
*
*/
void dfs_vnode_mgr_init(void) void dfs_vnode_mgr_init(void)
{ {
int i = 0; int i = 0;
@ -47,6 +53,23 @@ void dfs_vnode_mgr_init(void)
} }
} }
/**
* @brief Initialize a DFS vnode structure.
*
* @param vnode Pointer to the DFS vnode structure to be initialized.
* The caller must ensure this is a valid, allocated structure.
* @param type The type of the vnode, representing its role or category (e.g., regular file, directory).
* @param fops Pointer to the file operations structure associated with this vnode.
* This structure defines the behavior of the vnode for operations such as open, read, write, etc.
* If `fops` is NULL, the vnode will have no associated file operations.
*
* @return 0 on success, or a negative error code on failure.
*
* @note The caller should ensure that:
* - The `vnode` pointer is valid and properly allocated.
* - The `fops` pointer (if not NULL) points to a valid `struct dfs_file_ops`
* instance, where all necessary function pointers are properly set.
*/
int dfs_vnode_init(struct dfs_vnode *vnode, int type, const struct dfs_file_ops *fops) int dfs_vnode_init(struct dfs_vnode *vnode, int type, const struct dfs_file_ops *fops)
{ {
if (vnode) if (vnode)
@ -64,7 +87,7 @@ int dfs_vnode_init(struct dfs_vnode *vnode, int type, const struct dfs_file_ops
/* BKDR Hash Function */ /* BKDR Hash Function */
static unsigned int bkdr_hash(const char *str) static unsigned int bkdr_hash(const char *str)
{ {
unsigned int seed = 131; // 31 131 1313 13131 131313 etc.. unsigned int seed = 131; /* 31 131 1313 13131 131313 etc..*/
unsigned int hash = 0; unsigned int hash = 0;
while (*str) while (*str)
@ -75,6 +98,22 @@ static unsigned int bkdr_hash(const char *str)
return (hash % DFS_VNODE_HASH_NR); return (hash % DFS_VNODE_HASH_NR);
} }
/**
* @brief Find a DFS vnode by its path.
*
* This function searches for a vnode in the vnode hash table using the specified path.
* If found, it returns a pointer to the vnode and updates the hash head if required.
*
* @param path The file path to search for. This should be a valid null-terminated string.
* @param hash_head Pointer to a location where the hash table head associated with the vnode
* can be stored. This can be NULL if the hash head is not needed.
*
* @return Pointer to the DFS vnode if found, or NULL if no vnode matches the specified path.
*
* @note The caller must ensure that:
* - The `path` pointer is valid and points to a properly null-terminated string.
* - If `hash_head` is not NULL, it points to a valid location to store the hash head.
*/
static struct dfs_vnode *dfs_vnode_find(const char *path, rt_list_t **hash_head) static struct dfs_vnode *dfs_vnode_find(const char *path, rt_list_t **hash_head)
{ {
struct dfs_vnode *vnode = NULL; struct dfs_vnode *vnode = NULL;
@ -329,11 +368,12 @@ int dfs_file_close(struct dfs_file *fd)
} }
/** /**
* this function will perform a io control on a file descriptor. * this function will perform an io control on a file descriptor.
* *
* @param fd the file descriptor. * @param fd the file descriptor.
* @param cmd the command to send to file descriptor. * @param cmd the command to send to file descriptor.
* @param args the argument to send to file descriptor. * @param args the argument to send to file descriptor.
* - When `cmd` is `F_SETFL`, an additional integer argument specifies the new status flags.
* *
* @return 0 on successful, -1 on failed. * @return 0 on successful, -1 on failed.
*/ */
@ -1026,14 +1066,14 @@ void copy(const char *src, const char *dst)
flag |= FLAG_DST_IS_FILE; flag |= FLAG_DST_IS_FILE;
} }
//2. check status /*2. check status*/
if ((flag & FLAG_SRC_IS_DIR) && (flag & FLAG_DST_IS_FILE)) if ((flag & FLAG_SRC_IS_DIR) && (flag & FLAG_DST_IS_FILE))
{ {
rt_kprintf("cp faild, cp dir to file is not permitted!\n"); rt_kprintf("cp faild, cp dir to file is not permitted!\n");
return ; return ;
} }
//3. do copy /*3. do copy*/
if (flag & FLAG_SRC_IS_FILE) if (flag & FLAG_SRC_IS_FILE)
{ {
if (flag & FLAG_DST_IS_DIR) if (flag & FLAG_DST_IS_DIR)
@ -1053,7 +1093,7 @@ void copy(const char *src, const char *dst)
copyfile(src, dst); copyfile(src, dst);
} }
} }
else //flag & FLAG_SRC_IS_DIR else /*flag & FLAG_SRC_IS_DIR*/
{ {
if (flag & FLAG_DST_IS_DIR) if (flag & FLAG_DST_IS_DIR)
{ {

View File

@ -1,5 +1,5 @@
/* /*
* Copyright (c) 2006-2021, RT-Thread Development Team * Copyright (c) 2006-2024 RT-Thread Development Team
* *
* SPDX-License-Identifier: Apache-2.0 * SPDX-License-Identifier: Apache-2.0
* *
@ -529,7 +529,8 @@ int dfs_mount_device(rt_device_t dev)
{ {
int index = 0; int index = 0;
if(dev == RT_NULL) { if(dev == RT_NULL)
{
rt_kprintf("the device is NULL to be mounted.\n"); rt_kprintf("the device is NULL to be mounted.\n");
return -RT_ERROR; return -RT_ERROR;
} }
@ -538,7 +539,8 @@ int dfs_mount_device(rt_device_t dev)
{ {
if (mount_table[index].path == NULL) break; if (mount_table[index].path == NULL) break;
if(strcmp(mount_table[index].device_name, dev->parent.name) == 0) { if(strcmp(mount_table[index].device_name, dev->parent.name) == 0)
{
if (dfs_mount(mount_table[index].device_name, if (dfs_mount(mount_table[index].device_name,
mount_table[index].path, mount_table[index].path,
mount_table[index].filesystemtype, mount_table[index].filesystemtype,