From 6e86d6d69951278c8db59fc0c66ce9bda6955f54 Mon Sep 17 00:00:00 2001 From: Norman Feske Date: Mon, 7 Oct 2019 16:09:05 +0200 Subject: [PATCH] Remove server/fatfs_fs and libc_fatfs plugin Issue #3512 --- repos/libports/lib/mk/libc_fatfs.mk | 8 - repos/libports/run/libc_fatfs.run | 12 - repos/libports/run/libc_vfs_fatfs_fs.run | 7 - repos/libports/src/lib/libc_fatfs/plugin.cc | 805 ------------- .../libports/src/server/fatfs_fs/directory.h | 123 -- repos/libports/src/server/fatfs_fs/file.h | 266 ----- repos/libports/src/server/fatfs_fs/main.cc | 1004 ----------------- repos/libports/src/server/fatfs_fs/node.h | 75 -- .../libports/src/server/fatfs_fs/open_node.h | 95 -- repos/libports/src/server/fatfs_fs/target.mk | 6 - repos/libports/src/server/fatfs_fs/util.h | 87 -- repos/libports/src/test/libc_fatfs/target.mk | 8 - tool/autopilot.list | 1 - 13 files changed, 2497 deletions(-) delete mode 100644 repos/libports/lib/mk/libc_fatfs.mk delete mode 100644 repos/libports/run/libc_fatfs.run delete mode 100644 repos/libports/run/libc_vfs_fatfs_fs.run delete mode 100644 repos/libports/src/lib/libc_fatfs/plugin.cc delete mode 100644 repos/libports/src/server/fatfs_fs/directory.h delete mode 100644 repos/libports/src/server/fatfs_fs/file.h delete mode 100644 repos/libports/src/server/fatfs_fs/main.cc delete mode 100644 repos/libports/src/server/fatfs_fs/node.h delete mode 100644 repos/libports/src/server/fatfs_fs/open_node.h delete mode 100644 repos/libports/src/server/fatfs_fs/target.mk delete mode 100644 repos/libports/src/server/fatfs_fs/util.h delete mode 100644 repos/libports/src/test/libc_fatfs/target.mk diff --git a/repos/libports/lib/mk/libc_fatfs.mk b/repos/libports/lib/mk/libc_fatfs.mk deleted file mode 100644 index fa9d4699b..000000000 --- a/repos/libports/lib/mk/libc_fatfs.mk +++ /dev/null @@ -1,8 +0,0 @@ -SRC_CC = plugin.cc -LIBS += libc fatfs_block - -vpath plugin.cc $(REP_DIR)/src/lib/libc_fatfs - -SHARED_LIB = yes - -CC_CXX_WARN_STRICT = diff --git a/repos/libports/run/libc_fatfs.run b/repos/libports/run/libc_fatfs.run deleted file mode 100644 index f837d6959..000000000 --- a/repos/libports/run/libc_fatfs.run +++ /dev/null @@ -1,12 +0,0 @@ -set mkfs_cmd [installed_command mkfs.vfat] -set mkfs_opts "-F32" -set filesystem fatfs - -# -# The fatfs_libc plugin opens a block session directly. If the VFS opened -# the block session, the plugin would try to open a second one, which -# would get denied by the block driver. -# -set libc_dev_blkdev "" - -source ${genode_dir}/repos/libports/run/libc_filesystem_test.inc diff --git a/repos/libports/run/libc_vfs_fatfs_fs.run b/repos/libports/run/libc_vfs_fatfs_fs.run deleted file mode 100644 index 7095c665d..000000000 --- a/repos/libports/run/libc_vfs_fatfs_fs.run +++ /dev/null @@ -1,7 +0,0 @@ -set build_component server/fatfs_fs -set binary fatfs_fs -set mkfs_cmd mkfs.vfat -set mkfs_opts "-F32" -set vfs_dev_blkdev "" - -source ${genode_dir}/repos/libports/run/libc_vfs_fs_test.inc diff --git a/repos/libports/src/lib/libc_fatfs/plugin.cc b/repos/libports/src/lib/libc_fatfs/plugin.cc deleted file mode 100644 index 5864e22fc..000000000 --- a/repos/libports/src/lib/libc_fatfs/plugin.cc +++ /dev/null @@ -1,805 +0,0 @@ -/* - * \brief FATFS libc plugin - * \author Christian Prochaska - * \date 2011-05-27 - */ - -/* - * Copyright (C) 2011-2017 Genode Labs GmbH - * - * This file is part of the Genode OS framework, which is distributed - * under the terms of the GNU Affero General Public License version 3. - */ - -/* Genode includes */ -#include -#include -#include -#include - -/* libc includes */ -#include -#include -#include -#include -#include -#include - -/* libc plugin interface */ -#include -#include - -#include - -namespace Fatfs { extern "C" { -#include -} } - -static bool const verbose = false; - - -namespace { - - -class Plugin_context : public Libc::Plugin_context -{ - private: - - char *_filename; /* needed for fstat() */ - int _fd_flags; - int _status_flags; - - public: - - Plugin_context(const char *filename) - : _fd_flags(0), _status_flags(0) - { - _filename = (char*)malloc(::strlen(filename) + 1); - ::strcpy(_filename, filename); - } - - virtual ~Plugin_context() - { - ::free(_filename); - } - - const char *filename() { return _filename; } - - /** - * Set/get file descriptor flags - */ - void fd_flags(int flags) { _fd_flags = flags; } - int fd_flags() { return _fd_flags; } - - /** - * Set/get file status status flags - */ - void status_flags(int flags) { _status_flags = flags; } - int status_flags() { return _status_flags; } -}; - - -static inline Plugin_context *context(Libc::File_descriptor *fd) -{ - return fd->context ? static_cast(fd->context) : 0; -} - - -class File_plugin_context : public Plugin_context -{ - private: - - Fatfs::FIL _fatfs_file; - - public: - - /** - * Constructor - * - * \param filename - * \param fatfs_file file object used for interacting with the - * file API of fatfs - */ - File_plugin_context(const char *filename, Fatfs::FIL fatfs_file) : - Plugin_context(filename), _fatfs_file(fatfs_file) { } - - Fatfs::FIL *fatfs_file() { return &_fatfs_file; } -}; - - -class Directory_plugin_context : public Plugin_context -{ - private: - - Fatfs::DIR _fatfs_dir; - - public: - - /** - * Constructor - * - * \param filename - * \param fatfs_dir dir object used for interacting with the - * file API of fatfs - */ - Directory_plugin_context(const char *filename, Fatfs::DIR fatfs_dir) : - Plugin_context(filename), _fatfs_dir(fatfs_dir) { } - - Fatfs::DIR *fatfs_dir() { return &_fatfs_dir; } -}; - - -class Plugin : public Libc::Plugin -{ - private: - - Genode::Constructible _heap; - - Fatfs::FATFS _fatfs; - - Fatfs::FIL *_get_fatfs_file(Libc::File_descriptor *fd) - { - File_plugin_context *file_plugin_context = - dynamic_cast(context(fd)); - if (!file_plugin_context) { - return 0; - } - return file_plugin_context->fatfs_file(); - } - - Fatfs::DIR *_get_fatfs_dir(Libc::File_descriptor *fd) - { - Directory_plugin_context *directory_plugin_context = - dynamic_cast(context(fd)); - if (!directory_plugin_context) { - return 0; - } - return directory_plugin_context->fatfs_dir(); - } - - /* - * Override libc_vfs - */ - enum { PLUGIN_PRIORITY = 1 }; - - public: - - /** - * Constructor - */ - Plugin() : Libc::Plugin(PLUGIN_PRIORITY) { } - - ~Plugin() - { - /* unmount the file system */ - Fatfs::f_unmount(""); - } - - void init(Genode::Env &env) override - { - _heap.construct(env.ram(), env.rm()); - - Fatfs::block_init(env, *_heap); - - /* mount the file system */ - if (verbose) - Genode::log(__func__, ": mounting device ..."); - - if (f_mount(&_fatfs, "", 0) != Fatfs::FR_OK) { - Genode::error("mount failed"); - } - } - - /* - * TODO: decide if the file named shall be handled by this plugin - */ - - bool supports_mkdir(const char *path, mode_t) override - { - if (verbose) - Genode::log(__func__, ": path=", path); - return true; - } - - bool supports_open(const char *pathname, int flags) override - { - if (verbose) - Genode::log(__func__, ": pathname=", pathname); - return true; - } - - bool supports_rename(const char *oldpath, const char *newpath) override - { - if (verbose) - Genode::log(__func__, ": oldpath=", oldpath, ", newpath=", newpath); - return true; - } - - bool supports_rmdir(const char *path) override - { - if (verbose) - Genode::log(__func__, ": path=", path); - return true; - } - - bool supports_stat(const char *path) override - { - if (verbose) - Genode::log(__func__, ": path=", path); - return true; - } - - bool supports_unlink(const char *path) override - { - if (verbose) - Genode::log(__func__, ": path=", path); - return true; - } - - bool supports_symlink(const char *, const char *) override - { - return true; - } - - int close(Libc::File_descriptor *fd) override - { - using namespace Fatfs; - - FIL *fatfs_file = _get_fatfs_file(fd); - - if (!fatfs_file){ - /* directory */ - Genode::destroy(&*_heap, context(fd)); - Libc::file_descriptor_allocator()->free(fd); - return 0; - } - - FRESULT res = f_close(fatfs_file); - - Genode::destroy(&*_heap, context(fd)); - Libc::file_descriptor_allocator()->free(fd); - - switch(res) { - case FR_OK: - return 0; - case FR_DISK_ERR: - case FR_INT_ERR: - case FR_NOT_READY: - case FR_INVALID_OBJECT: - errno = EIO; - return -1; - default: - /* not supposed to occur according to the fatfs documentation */ - Genode::error("f_close() returned an unexpected error code"); - return -1; - } - } - - int fcntl(Libc::File_descriptor *fd, int cmd, long arg) override - { - switch (cmd) { - case F_GETFD: return context(fd)->fd_flags(); - case F_SETFD: context(fd)->fd_flags(arg); return 0; - case F_GETFL: return context(fd)->status_flags(); - default: Genode::error("fcntl(): command ", cmd, " not supported", cmd); return -1; - } - } - - int fstat(Libc::File_descriptor *fd, struct stat *buf) override - { - return stat(context(fd)->filename(), buf); - } - - int fstatfs(Libc::File_descriptor *, struct statfs *buf) override - { - /* libc's opendir() fails if _fstatfs() returns -1, so we return 0 here */ - if (verbose) - Genode::warning("_fstatfs() called - not yet implemented"); - return 0; - } - - int fsync(Libc::File_descriptor *fd) override - { - using namespace Fatfs; - - FRESULT res = f_sync(_get_fatfs_file(fd)); - - switch(res) { - case FR_OK: - return 0; - case FR_DISK_ERR: - case FR_INT_ERR: - case FR_NOT_READY: - case FR_INVALID_OBJECT: - errno = EIO; - return -1; - default: - /* not supposed to occur according to the fatfs documentation */ - Genode::error("f_sync() returned an unexpected error code"); - return -1; - } - } - - int ftruncate(Libc::File_descriptor *fd, ::off_t length) override - { - using namespace Fatfs; - - /* 'f_truncate()' truncates to the current seek pointer */ - - if (lseek(fd, length, SEEK_SET) == -1) - return -1; - - FRESULT res = f_truncate(_get_fatfs_file(fd)); - - switch(res) { - case FR_OK: - return 0; - case FR_DISK_ERR: - case FR_INT_ERR: - case FR_NOT_READY: - case FR_INVALID_OBJECT: - errno = EIO; - return -1; - default: - /* not supposed to occur according to the fatfs documentation */ - Genode::error("f_truncate() returned an unexpected error code"); - return -1; - } - } - - ssize_t getdirentries(Libc::File_descriptor *fd, char *buf, - ::size_t nbytes, ::off_t *basep) override - { - using namespace Fatfs; - - if (nbytes < sizeof(struct dirent)) { - Genode::error(__func__, ": buf too small"); - errno = ENOMEM; - return -1; - } - - struct dirent *dirent = (struct dirent *)buf; - ::memset(dirent, 0, sizeof(struct dirent)); - - FILINFO fatfs_file_info; - - FRESULT res = f_readdir(_get_fatfs_dir(fd), &fatfs_file_info); - switch(res) { - case FR_OK: - break; - case FR_DISK_ERR: - case FR_INT_ERR: - case FR_NOT_READY: - case FR_INVALID_OBJECT: - errno = EIO; - return -1; - default: - /* not supposed to occur according to the fatfs documentation */ - Genode::error("f_readdir() returned an unexpected error code"); - return -1; - } - - if (fatfs_file_info.fname[0] == 0) { /* no (more) entries */ - if (verbose) - Genode::log(__func__, ": no more dir entries"); - /* TODO: reset the f_readdir() index? */ - return 0; - } - - dirent->d_ino = 1; /* libc's readdir() wants an inode number */ - - if ((fatfs_file_info.fattrib & AM_DIR) == AM_DIR) - dirent->d_type = DT_DIR; - else - dirent->d_type = DT_REG; - - dirent->d_reclen = sizeof(struct dirent); - - ::strncpy(dirent->d_name, fatfs_file_info.fname, sizeof(dirent->d_name)); - - dirent->d_namlen = ::strlen(dirent->d_name); - - if (verbose) - Genode::log("found dir entry ", Genode::Cstring(dirent->d_name)); - - *basep += sizeof(struct dirent); - return sizeof(struct dirent); - } - - ::off_t lseek(Libc::File_descriptor *fd, ::off_t offset, int whence) override - { - using namespace Fatfs; - - switch(whence) { - case SEEK_CUR: - offset += f_tell(_get_fatfs_file(fd)); - break; - case SEEK_END: - offset += f_size(_get_fatfs_file(fd)); - break; - default: - break; - } - - FRESULT res = f_lseek(_get_fatfs_file(fd), offset); - - switch(res) { - case FR_OK: - /* according to the FatFs documentation this can happen */ - if ((off_t)f_tell(_get_fatfs_file(fd)) != offset) { - errno = EINVAL; - return -1; - } - return offset; - case FR_DISK_ERR: - case FR_INT_ERR: - case FR_NOT_READY: - case FR_INVALID_OBJECT: - errno = EIO; - return -1; - default: - /* not supposed to occur according to the fatfs documentation */ - Genode::error("f_lseek() returned an unexpected error code"); - return -1; - } - } - - int mkdir(const char *path, mode_t mode) override - { - using namespace Fatfs; - - FRESULT res = f_mkdir(path); - - switch(res) { - case FR_OK: - return 0; - case FR_NO_PATH: - case FR_INVALID_NAME: - case FR_INVALID_DRIVE: - errno = ENOENT; - return -1; - case FR_DENIED: - case FR_WRITE_PROTECTED: - errno = EACCES; - return -1; - case FR_EXIST: - errno = EEXIST; - return -1; - case FR_NOT_READY: - case FR_DISK_ERR: - case FR_INT_ERR: - case FR_NOT_ENABLED: - case FR_NO_FILESYSTEM: - errno = EIO; - return -1; - default: - /* not supposed to occur according to the fatfs documentation */ - Genode::error("f_mkdir() returned an unexpected error code"); - return -1; - } - } - - Libc::File_descriptor *open(const char *pathname, int flags) override - { - using namespace Fatfs; - - if (verbose) - Genode::log(__func__, ": pathname=", pathname); - - FIL fatfs_file; - BYTE fatfs_flags = 0; - - /* convert libc flags to fatfs flags */ - if (((flags & O_RDONLY) == O_RDONLY) || ((flags & O_RDWR) == O_RDWR)) - fatfs_flags |= FA_READ; - - if (((flags & O_WRONLY) == O_WRONLY) || ((flags & O_RDWR) == O_RDWR)) - fatfs_flags |= FA_WRITE; - - if ((flags & O_CREAT) == O_CREAT) { - if ((flags & O_EXCL) == O_EXCL) - fatfs_flags |= FA_CREATE_NEW; - else - fatfs_flags |= FA_OPEN_ALWAYS; - } - - FRESULT res = f_open(&fatfs_file, pathname, fatfs_flags); - - switch(res) { - case FR_OK: { - Plugin_context *context = new (&*_heap) - File_plugin_context(pathname, fatfs_file); - context->status_flags(flags); - Libc::File_descriptor *fd = Libc::file_descriptor_allocator()->alloc(this, context); - if ((flags & O_TRUNC) && (ftruncate(fd, 0) == -1)) - return 0; - return fd; - } - case FR_NO_FILE: { - /* - * libc's opendir() calls open() on directories, but - * that's not supported by f_open(). So we call - * f_opendir() in case the file is a directory. - */ - Fatfs::DIR fatfs_dir; - FRESULT f_opendir_res = f_opendir(&fatfs_dir, pathname); - if (verbose) - Genode::log(__func__, ": opendir res=", (int)f_opendir_res); - switch(f_opendir_res) { - case FR_OK: { - Plugin_context *context = new (&*_heap) - Directory_plugin_context(pathname, fatfs_dir); - context->status_flags(flags); - Libc::File_descriptor *f = - Libc::file_descriptor_allocator()->alloc(this, context); - if (verbose) - Genode::log(__func__, ": new fd=", f->libc_fd); - return f; - - } - case FR_NO_PATH: - case FR_INVALID_NAME: - case FR_INVALID_DRIVE: - errno = ENOENT; - return 0; - case FR_NOT_READY: - case FR_DISK_ERR: - case FR_INT_ERR: - case FR_NOT_ENABLED: - case FR_NO_FILESYSTEM: - errno = EIO; - return 0; - default: - /* not supposed to occur according to the fatfs documentation */ - Genode::error("f_opendir() returned an unexpected error code"); - return 0; - } - } - case FR_NO_PATH: - case FR_INVALID_NAME: - case FR_INVALID_DRIVE: - errno = ENOENT; - return 0; - case FR_EXIST: - errno = EEXIST; - return 0; - case FR_DENIED: - case FR_WRITE_PROTECTED: - errno = EACCES; - return 0; - case FR_NOT_READY: - case FR_DISK_ERR: - case FR_INT_ERR: - case FR_NOT_ENABLED: - case FR_NO_FILESYSTEM: - errno = EIO; - return 0; - default: - /* not supposed to occur according to the fatfs documentation */ - Genode::error("f_open() returned an unexpected error code"); - return 0; - } - } - - int rename(const char *oldpath, const char *newpath) override - { - using namespace Fatfs; - - FRESULT res = f_rename(oldpath, newpath); - - /* if newpath already exists - try to unlink it once */ - if (res == FR_EXIST) { - f_unlink(newpath); - res = f_rename(oldpath, newpath); - } - - switch(res) { - case FR_OK: - return 0; - case FR_NO_FILE: - case FR_NO_PATH: - case FR_INVALID_NAME: - case FR_INVALID_DRIVE: - errno = ENOENT; - return 0; - case FR_EXIST: - errno = EEXIST; - return -1; - case FR_DENIED: - case FR_WRITE_PROTECTED: - errno = EACCES; - return -1; - case FR_DISK_ERR: - case FR_INT_ERR: - case FR_NOT_READY: - case FR_NOT_ENABLED: - case FR_NO_FILESYSTEM: - errno = EIO; - return -1; - default: - /* not supposed to occur according to the fatfs documentation */ - Genode::error("f_rename() returned an unexpected error code"); - return -1; - } - } - - ssize_t read(Libc::File_descriptor *fd, void *buf, ::size_t count) override - { - using namespace Fatfs; - - UINT result; - FRESULT res = f_read(_get_fatfs_file(fd), buf, count, &result); - - switch(res) { - case FR_OK: - return result; - case FR_DENIED: - errno = EACCES; - return -1; - case FR_DISK_ERR: - case FR_INT_ERR: - case FR_NOT_READY: - case FR_INVALID_OBJECT: - errno = EIO; - return -1; - default: - /* not supposed to occur according to the fatfs documentation */ - Genode::error("f_read() returned an unexpected error code"); - return -1; - } - } - - int stat(const char *path, struct stat *buf) override - { - using namespace Fatfs; - - FILINFO file_info; - - ::memset(buf, 0, sizeof(struct stat)); - - /* 'f_stat()' does not work for the '/' directory */ - if (strcmp(path, "/") == 0) { - buf->st_mode |= S_IFDIR; - return 0; - } - - FRESULT res = f_stat(path, &file_info); - - switch(res) { - case FR_OK: - break; - case FR_NO_FILE: - case FR_NO_PATH: - case FR_INVALID_NAME: - case FR_INVALID_DRIVE: - errno = ENOENT; - return -1; - case FR_DISK_ERR: - case FR_INT_ERR: - case FR_NOT_READY: - case FR_NOT_ENABLED: - case FR_NO_FILESYSTEM: - errno = EIO; - return -1; - default: - /* not supposed to occur according to the fatfs documentation */ - Genode::error("f_stat() returned an unexpected error code"); - return -1; - } - - /* convert FILINFO to struct stat */ - buf->st_size = file_info.fsize; - - if ((file_info.fattrib & AM_DIR) == AM_DIR) { - buf->st_mode |= S_IFDIR; - if (verbose) - Genode::log(__func__, ": type: directory"); - } else { - buf->st_mode |= S_IFREG; - if (verbose) - Genode::log(__func__, ": type: regular file with a " - "size of ", buf->st_size, " bytes"); - } - /* TODO: handle more attributes */ - - struct tm tm; - ::memset(&tm, 0, sizeof(tm)); - - tm.tm_year = ((file_info.fdate & 0b1111111000000000) >> 9) + 80; - tm.tm_mon = (file_info.fdate & 0b0000000111100000) >> 5; - tm.tm_mday = (file_info.fdate & 0b0000000000011111); - tm.tm_hour = (file_info.ftime & 0b1111100000000000) >> 11; - tm.tm_min = (file_info.ftime & 0b0000011111100000) >> 5; - tm.tm_sec = (file_info.ftime & 0b0000000000011111) * 2; - - if (verbose) - Genode::log("last modified: ", - 1900 + tm.tm_year, "-", tm.tm_mon, "-", tm.tm_mday, " ", - tm.tm_hour, ":", tm.tm_min, ":", tm.tm_sec); - - buf->st_mtime = mktime(&tm); - if (buf->st_mtime == -1) - Genode::error("mktime() returned -1, the file modification time reported by stat() will be incorrect"); - - return 0; - } - - int unlink(const char *path) override - { - using namespace Fatfs; - - FRESULT res = f_unlink(path); - - switch(res) { - case FR_OK: - return 0; - case FR_NO_FILE: - case FR_NO_PATH: - case FR_INVALID_NAME: - case FR_INVALID_DRIVE: - errno = ENOENT; - return -1; - case FR_DENIED: - case FR_WRITE_PROTECTED: - errno = EACCES; - return -1; - case FR_DISK_ERR: - case FR_INT_ERR: - case FR_NOT_READY: - case FR_NOT_ENABLED: - case FR_NO_FILESYSTEM: - errno = EIO; - return -1; - default: - /* not supposed to occur according to the fatfs documentation */ - Genode::error("f_unlink() returned an unexpected error code"); - return -1; - } - } - - int rmdir(const char *path) override - { - return unlink(path); - } - - ssize_t write(Libc::File_descriptor *fd, const void *buf, ::size_t count) override - { - using namespace Fatfs; - - UINT result; - FRESULT res = f_write(_get_fatfs_file(fd), buf, count, &result); - - switch(res) { - case FR_OK: - return result; - case FR_DENIED: - errno = EACCES; - return -1; - case FR_DISK_ERR: - case FR_INT_ERR: - case FR_NOT_READY: - case FR_INVALID_OBJECT: - errno = EIO; - return -1; - default: - /* not supposed to occur according to the fatfs documentation */ - Genode::error("f_write() returned an unexpected error code"); - return -1; - } - } - - int symlink(const char *, const char *) override - { - errno = EPERM; - return -1; - } -}; - - -} /* unnamed namespace */ - - -void __attribute__((constructor)) init_libc_fatfs(void) -{ - static Plugin plugin; -} diff --git a/repos/libports/src/server/fatfs_fs/directory.h b/repos/libports/src/server/fatfs_fs/directory.h deleted file mode 100644 index 656743146..000000000 --- a/repos/libports/src/server/fatfs_fs/directory.h +++ /dev/null @@ -1,123 +0,0 @@ -/* - * \brief FATFS file-system directory node - * \author Christian Prochaska - * \date 2012-07-04 - */ - -/* - * Copyright (C) 2012-2017 Genode Labs GmbH - * - * This file is part of the Genode OS framework, which is distributed - * under the terms of the GNU Affero General Public License version 3. - */ - -#ifndef _DIRECTORY_H_ -#define _DIRECTORY_H_ - -/* fatfs includes */ -namespace Fatfs { extern "C" { -#include -} } - -/* local includes */ -#include - - -namespace Fatfs_fs { - using namespace Genode; - class Directory; -} - -class Fatfs_fs::Directory : public Node -{ - private: - - Fatfs::DIR _fatfs_dir; - int64_t _prev_index; - - public: - - Directory(const char *name) - : Node(name), - _prev_index(-1) { } - - void fatfs_dir(Fatfs::DIR fatfs_dir) { _fatfs_dir = fatfs_dir; } - Fatfs::DIR *fatfs_dir() { return &_fatfs_dir; } - - size_t read(char *dst, size_t len, seek_off_t seek_offset) - { - if (len < sizeof(Directory_entry)) { - error("read buffer too small for directory entry"); - return 0; - } - - if (seek_offset % sizeof(Directory_entry)) { - error("seek offset not alighed to sizeof(Directory_entry)"); - return 0; - } - - using namespace Fatfs; - - FILINFO fatfs_file_info; - - int64_t index = seek_offset / sizeof(Directory_entry); - - if (index != (_prev_index + 1)) { - /* rewind and iterate from the beginning */ - f_readdir(&_fatfs_dir, 0); - for (int i = 0; i < index; i++) - f_readdir(&_fatfs_dir, &fatfs_file_info); - } - - _prev_index = index; - - FRESULT res = f_readdir(&_fatfs_dir, &fatfs_file_info); - switch(res) { - case FR_OK: - break; - case FR_INVALID_OBJECT: - error("f_readdir() failed with error code FR_INVALID_OBJECT"); - return 0; - case FR_DISK_ERR: - error("f_readdir() failed with error code FR_DISK_ERR"); - return 0; - case FR_INT_ERR: - error("f_readdir() failed with error code FR_INT_ERR"); - return 0; - case FR_NOT_READY: - error("f_readdir() failed with error code FR_NOT_READY"); - return 0; - default: - /* not supposed to occur according to the libfatfs documentation */ - error("f_readdir() returned an unexpected error code"); - return 0; - } - - if (fatfs_file_info.fname[0] == 0) { /* no (more) entries */ - return 0; - } - - Directory_entry &e = *(Directory_entry *)(dst); - e = { - .inode = 0, - .type = ((fatfs_file_info.fattrib & AM_DIR) == AM_DIR) - ? Node_type::DIRECTORY - : Node_type::CONTINUOUS_FILE, - .rwx = { .readable = true, - .writeable = true, - .executable = true }, - .name = { fatfs_file_info.fname } - }; - - return sizeof(Directory_entry); - } - - size_t write(char const *src, size_t len, seek_off_t) - { - /* writing to directory nodes is not supported */ - return 0; - } - -}; - -#endif /* _DIRECTORY_H_ */ diff --git a/repos/libports/src/server/fatfs_fs/file.h b/repos/libports/src/server/fatfs_fs/file.h deleted file mode 100644 index 1d30948c8..000000000 --- a/repos/libports/src/server/fatfs_fs/file.h +++ /dev/null @@ -1,266 +0,0 @@ -/* - * \brief FATFS file-system file node - * \author Christian Prochaska - * \date 2012-07-04 - */ - -/* - * Copyright (C) 2012-2017 Genode Labs GmbH - * - * This file is part of the Genode OS framework, which is distributed - * under the terms of the GNU Affero General Public License version 3. - */ - -#ifndef _FILE_H_ -#define _FILE_H_ - -/* fatfs includes */ -namespace Fatfs { extern "C" { -#include -} } - -/* local includes */ -#include - - -namespace Fatfs_fs { - class File; -} - -class Fatfs_fs::File : public Node -{ - private: - - Fatfs::FIL _fatfs_fil; - - public: - - File(const char *name) : Node(name) { } - - ~File() - { - using namespace Fatfs; - - FRESULT res = f_close(&_fatfs_fil); - - switch(res) { - case FR_OK: - return; - case FR_INVALID_OBJECT: - error("f_close() failed with error code FR_INVALID_OBJECT"); - return; - case FR_DISK_ERR: - error("f_close() failed with error code FR_DISK_ERR"); - return; - case FR_INT_ERR: - error("f_close() failed with error code FR_INT_ERR"); - return; - case FR_NOT_READY: - error("f_close() failed with error code FR_NOT_READY"); - return; - default: - /* not supposed to occur according to the fatfs documentation */ - error("f_close() returned an unexpected error code"); - return; - } - } - - void fatfs_fil(Fatfs::FIL fatfs_fil) { _fatfs_fil = fatfs_fil; } - Fatfs::FIL *fatfs_fil() { return &_fatfs_fil; } - - size_t read(char *dst, size_t len, seek_off_t seek_offset) override - { - using namespace Fatfs; - - UINT result; - - if (seek_offset == (seek_off_t)(~0)) { - FILINFO file_info; - f_stat(name(), &file_info); - - seek_offset = file_info.fsize; - } - - FRESULT res = f_lseek(&_fatfs_fil, seek_offset); - - switch(res) { - case FR_OK: - break; - case FR_INVALID_OBJECT: - Genode::error("f_lseek() failed with error code FR_INVALID_OBJECT"); - return 0; - case FR_DISK_ERR: - Genode::error("f_lseek() failed with error code FR_DISK_ERR"); - return 0; - case FR_INT_ERR: - Genode::error("f_lseek() failed with error code FR_INT_ERR"); - return 0; - case FR_NOT_READY: - Genode::error("f_lseek() failed with error code FR_NOT_READY"); - return 0; - default: - /* not supposed to occur according to the fatfs documentation */ - Genode::error("f_lseek() returned an unexpected error code"); - return 0; - } - - res = f_read(&_fatfs_fil, dst, len, &result); - - switch(res) { - case FR_OK: - return result; - case FR_DENIED: - Genode::warning("f_read() failed with error code FR_DENIED"); - return 0; - case FR_INVALID_OBJECT: - Genode::error("f_read() failed with error code FR_INVALID_OBJECT"); - return 0; - case FR_DISK_ERR: - Genode::error("f_read() failed with error code FR_DISK_ERR"); - return 0; - case FR_INT_ERR: - Genode::error("f_read() failed with error code FR_INT_ERR"); - return 0; - case FR_NOT_READY: - Genode::error("f_read() failed with error code FR_NOT_READY"); - return 0; - default: - /* not supposed to occur according to the fatfs documentation */ - Genode::error("f_read() returned an unexpected error code"); - return 0; - } - } - - size_t write(char const *src, size_t len, seek_off_t seek_offset) override - { - using namespace Fatfs; - - UINT result; - - if (seek_offset == (seek_off_t)(~0)) { - FILINFO file_info; - f_stat(name(), &file_info); - - seek_offset = file_info.fsize; - } - - FRESULT res = f_lseek(&_fatfs_fil, seek_offset); - - switch(res) { - case FR_OK: - break; - case FR_INVALID_OBJECT: - Genode::error("f_lseek() failed with error code FR_INVALID_OBJECT"); - return 0; - case FR_DISK_ERR: - Genode::error("f_lseek() failed with error code FR_DISK_ERR"); - return 0; - case FR_INT_ERR: - Genode::error("f_lseek() failed with error code FR_INT_ERR"); - return 0; - case FR_NOT_READY: - Genode::error("f_lseek() failed with error code FR_NOT_READY"); - return 0; - default: - /* not supposed to occur according to the fatfs documentation */ - Genode::error("f_lseek() returned an unexpected error code"); - return 0; - } - - res = f_write(&_fatfs_fil, src, len, &result); - - switch(res) { - case FR_OK: - return result; - case FR_DENIED: - Genode::error("f_write() failed with error code FR_DENIED"); - return 0; - case FR_INVALID_OBJECT: - Genode::error("f_write() failed with error code FR_INVALID_OBJECT"); - return 0; - case FR_DISK_ERR: - Genode::error("f_write() failed with error code FR_DISK_ERR"); - return 0; - case FR_INT_ERR: - Genode::error("f_write() failed with error code FR_INT_ERR"); - return 0; - case FR_NOT_READY: - Genode::error("f_write() failed with error code FR_NOT_READY"); - return 0; - default: - /* not supposed to occur according to the fatfs documentation */ - Genode::error("f_write() returned an unexpected error code"); - return 0; - } - } - - void truncate(file_size_t size) override - { - using namespace Fatfs; - - /* - * This macro is defined in later versions of the FatFs lib, but not in the - * one currently used for Genode. - */ - #define f_tell(fp) ((fp)->fptr) - - /* 'f_truncate()' truncates to the current seek pointer */ - - FRESULT res = f_lseek(&_fatfs_fil, size); - - switch(res) { - case FR_OK: - /* according to the FatFs documentation this can happen */ - if (f_tell(&_fatfs_fil) != size) { - error("f_lseek() could not seek to offset ", size); - return; - } - break; - case FR_DISK_ERR: - error("f_lseek() failed with error code FR_DISK_ERR"); - return; - case FR_INT_ERR: - error("f_lseek() failed with error code FR_INT_ERR"); - return; - case FR_NOT_READY: - error("f_lseek() failed with error code FR_NOT_READY"); - return; - case FR_INVALID_OBJECT: - error("f_lseek() failed with error code FR_INVALID_OBJECT"); - throw Invalid_handle(); - default: - /* not supposed to occur according to the fatfs documentation */ - error("f_lseek() returned an unexpected error code"); - return; - } - - res = f_truncate(&_fatfs_fil); - - switch(res) { - case FR_OK: - return; - case FR_INVALID_OBJECT: - error("f_truncate() failed with error code FR_INVALID_OBJECT"); - throw Invalid_handle(); - case FR_DISK_ERR: - error("f_truncate() failed with error code FR_DISK_ERR"); - return; - case FR_INT_ERR: - error("f_truncate() failed with error code FR_INT_ERR"); - return; - case FR_NOT_READY: - error("f_truncate() failed with error code FR_NOT_READY"); - return; - case FR_TIMEOUT: - error("f_truncate() failed with error code FR_TIMEOUT"); - return; - default: - /* not supposed to occur according to the fatfs documentation */ - error("f_truncate() returned an unexpected error code"); - return; - } - } - -}; - -#endif /* _FILE_H_ */ diff --git a/repos/libports/src/server/fatfs_fs/main.cc b/repos/libports/src/server/fatfs_fs/main.cc deleted file mode 100644 index 888f51b53..000000000 --- a/repos/libports/src/server/fatfs_fs/main.cc +++ /dev/null @@ -1,1004 +0,0 @@ -/* - * \brief FATFS file system - * \author Christian Prochaska - * \date 2012-07-03 - */ - -/* - * Copyright (C) 2012-2017 Genode Labs GmbH - * - * This file is part of the Genode OS framework, which is distributed - * under the terms of the GNU Affero General Public License version 3. - */ - -/* Genode includes */ -#include -#include -#include -#include -#include -#include -#include -#include - -/* local includes */ -#include -#include -#include -#include - -/* Genode block backend */ -#include - -/* fatfs includes */ -namespace Fatfs { extern "C" { -#include -} } - - -/************************* - ** File-system service ** - *************************/ - -namespace Fatfs_fs { - - using namespace Genode; - using File_system::Exception; - using File_system::Packet_descriptor; - using File_system::Path; - - class Session_component; - class Root; - struct Main; -} - -class Fatfs_fs::Session_component : public Session_rpc_object -{ - private: - - typedef File_system::Open_node Open_node; - - Genode::Env &_env; - Genode::Allocator &_heap; - - Directory &_root; - Id_space _open_node_registry; - bool _writable; - - Signal_handler _process_packet_dispatcher; - - /****************************** - ** Packet-stream processing ** - ******************************/ - - /** - * Perform packet operation - * - * \return true on success, false on failure - */ - void _process_packet_op(Packet_descriptor &packet, Open_node &open_node) - { - void * const content = tx_sink()->packet_content(packet); - size_t const length = packet.length(); - seek_off_t const offset = packet.position(); - - /* resulting length */ - size_t res_length = 0; - bool succeeded = false; - - switch (packet.operation()) { - - case Packet_descriptor::READ: - if (content && (packet.length() <= packet.size())) { - res_length = open_node.node().read((char *)content, length, - offset); - - /* read data or EOF is a success */ - succeeded = res_length > 0; - if (!succeeded) { - File * file = dynamic_cast(&open_node.node()); - if (file) - succeeded = f_eof((file->fatfs_fil())); - } - } - break; - - case Packet_descriptor::WRITE: - if (content && (packet.length() <= packet.size())) { - res_length = open_node.node().write((char const *)content, - length, offset); - - /* File system session can't handle partial writes */ - if (res_length != length) { - Genode::error("partial write detected ", - res_length, " vs ", length); - /* don't acknowledge */ - return; - } - succeeded = true; - } - break; - - case Packet_descriptor::CONTENT_CHANGED: - open_node.register_notify(*tx_sink()); - open_node.node().notify_listeners(); - return; - - case Packet_descriptor::READ_READY: - succeeded = true; - /* not supported */ - break; - - case Packet_descriptor::SYNC: - succeeded = true; - /* not supported */ - break; - - case Packet_descriptor::WRITE_TIMESTAMP: - succeeded = false; - break; - } - - packet.length(res_length); - packet.succeeded(succeeded); - - tx_sink()->acknowledge_packet(packet); - } - - void _process_packet() - { - Packet_descriptor packet = tx_sink()->get_packet(); - - /* assume failure by default */ - packet.succeeded(false); - - auto process_packet_fn = [&] (Open_node &open_node) { - _process_packet_op(packet, open_node); - }; - - try { - _open_node_registry.apply(packet.handle(), process_packet_fn); - } catch (Id_space::Unknown_id const &) { - Genode::error("Invalid_handle"); - } - } - - /** - * Called by signal dispatcher, executed in the context of the main - * thread (not serialized with the RPC functions) - */ - void _process_packets() - { - while (tx_sink()->packet_avail()) { - - /* - * Make sure that the '_process_packet' function does not - * block. - * - * If the acknowledgement queue is full, we defer packet - * processing until the client processed pending - * acknowledgements and thereby emitted a ready-to-ack - * signal. Otherwise, the call of 'acknowledge_packet()' - * in '_process_packet' would infinitely block the context - * of the main thread. The main thread is however needed - * for receiving any subsequent 'ready-to-ack' signals. - */ - if (!tx_sink()->ready_to_ack()) - return; - - _process_packet(); - } - } - - /** - * Check if string represents a valid path (most start with '/') - */ - static void _assert_valid_path(char const *path) - { - if (!valid_path(path)) { - warning("malformed path '", path, "'"); - throw Lookup_failed(); - } - } - - public: - - /** - * Constructor - */ - Session_component(Genode::Env &env, - Genode::Allocator &heap, - size_t tx_buf_size, - Directory &root, - bool writable) - : - Session_rpc_object(env.ram().alloc(tx_buf_size), - env.rm(), env.ep().rpc_ep()), - _env(env), _heap(heap), _root(root), _writable(writable), - _process_packet_dispatcher(env.ep(), *this, - &Session_component::_process_packets) - { - /* - * Register '_process_packets' dispatch function as signal - * handler for packet-avail and ready-to-ack signals. - */ - _tx.sigh_packet_avail(_process_packet_dispatcher); - _tx.sigh_ready_to_ack(_process_packet_dispatcher); - } - - /** - * Destructor - */ - ~Session_component() - { - Dataspace_capability ds = tx_sink()->dataspace(); - _env.ram().free(static_cap_cast(ds)); - } - - /*************************** - ** File_system interface ** - ***************************/ - - File_handle file(Dir_handle dir_handle, Name const &name, - Mode mode, bool create) - { - if (!valid_filename(name.string())) - throw Invalid_name(); - - auto file_fn = [&] (Open_node &open_node) { - - using namespace Fatfs; - - FIL fatfs_fil; - BYTE fatfs_flags = 0; - - if (!_writable) - if (create || (mode != STAT_ONLY && mode != READ_ONLY)) - throw Permission_denied(); - - if (create) - fatfs_flags |= FA_CREATE_NEW; - - if ((mode == READ_ONLY) || (mode == READ_WRITE)) - fatfs_flags |= FA_READ; - - if ((mode == WRITE_ONLY) || (mode == READ_WRITE)) - fatfs_flags |= FA_WRITE; - - Absolute_path absolute_path(_root.name()); - - try { - absolute_path.append(open_node.node().name()); - absolute_path.append("/"); - absolute_path.append(name.string()); - } catch (Path_base::Path_too_long) { - throw Invalid_name(); - } - - FRESULT res = f_open(&fatfs_fil, absolute_path.base(), fatfs_flags); - - switch(res) { - case FR_OK: { - File *file_node = new (&_heap) File(absolute_path.base()); - file_node->fatfs_fil(fatfs_fil); - - Open_node *open_file = - new (_heap) Open_node(*file_node, _open_node_registry); - - return open_file->id(); - } - case FR_NO_FILE: - case FR_NO_PATH: - throw Lookup_failed(); - case FR_INVALID_NAME: - case FR_INVALID_DRIVE: - throw Invalid_name(); - case FR_EXIST: - throw Node_already_exists(); - case FR_DENIED: - case FR_WRITE_PROTECTED: - throw Permission_denied(); - case FR_NOT_READY: - error("f_open() failed with error code FR_NOT_READY"); - throw Lookup_failed(); - case FR_DISK_ERR: - error("f_open() failed with error code FR_DISK_ERR"); - throw Lookup_failed(); - case FR_INT_ERR: - error("f_open() failed with error code FR_INT_ERR"); - throw Lookup_failed(); - case FR_NOT_ENABLED: - error("f_open() failed with error code FR_NOT_ENABLED"); - throw Lookup_failed(); - case FR_NO_FILESYSTEM: - error("f_open() failed with error code FR_NO_FILESYSTEM"); - throw Lookup_failed(); - default: - /* not supposed to occur according to the fatfs documentation */ - error("f_open() returned an unexpected error code"); - throw Lookup_failed(); - } - }; - - try { - return File_handle { - _open_node_registry.apply(dir_handle, file_fn).value - }; - } catch (Id_space::Unknown_id const &) { - throw Invalid_handle(); - } - } - - Symlink_handle symlink(Dir_handle, Name const &name, bool create) - { - /* not supported */ - throw Permission_denied(); - } - - Dir_handle dir(Path const &path, bool create) - { - if (create && !_writable) - throw Permission_denied(); - - _assert_valid_path(path.string()); - - /* - * The 'Directory' constructor removes trailing slashes, - * except for "/" - */ - Directory *dir_node = new (&_heap) Directory(path.string()); - - using namespace Fatfs; - - Absolute_path absolute_path(_root.name()); - - try { - absolute_path.append(dir_node->name()); - absolute_path.remove_trailing('/'); - } catch (Path_base::Path_too_long) { - throw Name_too_long(); - } - - if (create) { - - if (is_root(dir_node->name())) - throw Node_already_exists(); - - FRESULT res = f_mkdir(absolute_path.base()); - - try { - switch(res) { - case FR_OK: - break; - case FR_NO_PATH: - throw Lookup_failed(); - case FR_INVALID_NAME: - throw Name_too_long(); - case FR_INVALID_DRIVE: - throw Name_too_long(); - case FR_DENIED: - case FR_WRITE_PROTECTED: - throw Permission_denied(); - case FR_EXIST: - throw Node_already_exists(); - case FR_NOT_READY: - error("f_mkdir() failed with error code FR_NOT_READY"); - throw Lookup_failed(); - case FR_DISK_ERR: - error("f_mkdir() failed with error code FR_DISK_ERR"); - throw Lookup_failed(); - case FR_INT_ERR: - error("f_mkdir() failed with error code FR_INT_ERR"); - throw Lookup_failed(); - case FR_NOT_ENABLED: - error("f_mkdir() failed with error code FR_NOT_ENABLED"); - throw Lookup_failed(); - case FR_NO_FILESYSTEM: - error("f_mkdir() failed with error code FR_NO_FILESYSTEM"); - throw Lookup_failed(); - default: - /* not supposed to occur according to the fatfs documentation */ - error("f_mkdir() returned an unexpected error code"); - throw Lookup_failed(); - } - } catch (Exception e) { - destroy(&_heap, dir_node); - throw e; - } - } - - Fatfs::DIR fatfs_dir; - FRESULT f_opendir_res = f_opendir(&fatfs_dir, absolute_path.base()); - - try { - switch(f_opendir_res) { - case FR_OK: { - dir_node->fatfs_dir(fatfs_dir); - - Open_node *open_dir = - new (_heap) Open_node(*dir_node, _open_node_registry); - - return Dir_handle { open_dir->id().value }; - } - case FR_NO_PATH: - throw Lookup_failed(); - case FR_INVALID_NAME: - throw Name_too_long(); - case FR_INVALID_DRIVE: - throw Name_too_long(); - case FR_NOT_READY: - error("f_opendir() failed with error code FR_NOT_READY"); - throw Lookup_failed(); - case FR_DISK_ERR: - error("f_opendir() failed with error code FR_DISK_ERR"); - throw Lookup_failed(); - case FR_INT_ERR: - error("f_opendir() failed with error code FR_INT_ERR"); - throw Lookup_failed(); - case FR_NOT_ENABLED: - error("f_opendir() failed with error code FR_NOT_ENABLED"); - throw Lookup_failed(); - case FR_NO_FILESYSTEM: - error("f_opendir() failed with error code FR_NO_FILESYSTEM"); - throw Lookup_failed(); - default: - /* not supposed to occur according to the fatfs documentation */ - error("f_opendir() returned an unexpected error code"); - throw Lookup_failed(); - } - } catch (Exception e) { - destroy(&_heap, dir_node); - throw e; - } - } - - Node_handle node(Path const &path) - { - if (!valid_path(path.string())) - throw Lookup_failed(); - - Absolute_path absolute_path(_root.name()); - - try { - absolute_path.append(path.string()); - absolute_path.remove_trailing('/'); - } catch (Path_base::Path_too_long) { - throw Lookup_failed(); - } - - Node *node = new (&_heap) Node(absolute_path.base()); - - /* f_stat() does not work for "/" */ - if (!is_root(node->name())) { - - using namespace Fatfs; - - FILINFO file_info; - - FRESULT res = f_stat(node->name(), &file_info); - - try { - switch(res) { - case FR_OK: - break; - case FR_NO_FILE: - case FR_NO_PATH: - throw Lookup_failed(); - case FR_INVALID_NAME: - case FR_INVALID_DRIVE: - throw Lookup_failed(); - case FR_DISK_ERR: - error("f_stat() failed with error code FR_DISK_ERR"); - throw Lookup_failed(); - case FR_INT_ERR: - error("f_stat() failed with error code FR_INT_ERR"); - throw Lookup_failed(); - case FR_NOT_READY: - error("f_stat() failed with error code FR_NOT_READY"); - throw Lookup_failed(); - case FR_NOT_ENABLED: - error("f_stat() failed with error code FR_NOT_ENABLED"); - throw Lookup_failed(); - case FR_NO_FILESYSTEM: - error("f_stat() failed with error code FR_NO_FILESYSTEM"); - throw Lookup_failed(); - default: - /* not supposed to occur according to the fatfs documentation */ - error("f_stat() returned an unexpected error code"); - throw Lookup_failed(); - } - } catch (Exception e) { - destroy(&_heap, node); - throw e; - } - } - - Open_node *open_node = - new (_heap) Open_node(*node, _open_node_registry); - - return open_node->id(); - } - - void close(Node_handle handle) - { - auto close_fn = [&] (Open_node &open_node) { - Node &node = open_node.node(); - destroy(_heap, &open_node); - destroy(_heap, &node); - }; - - try { - _open_node_registry.apply(handle, close_fn); - } catch (Id_space::Unknown_id const &) { - throw Invalid_handle(); - } - } - - Status status(Node_handle node_handle) - { - auto status_fn = [&] (Open_node &open_node) { - - Status status; - status.inode = 1; - status.size = 0; - status.rwx = { .readable = true, - .writeable = true, - .executable = true }; - Node &node = open_node.node(); - - using namespace Fatfs; - - /* f_stat() does not work for the '/' directory */ - if (!is_root(node.name())) { - - FILINFO fatfs_file_info; - - FRESULT res = f_stat(node.name(), &fatfs_file_info); - - switch(res) { - case FR_OK: - break; - case FR_NO_FILE: - error("f_stat() failed with error code FR_NO_FILE"); - return status; - case FR_NO_PATH: - error("f_stat() failed with error code FR_NO_PATH"); - return status; - case FR_INVALID_NAME: - error("f_stat() failed with error code FR_INVALID_NAME"); - return status; - case FR_INVALID_DRIVE: - error("f_stat() failed with error code FR_INVALID_DRIVE"); - return status; - case FR_DISK_ERR: - error("f_stat() failed with error code FR_DISK_ERR"); - return status; - case FR_INT_ERR: - error("f_stat() failed with error code FR_INT_ERR"); - return status; - case FR_NOT_READY: - error("f_stat() failed with error code FR_NOT_READY"); - return status; - case FR_NOT_ENABLED: - error("f_stat() failed with error code FR_NOT_ENABLED"); - return status; - case FR_NO_FILESYSTEM: - error("f_stat() failed with error code FR_NO_FILESYSTEM"); - return status; - default: - /* not supposed to occur according to the fatfs documentation */ - error("f_stat() returned an unexpected error code"); - return status; - } - - if ((fatfs_file_info.fattrib & AM_DIR) == AM_DIR) { - status.type = File_system::Node_type::DIRECTORY; } - else { - status.type = File_system::Node_type::CONTINUOUS_FILE; - status.size = fatfs_file_info.fsize; - } - - } else { - status.type = File_system::Node_type::DIRECTORY; - } - - if (status.type == File_system::Node_type::DIRECTORY) { - - /* determine the number of directory entries */ - - Fatfs::DIR fatfs_dir; - FRESULT f_opendir_res = f_opendir(&fatfs_dir, node.name()); - - if (f_opendir_res != FR_OK) - return status; - - FILINFO fatfs_file_info; - - int num_direntries = -1; - do { - ++num_direntries; - FRESULT res = f_readdir(&fatfs_dir, &fatfs_file_info); - if (res != FR_OK) - return status; - } while (fatfs_file_info.fname[0] != 0); - - status.size = num_direntries * sizeof(Directory_entry); - } - - return status; - }; - - try { - return _open_node_registry.apply(node_handle, status_fn); - } catch (Id_space::Unknown_id const &) { - throw Invalid_handle(); - } - } - - void control(Node_handle, Control) { } - - void unlink(Dir_handle dir_handle, Name const &name) - { - if (!valid_filename(name.string())) - throw Invalid_name(); - - if (!_writable) - throw Permission_denied(); - - auto unlink_fn = [&] (Open_node &open_node) { - - using namespace Fatfs; - - Absolute_path absolute_path(_root.name()); - - try { - absolute_path.append(open_node.node().name()); - absolute_path.append("/"); - absolute_path.append(name.string()); - } catch (Path_base::Path_too_long) { - throw Invalid_name(); - } - - FRESULT res = f_unlink(absolute_path.base()); - - switch(res) { - case FR_OK: - break; - case FR_NO_FILE: - case FR_NO_PATH: - throw Lookup_failed(); - case FR_INVALID_NAME: - case FR_INVALID_DRIVE: - throw Invalid_name(); - case FR_DENIED: - case FR_WRITE_PROTECTED: - throw Permission_denied(); - case FR_DISK_ERR: - error("f_unlink() failed with error code FR_DISK_ERR"); - return; - case FR_INT_ERR: - error("f_unlink() failed with error code FR_INT_ERR"); - return; - case FR_NOT_READY: - error("f_unlink() failed with error code FR_NOT_READY"); - return; - case FR_NOT_ENABLED: - error("f_unlink() failed with error code FR_NOT_ENABLED"); - return; - case FR_NO_FILESYSTEM: - error("f_unlink() failed with error code FR_NO_FILESYSTEM"); - return; - default: - /* not supposed to occur according to the fatfs documentation */ - error("f_unlink() returned an unexpected error code"); - return; - } - }; - - try { - _open_node_registry.apply(dir_handle, unlink_fn); - } catch (Id_space::Unknown_id const &) { - throw Invalid_handle(); - } - } - - void truncate(File_handle file_handle, file_size_t size) - { - if (!_writable) - throw Permission_denied(); - - auto truncate_fn = [&] (Open_node &open_node) { - open_node.node().truncate(size); - }; - - try { - _open_node_registry.apply(file_handle, truncate_fn); - } catch (Id_space::Unknown_id const &) { - throw Invalid_handle(); - } - } - - void move(Dir_handle from_dir_handle, Name const &from_name, - Dir_handle to_dir_handle, Name const &to_name) - { - if (!_writable) - throw Permission_denied(); - - if (!valid_filename(from_name.string())) - throw Lookup_failed(); - - if (!valid_filename(to_name.string())) - throw Invalid_name(); - - auto move_fn = [&] (Open_node &open_from_dir_node) { - - auto inner_move_fn = [&] (Open_node &open_to_dir_node) { - - Absolute_path absolute_from_path(_root.name()); - Absolute_path absolute_to_path(_root.name()); - - try { - absolute_from_path.append(open_from_dir_node.node().name()); - absolute_from_path.append("/"); - absolute_from_path.append(from_name.string()); - absolute_to_path.append(open_to_dir_node.node().name()); - absolute_to_path.append("/"); - absolute_to_path.append(to_name.string()); - } catch (Path_base::Path_too_long) { - throw Invalid_name(); - } - - using namespace Fatfs; - - FRESULT res = f_rename(absolute_from_path.base(), absolute_to_path.base()); - - /* if newpath already exists - try to unlink it once */ - if (res == FR_EXIST) { - f_unlink(absolute_to_path.base()); - res = f_rename(absolute_from_path.base(), absolute_to_path.base()); - } - - switch(res) { - case FR_OK: - break; - case FR_NO_FILE: - case FR_NO_PATH: - throw Lookup_failed(); - case FR_INVALID_NAME: - case FR_INVALID_DRIVE: - throw Invalid_name(); - case FR_EXIST: - error("f_rename() failed with error code FR_EXIST"); - throw Invalid_name(); - case FR_DENIED: - case FR_WRITE_PROTECTED: - throw Permission_denied(); - case FR_DISK_ERR: - error("f_rename() failed with error code FR_DISK_ERR"); - throw Lookup_failed(); - case FR_INT_ERR: - error("f_rename() failed with error code FR_INT_ERR"); - throw Lookup_failed(); - case FR_NOT_READY: - error("f_rename() failed with error code FR_NOT_READY"); - throw Lookup_failed(); - case FR_NOT_ENABLED: - error("f_rename() failed with error code FR_NOT_ENABLED"); - throw Lookup_failed(); - case FR_NO_FILESYSTEM: - error("f_rename() failed with error code FR_NO_FILESYSTEM"); - throw Lookup_failed(); - default: - /* not supposed to occur according to the fatfs documentation */ - error("f_rename() returned an unexpected error code"); - throw Lookup_failed(); - } - }; - - try { - _open_node_registry.apply(to_dir_handle, inner_move_fn); - } catch (Id_space::Unknown_id const &) { - throw Invalid_handle(); - } - }; - - try { - _open_node_registry.apply(from_dir_handle, move_fn); - } catch (Id_space::Unknown_id const &) { - throw Invalid_handle(); - } - } - - void sigh(Node_handle, Genode::Signal_context_capability) - { - error("File_system::Session::sigh not supported"); - } -}; - - -class Fatfs_fs::Root : public Root_component -{ - private: - - Genode::Env &_env; - Genode::Allocator &_md_alloc; - Genode::Allocator &_heap; - Genode::Attached_rom_dataspace _config { _env, "config" }; - Directory &_root_dir; - - protected: - - Session_component *_create_session(const char *args) - { - /* - * Determine client-specific policy defined implicitly by - * the client's label. - */ - Directory *session_root_dir = 0; - bool writeable = false; - - typedef String<256> Root_path; - Root_path root; - - Session_label const label = label_from_args(args); - try { - Session_policy policy(label, _config.xml()); - - /* - * Determine directory that is used as root directory of - * the session. - */ - try { - policy.attribute("root").value(root); - if (is_root(root.string())) { - session_root_dir = &_root_dir; - } else { - /* - * Make sure the root path is specified with a - * leading path delimiter. For performing the - * lookup, we skip the first character. - */ - if (root.string()[0] != '/') - throw Lookup_failed(); - - /* Check if the root path exists */ - - using namespace Fatfs; - - FRESULT res = f_chdir(root.string()); - - switch(res) { - case FR_OK: - break; - case FR_NO_PATH: - throw Lookup_failed(); - case FR_INVALID_NAME: - case FR_INVALID_DRIVE: - throw Lookup_failed(); - case FR_NOT_READY: - error("f_chdir() failed with error code FR_NOT_READY"); - throw Service_denied(); - case FR_DISK_ERR: - error("f_chdir() failed with error code FR_DISK_ERR"); - throw Service_denied(); - case FR_INT_ERR: - error("f_chdir() failed with error code FR_INT_ERR"); - throw Service_denied(); - case FR_NOT_ENABLED: - error("f_chdir() failed with error code FR_NOT_ENABLED"); - throw Service_denied(); - case FR_NO_FILESYSTEM: - error("f_chdir() failed with error code FR_NO_FILESYSTEM"); - throw Service_denied(); - default: - /* not supposed to occur according to the fatfs documentation */ - error("f_chdir() returned an unexpected error code"); - throw Service_denied(); - } - - session_root_dir = new (&_md_alloc) Directory(root.string()); - } - } - catch (Xml_node::Nonexistent_attribute) { - error("missing \"root\" attribute in policy definition"); - throw Service_denied(); - } - catch (Lookup_failed) { - error("session root directory \"", root, "\" does not exist"); - throw Service_denied(); - } - - /* - * Determine if write access is permitted for the session. - */ - writeable = policy.attribute_value("writeable", false); - } - catch (Session_policy::No_policy_defined) { - error("Invalid session request, no matching policy"); - throw Service_denied(); - } - - size_t ram_quota = - Arg_string::find_arg(args, "ram_quota" ).ulong_value(0); - size_t tx_buf_size = - Arg_string::find_arg(args, "tx_buf_size").ulong_value(0); - - if (!tx_buf_size) { - error(label, " requested a session with a zero length transmission buffer"); - throw Service_denied(); - } - - /* - * Check if donated ram quota suffices for session data, - * and communication buffer. - */ - size_t session_size = sizeof(Session_component) + tx_buf_size; - if (max((size_t)4096, session_size) > ram_quota) { - error("insufficient 'ram_quota', got ", ram_quota, ", " - "need ", session_size); - throw Insufficient_ram_quota(); - } - return new (md_alloc()) - Session_component(_env, _heap, tx_buf_size, - *session_root_dir, writeable); - } - - public: - - /** - * Constructor - * - * \param env reference to Genode environment - * \param heap meta-data allocator - * \param root normal root directory if root in policy starts - * at root - */ - Root(Genode::Env &env, Allocator &md_alloc, Genode::Allocator &heap, - Directory &root) - : - Root_component(&env.ep().rpc_ep(), &md_alloc), - _env(env), _md_alloc(md_alloc), _heap(heap), _root_dir(root) - { } -}; - - -struct Fatfs_fs::Main -{ - Genode::Env &_env; - Genode::Heap _heap { _env.ram(), _env.rm() }; - Genode::Sliced_heap _sliced_heap { _env.ram(), _env.rm() }; - - Directory _root_dir { "/" }; - Root _root { _env, _sliced_heap, _heap, _root_dir }; - - Fatfs::FATFS _fatfs; - - Main(Genode::Env &env) : _env(env) - { - Fatfs::block_init(_env, _heap); - - using namespace File_system; - using namespace Fatfs; - - /* mount the file system */ - if (f_mount(&_fatfs, "", 0) != Fatfs::FR_OK) { - error("mount failed"); - - struct Mount_failed : Genode::Exception { }; - throw Mount_failed(); - } - - Genode::log("--- Starting Fatfs_fs ---"); - - _env.parent().announce(_env.ep().manage(_root)); - } -}; - - -void Component::construct(Genode::Env &env) -{ - /* XXX execute constructors of global statics */ - env.exec_static_constructors(); - - static Fatfs_fs::Main main(env); -} diff --git a/repos/libports/src/server/fatfs_fs/node.h b/repos/libports/src/server/fatfs_fs/node.h deleted file mode 100644 index d41629e2f..000000000 --- a/repos/libports/src/server/fatfs_fs/node.h +++ /dev/null @@ -1,75 +0,0 @@ -/* - * \brief FATFS file-system node - * \author Christian Prochaska - * \date 2012-07-04 - */ - -/* - * Copyright (C) 2012-2017 Genode Labs GmbH - * - * This file is part of the Genode OS framework, which is distributed - * under the terms of the GNU Affero General Public License version 3. - */ - -#ifndef _NODE_H_ -#define _NODE_H_ - -/* Genode includes */ -#include -#include -#include - -/* fatfs includes */ -namespace Fatfs { extern "C" { -#include -} } - -namespace Fatfs_fs { - using namespace File_system; - - typedef Genode::Path Absolute_path; - - class Node; -} - - -class Fatfs_fs::Node : public Node_base -{ - protected: - - Absolute_path _name; - - public: - - Node(const char *name) : _name(name) { } - - char const *name() { return _name.base(); } - - /* - * A generic Node object can be created to represent a file or - * directory by its name without opening it, so the functions - * of this class must not be abstract. - */ - - virtual size_t read(char *dst, size_t len, seek_off_t) - { - Genode::error("read() called on generic Node object"); - return 0; - } - - virtual size_t write(char const *src, size_t len, seek_off_t) - { - Genode::error("write() called on generic Node object"); - return 0; - } - - /* - * File functionality - */ - virtual void truncate(file_size_t size) - { - Genode::error(__PRETTY_FUNCTION__, " called on a non-file node"); - } -}; - -#endif /* _NODE_H_ */ diff --git a/repos/libports/src/server/fatfs_fs/open_node.h b/repos/libports/src/server/fatfs_fs/open_node.h deleted file mode 100644 index 942976828..000000000 --- a/repos/libports/src/server/fatfs_fs/open_node.h +++ /dev/null @@ -1,95 +0,0 @@ -/* - * \brief Representation of an open file system node within the component (deprecated) - * \author Christian Prochaska - * \date 2017-06-09 - */ - -/* - * Copyright (C) 2017 Genode Labs GmbH - * - * This file is part of the Genode OS framework, which is distributed - * under the terms of the GNU Affero General Public License version 3. - */ - -#ifndef _OPEN_NODE_H_ -#define _OPEN_NODE_H_ - -/* Genode includes */ -#include -#include - -namespace File_system { - /* - * \param NODE component-specific node type - */ - template class Open_node; -} - -template -class File_system::Open_node : public File_system::Node -{ - private: - - Genode::Id_space::Element _element; - - NODE &_node; - Genode::Constructible _listener; - - Listener::Version const _version_when_opened = _node.curr_version(); - - /* - * Flag to track whether the underlying file-system node was - * modified via this 'Open_node'. That is, if closing the 'Open_node' - * should notify listeners of the file. - */ - bool _was_written = false; - - public: - - Open_node(NODE &node, Genode::Id_space &id_space) - : _element(*this, id_space), _node(node) { } - - ~Open_node() - { - if (_listener.constructed()) { - _node.remove_listener(&*_listener); - _listener.destruct(); - } - - /* - * Notify remaining listeners about the changed file - */ - if (_was_written) - _node.notify_listeners(); - } - - NODE &node() { return _node; } - File_system::Listener &listener() { return *_listener; } - - Genode::Id_space::Id id() { return _element.id(); } - - /** - * Register packet stream sink to be notified of node changes - */ - void register_notify(File_system::Sink &sink) - { - /* - * If there was already a handler registered for the node, - * remove the old handler. - */ - if (_listener.constructed()) { - _node.remove_listener(&*_listener); - _listener.destruct(); - } - - /* - * Register new handler - */ - _listener.construct(sink, id(), _version_when_opened); - _node.add_listener(&*_listener); - } - - void mark_as_written() { _was_written = true; } -}; - -#endif /* _OPEN_NODE_H_ */ diff --git a/repos/libports/src/server/fatfs_fs/target.mk b/repos/libports/src/server/fatfs_fs/target.mk deleted file mode 100644 index 917d5901b..000000000 --- a/repos/libports/src/server/fatfs_fs/target.mk +++ /dev/null @@ -1,6 +0,0 @@ -TARGET = fatfs_fs -SRC_CC = main.cc -LIBS = base fatfs_block -INC_DIR += $(PRG_DIR) - -CC_CXX_WARN_STRICT = diff --git a/repos/libports/src/server/fatfs_fs/util.h b/repos/libports/src/server/fatfs_fs/util.h deleted file mode 100644 index 36f7c1c42..000000000 --- a/repos/libports/src/server/fatfs_fs/util.h +++ /dev/null @@ -1,87 +0,0 @@ -/* - * \brief Utilities - * \author Norman Feske - * \author Christian Prochaska - * \date 2012-04-11 - */ - -#ifndef _UTIL_H_ -#define _UTIL_H_ - -/* Genode includes */ -#include -#include - - -/** - * Return true if null-terminated string 'substr' occurs in null-terminated - * string 'str' - */ -static bool string_contains(char const *str, char const *substr) -{ - using namespace Genode; - - size_t str_len = strlen(str); - size_t substr_len = strlen(substr); - - if (str_len < substr_len) - return false; - - for (size_t i = 0; i <= (str_len - substr_len); i++) - if (strcmp(&str[i], substr, substr_len) == 0) - return true; - - return false; -} - - -/** - * Return true if 'str' is a valid file name - */ -static inline bool valid_filename(char const *str) -{ - if (!str) return false; - - /* must have at least one character */ - if (str[0] == 0) return false; - - /* must not contain '/' or '\' or ':' */ - if (File_system::string_contains(str, '/') || - File_system::string_contains(str, '\\') || - File_system::string_contains(str, ':')) - return false; - - return true; -} - -/** - * Return true if 'str' is a valid path - */ -static inline bool valid_path(char const *str) -{ - if (!str) return false; - - /* must start with '/' */ - if (str[0] != '/') - return false; - - /* must not contain '\' or ':' */ - if (File_system::string_contains(str, '\\') || - File_system::string_contains(str, ':')) - return false; - - /* must not contain "/../" */ - if (string_contains(str, "/../")) return false; - - return true; -} - -/** - * Return true if 'str' is "/" - */ -static inline bool is_root(const char *str) -{ - return (Genode::strcmp(str, "/") == 0); -} - -#endif /* _UTIL_H_ */ diff --git a/repos/libports/src/test/libc_fatfs/target.mk b/repos/libports/src/test/libc_fatfs/target.mk deleted file mode 100644 index 491222bb2..000000000 --- a/repos/libports/src/test/libc_fatfs/target.mk +++ /dev/null @@ -1,8 +0,0 @@ -TARGET = test-libc_fatfs -LIBS = libc libc_fatfs -SRC_CC = main.cc - -# we re-use the libc_vfs test -vpath main.cc $(REP_DIR)/src/test/libc_vfs - -CC_CXX_WARN_STRICT = diff --git a/tool/autopilot.list b/tool/autopilot.list index 7d7aca62b..3b1bfe7aa 100644 --- a/tool/autopilot.list +++ b/tool/autopilot.list @@ -15,7 +15,6 @@ gdb_monitor ieee754 init_smp input_filter -libc_fatfs libc_vfs_fs_ext2 log_core lwip