From 11153809aba18e6500b151a5edb1f0c73a33ec5c Mon Sep 17 00:00:00 2001 From: Giovanni Di Sirio Date: Fri, 28 Jan 2022 10:24:04 +0000 Subject: [PATCH] File unlink handling added. git-svn-id: svn://svn.code.sf.net/p/chibios/svn/trunk@15416 27425a3e-05d8-49a3-a47f-9c15f0e5edd8 --- os/vfs/drivers/fatfs/drvfatfs.c | 10 ++- os/vfs/drivers/overlay/drvoverlay.c | 123 +++++++++++++++++----------- 2 files changed, 84 insertions(+), 49 deletions(-) diff --git a/os/vfs/drivers/fatfs/drvfatfs.c b/os/vfs/drivers/fatfs/drvfatfs.c index d270d6754..9b8b21913 100644 --- a/os/vfs/drivers/fatfs/drvfatfs.c +++ b/os/vfs/drivers/fatfs/drvfatfs.c @@ -119,6 +119,7 @@ static msg_t drv_open_file(void *instance, const char *path, int flags, vfs_file_node_c **vfnpp); +msg_t drv_unlink(void *instance, const char *path); msg_t drv_mkdir(void *instance, const char *path); msg_t drv_rmdir(void *instance, const char *path); @@ -127,7 +128,7 @@ static const struct vfs_fatfs_driver_vmt driver_vmt = { .get_cwd = drv_get_cwd, .open_dir = drv_open_dir, .open_file = drv_open_file, - .unlink = drv_unlink_unimpl, + .unlink = drv_unlink, .rename = drv_rename_unimpl, .mkdir = drv_mkdir, .rmdir = drv_rmdir @@ -429,6 +430,13 @@ static msg_t drv_open_file(void *instance, return err; } +msg_t drv_unlink(void *instance, const char *path) { + + (void)instance; + + return translate_error(f_unlink(path)); +} + msg_t drv_mkdir(void *instance, const char *path) { (void)instance; diff --git a/os/vfs/drivers/overlay/drvoverlay.c b/os/vfs/drivers/overlay/drvoverlay.c index 19137de72..8814a08c7 100644 --- a/os/vfs/drivers/overlay/drvoverlay.c +++ b/os/vfs/drivers/overlay/drvoverlay.c @@ -438,12 +438,79 @@ static msg_t drv_open_file(void *instance, return err; } +static msg_t drv_overlaid_path_call(vfs_overlay_driver_c *drvp, + char *buf, + msg_t (*fn)(void *ip, const char *path)) { + msg_t err; + + do { + /* Is there an overlaid driver? if so we need to pass request + processing there.*/ + if (drvp->overlaid_drv != NULL) { + + /* Processing the prefix, if defined.*/ + if (drvp->path_prefix != NULL) { + if (path_prepend(buf, + drvp->path_prefix, + VFS_CFG_PATHLEN_MAX + 1) == (size_t)0) { + err = CH_RET_ENAMETOOLONG; + break; + } + } + + /* Passing the combined path to the overlaid driver.*/ + err = fn((void *)drvp->overlaid_drv, buf); + } + else { + err = CH_RET_ENOENT; + } + } while (false); + + return err; +} + msg_t drv_unlink(void *instance, const char *path) { + msg_t err; + char *buf; - (void)instance; - (void)path; + /* Taking a path buffer from the pool.*/ + buf = vfs_buffer_take(); - return CH_RET_ENOSYS; + do { + vfs_overlay_driver_c *drvp = (vfs_overlay_driver_c *)instance; + const char *scanpath; + + /* Building the absolute path based on current directory.*/ + err = build_absolute_path(drvp, buf, path); + CH_BREAK_ON_ERROR(err); + + /* Skipping the root separator.*/ + scanpath = buf + 1; + + /* If it is the root.*/ + if (*scanpath == '\0') { + err = CH_RET_EISDIR; + } + else { /* Not the root.*/ + vfs_driver_c *dp; + + /* Searching for a match among registered overlays.*/ + err = match_driver(drvp, &scanpath, &dp); + if (!CH_RET_IS_ERROR(err)) { + /* Delegating file deletion to a registered driver.*/ + err = dp->vmt->unlink((void *)dp, scanpath); + } + else { + /* Passing the request to the overlaid driver, if any.*/ + err = drv_overlaid_path_call(drvp, buf, drvp->overlaid_drv->vmt->unlink); + } + } + } while (false); + + /* Buffer returned.*/ + vfs_buffer_release(buf); + + return err; } msg_t drv_rename(void *instance, const char *oldpath, const char *newpath) { @@ -487,30 +554,10 @@ msg_t drv_mkdir(void *instance, const char *path) { err = dp->vmt->mkdir((void *)dp, scanpath); } else { - /* Is there an overlaid driver? if so we need to pass request - processing there.*/ - if (drvp->overlaid_drv != NULL) { - - /* Processing the prefix, if defined.*/ - if (drvp->path_prefix != NULL) { - if (path_prepend(buf, - drvp->path_prefix, - VFS_CFG_PATHLEN_MAX + 1) == (size_t)0) { - err = CH_RET_ENAMETOOLONG; - break; - } - } - - /* Passing the combined path to the overlaid driver.*/ - err = drvp->overlaid_drv->vmt->mkdir((void *)drvp->overlaid_drv, - buf); - CH_BREAK_ON_ERROR(err); - } + /* Passing the request to the overlaid driver, if any.*/ + err = drv_overlaid_path_call(drvp, buf, drvp->overlaid_drv->vmt->mkdir); } } - - /* Required because the offset returned by vfs_path_prepend().*/ - err = CH_RET_SUCCESS; } while (false); /* Buffer returned.*/ @@ -547,34 +594,14 @@ msg_t drv_rmdir(void *instance, const char *path) { /* Searching for a match among registered overlays.*/ err = match_driver(drvp, &scanpath, &dp); if (!CH_RET_IS_ERROR(err)) { - /* Delegating directory creation to a registered driver.*/ + /* Delegating directory deletion to a registered driver.*/ err = dp->vmt->rmdir((void *)dp, scanpath); } else { - /* Is there an overlaid driver? if so we need to pass request - processing there.*/ - if (drvp->overlaid_drv != NULL) { - - /* Processing the prefix, if defined.*/ - if (drvp->path_prefix != NULL) { - if (path_prepend(buf, - drvp->path_prefix, - VFS_CFG_PATHLEN_MAX + 1) == (size_t)0) { - err = CH_RET_ENAMETOOLONG; - break; - } - } - - /* Passing the combined path to the overlaid driver.*/ - err = drvp->overlaid_drv->vmt->rmdir((void *)drvp->overlaid_drv, - buf); - CH_BREAK_ON_ERROR(err); - } + /* Passing the request to the overlaid driver, if any.*/ + err = drv_overlaid_path_call(drvp, buf, drvp->overlaid_drv->vmt->rmdir); } } - - /* Required because the offset returned by vfs_path_prepend().*/ - err = CH_RET_SUCCESS; } while (false); /* Buffer returned.*/