From a8b7a21524ceead6eb5fb42b9aef7b5278743ff8 Mon Sep 17 00:00:00 2001 From: "Peter A. Bigot" Date: Fri, 2 Aug 2019 09:50:52 -0500 Subject: [PATCH] subsys/fs: remove ambiguity in readdir results Existing file system implementations do not provide the special "." (current) and ".." (parent) directory entries in the readdir results. littlefs does. Remove these entries in the abstraction layer. This simplifies code in higher level consumers that aren't prepared to see them. Consumers like FUSE that need them can put them back without having to worry about conflicts. Closes issue #17951 Signed-off-by: Peter A. Bigot --- include/fs/fs.h | 7 ++++++- subsys/fs/fs.c | 16 +++++++++++++++- tests/subsys/fs/littlefs/src/testfs_util.c | 3 ++- 3 files changed, 23 insertions(+), 3 deletions(-) diff --git a/include/fs/fs.h b/include/fs/fs.h index 50ccf1fb64d..d35b6a6976f 100644 --- a/include/fs/fs.h +++ b/include/fs/fs.h @@ -362,7 +362,12 @@ int fs_opendir(struct fs_dir_t *zdp, const char *path); /** * @brief Directory read entry * - * Reads directory entries of a open directory + * Reads directory entries of a open directory. + * + * @note: Most existing underlying file systems do not generate POSIX + * special directory entries "." or "..". For consistency the + * abstraction layer will remove these from lower layer results so + * higher layers see consistent results. * * @param zdp Pointer to the directory object * @param entry Pointer to zfs_dirent structure to read the entry into diff --git a/subsys/fs/fs.c b/subsys/fs/fs.c index 6ec4bc59cde..fedec7c15ae 100644 --- a/subsys/fs/fs.c +++ b/subsys/fs/fs.c @@ -255,11 +255,25 @@ int fs_readdir(struct fs_dir_t *zdp, struct fs_dirent *entry) int rc = -EINVAL; if (zdp->mp->fs->readdir != NULL) { - rc = zdp->mp->fs->readdir(zdp, entry); + /* Loop until error or not special directory */ + while (true) { + rc = zdp->mp->fs->readdir(zdp, entry); + if (rc < 0) { + break; + } + if (entry->type != FS_DIR_ENTRY_DIR) { + break; + } + if ((strcmp(entry->name, ".") != 0) + && (strcmp(entry->name, "..") != 0)) { + break; + } + } if (rc < 0) { LOG_ERR("directory read error (%d)", rc); } } + return rc; } diff --git a/tests/subsys/fs/littlefs/src/testfs_util.c b/tests/subsys/fs/littlefs/src/testfs_util.c index f21159e2e0f..9f1827a77f6 100644 --- a/tests/subsys/fs/littlefs/src/testfs_util.c +++ b/tests/subsys/fs/littlefs/src/testfs_util.c @@ -393,7 +393,8 @@ int testfs_bcmd_verify_layout(struct testfs_path *pp, stat.size); if (dotdir) { - /* ignore */ + zassert_true(false, + "special directories observed"); } else if (cp != NULL) { rc = check_layout_entry(pp, &stat, cp, ecp); if (rc > 0) {