Loading include/client/gkfs_functions.hpp +34 −38 Original line number Diff line number Diff line Loading @@ -36,77 +36,73 @@ using sys_statfs = struct statfs; using sys_statvfs = struct statvfs; namespace gkfs { namespace func { namespace syscall { int gkfs_open(const std::string& path, mode_t mode, int flags); std::shared_ptr<gkfs::metadata::Metadata> metadata(const std::string& path, bool follow_links = false); int gkfs_create(const std::string& path, mode_t mode); int check_parent_dir(const std::string& path); int gkfs_remove(const std::string& path); int open(const std::string& path, mode_t mode, int flags); int gkfs_access(const std::string& path, int mask, bool follow_links = true); int mk_node(const std::string& path, mode_t mode); int gkfs_stat(const std::string& path, struct stat* buf, bool follow_links = true); int rm_node(const std::string& path); int gkfs_statfs(sys_statfs* buf); int access(const std::string& path, int mask, bool follow_links = true); int gkfs_statvfs(sys_statvfs* buf); int stat(const std::string& path, struct stat* buf, bool follow_links = true); off64_t gkfs_lseek(unsigned int fd, off64_t offset, unsigned int whence); int statfs(sys_statfs* buf); off64_t gkfs_lseek(std::shared_ptr<OpenFile> gkfs_fd, off64_t offset, unsigned int whence); int statvfs(sys_statvfs* buf); int gkfs_truncate(const std::string& path, off_t offset); off64_t lseek(unsigned int fd, off64_t offset, unsigned int whence); int gkfs_truncate(const std::string& path, off_t old_size, off_t new_size); off64_t lseek(std::shared_ptr<OpenFile> gkfs_fd, off64_t offset, unsigned int whence); int gkfs_dup(int oldfd); int truncate(const std::string& path, off_t offset); int truncate(const std::string& path, off_t old_size, off_t new_size); int dup(int oldfd); int dup2(int oldfd, int newfd); int gkfs_dup2(int oldfd, int newfd); #ifdef HAS_SYMLINKS int mk_symlink(const std::string& path, const std::string& target_path); int gkfs_mk_symlink(const std::string& path, const std::string& target_path); int readlink(const std::string& path, char* buf, int bufsize); int gkfs_readlink(const std::string& path, char* buf, int bufsize); #endif ssize_t pwrite(std::shared_ptr<OpenFile> file, ssize_t gkfs_pwrite(std::shared_ptr<OpenFile> file, const char* buf, size_t count, off64_t offset); ssize_t pwrite_ws(int fd, const void* buf, size_t count, off64_t offset); ssize_t gkfs_pwrite_ws(int fd, const void* buf, size_t count, off64_t offset); ssize_t write(int fd, const void* buf, size_t count); ssize_t gkfs_write(int fd, const void* buf, size_t count); ssize_t pwritev(int fd, const struct iovec* iov, int iovcnt, off_t offset); ssize_t gkfs_pwritev(int fd, const struct iovec* iov, int iovcnt, off_t offset); ssize_t writev(int fd, const struct iovec* iov, int iovcnt); ssize_t gkfs_writev(int fd, const struct iovec* iov, int iovcnt); ssize_t pread(std::shared_ptr<OpenFile> file, char* buf, size_t count, off64_t offset); ssize_t gkfs_pread(std::shared_ptr<OpenFile> file, char* buf, size_t count, off64_t offset); ssize_t pread_ws(int fd, void* buf, size_t count, off64_t offset); ssize_t gkfs_pread_ws(int fd, void* buf, size_t count, off64_t offset); ssize_t read(int fd, void* buf, size_t count); ssize_t gkfs_read(int fd, void* buf, size_t count); int opendir(const std::string& path); int gkfs_opendir(const std::string& path); int getdents(unsigned int fd, int gkfs_getdents(unsigned int fd, struct linux_dirent* dirp, unsigned int count); int getdents64(unsigned int fd, int gkfs_getdents64(unsigned int fd, struct linux_dirent64* dirp, unsigned int count); int rmdir(const std::string& path); } } int gkfs_rmdir(const std::string& path); } // namespace syscall } // namespace gkfs #endif //GEKKOFS_GKFS_FUNCTIONS_HPP include/client/preload_util.hpp +5 −2 Original line number Diff line number Diff line Loading @@ -48,12 +48,15 @@ constexpr typename std::underlying_type<E>::type to_underlying(E e) { return static_cast<typename std::underlying_type<E>::type>(e); } std::shared_ptr<gkfs::metadata::Metadata> get_metadata(const std::string& path, bool follow_links = false); int metadata_to_stat(const std::string& path, const gkfs::metadata::Metadata& md, struct stat& attr); std::vector<std::pair<std::string, std::string>> load_hostfile(const std::string& lfpath); void load_hosts(); } } } // namespace util } // namespace gkfs #endif //GEKKOFS_PRELOAD_UTIL_HPP src/client/gkfs_functions.cpp +65 −77 Original line number Diff line number Diff line Loading @@ -34,31 +34,12 @@ extern "C" { using namespace std; std::shared_ptr<gkfs::metadata::Metadata> gkfs::func::metadata(const string& path, bool follow_links) { std::string attr; auto err = gkfs::rpc::forward_stat(path, attr); if (err) { return nullptr; } #ifdef HAS_SYMLINKS if (follow_links) { gkfs::metadata::Metadata md{attr}; while (md.is_link()) { err = gkfs::rpc::forward_stat(md.target_path(), attr); if (err) { return nullptr; } md = gkfs::metadata::Metadata{attr}; } } #endif return make_shared<gkfs::metadata::Metadata>(attr); } namespace { int gkfs::func::check_parent_dir(const std::string& path) { int check_parent_dir(const std::string& path) { #if CREATE_CHECK_PARENTS auto p_comp = path::dirname(path); auto md = gkfs::func::metadata(p_comp); auto p_comp = gkfs::path::dirname(path); auto md = gkfs::util::get_metadata(p_comp); if (!md) { if (errno == ENOENT) { LOG(DEBUG, "Parent component does not exist: '{}'", p_comp); Loading @@ -75,8 +56,12 @@ int gkfs::func::check_parent_dir(const std::string& path) { #endif // CREATE_CHECK_PARENTS return 0; } } // namespace int gkfs::func::open(const std::string& path, mode_t mode, int flags) { namespace gkfs { namespace syscall { int gkfs_open(const std::string& path, mode_t mode, int flags) { if (flags & O_PATH) { LOG(ERROR, "`O_PATH` flag is not supported"); Loading @@ -91,7 +76,7 @@ int gkfs::func::open(const std::string& path, mode_t mode, int flags) { } bool exists = true; auto md = gkfs::func::metadata(path); auto md = gkfs::util::get_metadata(path); if (!md) { if (errno == ENOENT) { exists = false; Loading @@ -118,7 +103,7 @@ int gkfs::func::open(const std::string& path, mode_t mode, int flags) { } // no access check required here. If one is using our FS they have the permissions. if (gkfs::func::mk_node(path, mode | S_IFREG)) { if (gkfs_create(path, mode | S_IFREG)) { LOG(ERROR, "Error creating non-existent file: '{}'", strerror(errno)); return -1; } Loading @@ -138,12 +123,12 @@ int gkfs::func::open(const std::string& path, mode_t mode, int flags) { errno = ELOOP; return -1; } return gkfs::func::open(md->target_path(), mode, flags); return gkfs_open(md->target_path(), mode, flags); } #endif if (S_ISDIR(md->mode())) { return gkfs::func::opendir(path); return gkfs_opendir(path); } Loading @@ -151,7 +136,7 @@ int gkfs::func::open(const std::string& path, mode_t mode, int flags) { assert(S_ISREG(md->mode())); if ((flags & O_TRUNC) && ((flags & O_RDWR) || (flags & O_WRONLY))) { if (gkfs::func::truncate(path, md->size(), 0)) { if (gkfs_truncate(path, md->size(), 0)) { LOG(ERROR, "Error truncating file"); return -1; } Loading @@ -161,7 +146,7 @@ int gkfs::func::open(const std::string& path, mode_t mode, int flags) { return CTX->file_map()->add(std::make_shared<OpenFile>(path, flags)); } int gkfs::func::mk_node(const std::string& path, mode_t mode) { int gkfs_create(const std::string& path, mode_t mode) { //file type must be set switch (mode & S_IFMT) { Loading Loading @@ -195,8 +180,8 @@ int gkfs::func::mk_node(const std::string& path, mode_t mode) { * @param path * @return */ int gkfs::func::rm_node(const std::string& path) { auto md = gkfs::func::metadata(path); int gkfs_remove(const std::string& path) { auto md = gkfs::util::get_metadata(path); if (!md) { return -1; } Loading @@ -204,8 +189,8 @@ int gkfs::func::rm_node(const std::string& path) { return gkfs::rpc::forward_remove(path, !has_data, md->size()); } int gkfs::func::access(const std::string& path, const int mask, bool follow_links) { auto md = gkfs::func::metadata(path, follow_links); int gkfs_access(const std::string& path, const int mask, bool follow_links) { auto md = gkfs::util::get_metadata(path, follow_links); if (!md) { errno = ENOENT; return -1; Loading @@ -213,8 +198,8 @@ int gkfs::func::access(const std::string& path, const int mask, bool follow_link return 0; } int gkfs::func::stat(const string& path, struct stat* buf, bool follow_links) { auto md = gkfs::func::metadata(path, follow_links); int gkfs_stat(const string& path, struct stat* buf, bool follow_links) { auto md = gkfs::util::get_metadata(path, follow_links); if (!md) { return -1; } Loading @@ -222,7 +207,7 @@ int gkfs::func::stat(const string& path, struct stat* buf, bool follow_links) { return 0; } int gkfs::func::statfs(sys_statfs* buf) { int gkfs_statfs(sys_statfs* buf) { auto blk_stat = gkfs::rpc::forward_get_chunk_stat(); buf->f_type = 0; buf->f_bsize = blk_stat.chunk_size; Loading @@ -239,7 +224,7 @@ int gkfs::func::statfs(sys_statfs* buf) { return 0; } int gkfs::func::statvfs(sys_statvfs* buf) { int gkfs_statvfs(sys_statvfs* buf) { init_ld_env_if_needed(); auto blk_stat = gkfs::rpc::forward_get_chunk_stat(); buf->f_bsize = blk_stat.chunk_size; Loading @@ -257,11 +242,11 @@ int gkfs::func::statvfs(sys_statvfs* buf) { return 0; } off_t gkfs::func::lseek(unsigned int fd, off_t offset, unsigned int whence) { return gkfs::func::lseek(CTX->file_map()->get(fd), offset, whence); off_t gkfs_lseek(unsigned int fd, off_t offset, unsigned int whence) { return gkfs_lseek(CTX->file_map()->get(fd), offset, whence); } off_t gkfs::func::lseek(shared_ptr<OpenFile> gkfs_fd, off_t offset, unsigned int whence) { off_t gkfs_lseek(shared_ptr<OpenFile> gkfs_fd, off_t offset, unsigned int whence) { switch (whence) { case SEEK_SET: gkfs_fd->pos(offset); Loading Loading @@ -297,7 +282,7 @@ off_t gkfs::func::lseek(shared_ptr<OpenFile> gkfs_fd, off_t offset, unsigned int return gkfs_fd->pos(); } int gkfs::func::truncate(const std::string& path, off_t old_size, off_t new_size) { int gkfs_truncate(const std::string& path, off_t old_size, off_t new_size) { assert(new_size >= 0); assert(new_size <= old_size); Loading @@ -317,7 +302,7 @@ int gkfs::func::truncate(const std::string& path, off_t old_size, off_t new_size return 0; } int gkfs::func::truncate(const std::string& path, off_t length) { int gkfs_truncate(const std::string& path, off_t length) { /* TODO CONCURRENCY: * At the moment we first ask the length to the metadata-server in order to * know which data-server have data to be deleted. Loading @@ -332,7 +317,7 @@ int gkfs::func::truncate(const std::string& path, off_t length) { return -1; } auto md = gkfs::func::metadata(path, true); auto md = gkfs::util::get_metadata(path, true); if (!md) { return -1; } Loading @@ -342,18 +327,18 @@ int gkfs::func::truncate(const std::string& path, off_t length) { errno = EINVAL; return -1; } return gkfs::func::truncate(path, size, length); return gkfs_truncate(path, size, length); } int gkfs::func::dup(const int oldfd) { int gkfs_dup(const int oldfd) { return CTX->file_map()->dup(oldfd); } int gkfs::func::dup2(const int oldfd, const int newfd) { int gkfs_dup2(const int oldfd, const int newfd) { return CTX->file_map()->dup2(oldfd, newfd); } ssize_t gkfs::func::pwrite(std::shared_ptr<OpenFile> file, const char* buf, size_t count, off64_t offset) { ssize_t gkfs_pwrite(std::shared_ptr<OpenFile> file, const char* buf, size_t count, off64_t offset) { if (file->type() != FileType::regular) { assert(file->type() == FileType::directory); LOG(WARNING, "Cannot read from directory"); Loading @@ -377,9 +362,9 @@ ssize_t gkfs::func::pwrite(std::shared_ptr<OpenFile> file, const char* buf, size return ret; // return written size or -1 as error } ssize_t gkfs::func::pwrite_ws(int fd, const void* buf, size_t count, off64_t offset) { ssize_t gkfs_pwrite_ws(int fd, const void* buf, size_t count, off64_t offset) { auto file = CTX->file_map()->get(fd); return gkfs::func::pwrite(file, reinterpret_cast<const char*>(buf), count, offset); return gkfs_pwrite(file, reinterpret_cast<const char*>(buf), count, offset); } /* Write counts bytes starting from current file position Loading @@ -387,12 +372,12 @@ ssize_t gkfs::func::pwrite_ws(int fd, const void* buf, size_t count, off64_t off * * Same as write syscall. */ ssize_t gkfs::func::write(int fd, const void* buf, size_t count) { ssize_t gkfs_write(int fd, const void* buf, size_t count) { auto gkfs_fd = CTX->file_map()->get(fd); auto pos = gkfs_fd->pos(); //retrieve the current offset if (gkfs_fd->get_flag(OpenFile_flags::append)) gkfs::func::lseek(gkfs_fd, 0, SEEK_END); auto ret = gkfs::func::pwrite(gkfs_fd, reinterpret_cast<const char*>(buf), count, pos); gkfs_lseek(gkfs_fd, 0, SEEK_END); auto ret = gkfs_pwrite(gkfs_fd, reinterpret_cast<const char*>(buf), count, pos); // Update offset in file descriptor in the file map if (ret > 0) { gkfs_fd->pos(pos + count); Loading @@ -400,7 +385,7 @@ ssize_t gkfs::func::write(int fd, const void* buf, size_t count) { return ret; } ssize_t gkfs::func::pwritev(int fd, const struct iovec* iov, int iovcnt, off_t offset) { ssize_t gkfs_pwritev(int fd, const struct iovec* iov, int iovcnt, off_t offset) { auto file = CTX->file_map()->get(fd); auto pos = offset; // keep truck of current position Loading @@ -412,7 +397,7 @@ ssize_t gkfs::func::pwritev(int fd, const struct iovec* iov, int iovcnt, off_t o continue; } auto buf = (iov + i)->iov_base; ret = gkfs::func::pwrite(file, reinterpret_cast<char*>(buf), count, pos); ret = gkfs_pwrite(file, reinterpret_cast<char*>(buf), count, pos); if (ret == -1) { break; } Loading @@ -430,11 +415,11 @@ ssize_t gkfs::func::pwritev(int fd, const struct iovec* iov, int iovcnt, off_t o return written; } ssize_t gkfs::func::writev(int fd, const struct iovec* iov, int iovcnt) { ssize_t gkfs_writev(int fd, const struct iovec* iov, int iovcnt) { auto gkfs_fd = CTX->file_map()->get(fd); auto pos = gkfs_fd->pos(); // retrieve the current offset auto ret = gkfs::func::pwritev(fd, iov, iovcnt, pos); auto ret = gkfs_pwritev(fd, iov, iovcnt, pos); assert(ret != 0); if (ret < 0) { return -1; Loading @@ -443,7 +428,7 @@ ssize_t gkfs::func::writev(int fd, const struct iovec* iov, int iovcnt) { return ret; } ssize_t gkfs::func::pread(std::shared_ptr<OpenFile> file, char* buf, size_t count, off64_t offset) { ssize_t gkfs_pread(std::shared_ptr<OpenFile> file, char* buf, size_t count, off64_t offset) { if (file->type() != FileType::regular) { assert(file->type() == FileType::directory); LOG(WARNING, "Cannot read from directory"); Loading @@ -463,10 +448,10 @@ ssize_t gkfs::func::pread(std::shared_ptr<OpenFile> file, char* buf, size_t coun return ret; // return read size or -1 as error } ssize_t gkfs::func::read(int fd, void* buf, size_t count) { ssize_t gkfs_read(int fd, void* buf, size_t count) { auto gkfs_fd = CTX->file_map()->get(fd); auto pos = gkfs_fd->pos(); //retrieve the current offset auto ret = gkfs::func::pread(gkfs_fd, reinterpret_cast<char*>(buf), count, pos); auto ret = gkfs_pread(gkfs_fd, reinterpret_cast<char*>(buf), count, pos); // Update offset in file descriptor in the file map if (ret > 0) { gkfs_fd->pos(pos + ret); Loading @@ -474,14 +459,14 @@ ssize_t gkfs::func::read(int fd, void* buf, size_t count) { return ret; } ssize_t gkfs::func::pread_ws(int fd, void* buf, size_t count, off64_t offset) { ssize_t gkfs_pread_ws(int fd, void* buf, size_t count, off64_t offset) { auto gkfs_fd = CTX->file_map()->get(fd); return gkfs::func::pread(gkfs_fd, reinterpret_cast<char*>(buf), count, offset); return gkfs_pread(gkfs_fd, reinterpret_cast<char*>(buf), count, offset); } int gkfs::func::opendir(const std::string& path) { int gkfs_opendir(const std::string& path) { auto md = gkfs::func::metadata(path); auto md = gkfs::util::get_metadata(path); if (!md) { return -1; } Loading @@ -496,8 +481,8 @@ int gkfs::func::opendir(const std::string& path) { return CTX->file_map()->add(open_dir); } int gkfs::func::rmdir(const std::string& path) { auto md = gkfs::func::metadata(path); int gkfs_rmdir(const std::string& path) { auto md = gkfs::util::get_metadata(path); if (!md) { LOG(DEBUG, "Path '{}' does not exist: ", path); errno = ENOENT; Loading @@ -518,7 +503,7 @@ int gkfs::func::rmdir(const std::string& path) { return gkfs::rpc::forward_remove(path, true, 0); } int gkfs::func::getdents(unsigned int fd, int gkfs_getdents(unsigned int fd, struct linux_dirent* dirp, unsigned int count) { Loading Loading @@ -571,7 +556,7 @@ int gkfs::func::getdents(unsigned int fd, } int gkfs::func::getdents64(unsigned int fd, int gkfs_getdents64(unsigned int fd, struct linux_dirent64* dirp, unsigned int count) { Loading Loading @@ -624,14 +609,14 @@ int gkfs::func::getdents64(unsigned int fd, #ifdef HAS_SYMLINKS int gkfs::func::mk_symlink(const std::string& path, const std::string& target_path) { int gkfs_mk_symlink(const std::string& path, const std::string& target_path) { init_ld_env_if_needed(); /* The following check is not POSIX compliant. * In POSIX the target is not checked at all. * Here if the target is a directory we raise a NOTSUP error. * So that application know we don't support link to directory. */ auto target_md = gkfs::func::metadata(target_path, false); auto target_md = gkfs::util::get_metadata(target_path, false); if (target_md != nullptr) { auto trg_mode = target_md->mode(); if (!(S_ISREG(trg_mode) || S_ISLNK(trg_mode))) { Loading @@ -646,7 +631,7 @@ int gkfs::func::mk_symlink(const std::string& path, const std::string& target_pa return -1; } auto link_md = gkfs::func::metadata(path, false); auto link_md = gkfs::util::get_metadata(path, false); if (link_md != nullptr) { LOG(DEBUG, "Link exists: '{}'", path); errno = EEXIST; Loading @@ -656,9 +641,9 @@ int gkfs::func::mk_symlink(const std::string& path, const std::string& target_pa return gkfs::rpc::forward_mk_symlink(path, target_path); } int gkfs::func::readlink(const std::string& path, char* buf, int bufsize) { int gkfs_readlink(const std::string& path, char* buf, int bufsize) { init_ld_env_if_needed(); auto md = gkfs::func::metadata(path, false); auto md = gkfs::util::get_metadata(path, false); if (md == nullptr) { LOG(DEBUG, "Named link doesn't exist"); return -1; Loading @@ -680,4 +665,7 @@ int gkfs::func::readlink(const std::string& path, char* buf, int bufsize) { return path_size; } } // namespace syscall } // namespace gkfs #endif No newline at end of file src/client/hooks.cpp +28 −27 Original line number Diff line number Diff line Loading @@ -13,6 +13,7 @@ #include <client/hooks.hpp> #include <client/preload.hpp> #include <client/preload_util.hpp> #include <client/logging.hpp> #include <client/gkfs_functions.hpp> #include <client/path.hpp> Loading Loading @@ -51,7 +52,7 @@ int hook_openat(int dirfd, const char* cpath, int flags, mode_t mode) { return -ENOTDIR; case RelativizeStatus::internal: return with_errno(gkfs::func::open(resolved, mode, flags)); return with_errno(gkfs::syscall::gkfs_open(resolved, mode, flags)); default: LOG(ERROR, "{}() relativize status unknown: {}", __func__); Loading Loading @@ -85,7 +86,7 @@ int hook_stat(const char* path, struct stat* buf) { std::string rel_path; if (CTX->relativize_path(path, rel_path, false)) { return with_errno(gkfs::func::stat(rel_path, buf)); return with_errno(gkfs::syscall::gkfs_stat(rel_path, buf)); } return syscall_no_intercept(SYS_stat, rel_path.c_str(), buf); } Loading @@ -97,7 +98,7 @@ int hook_lstat(const char* path, struct stat* buf) { std::string rel_path; if (CTX->relativize_path(path, rel_path)) { return with_errno(gkfs::func::stat(rel_path, buf)); return with_errno(gkfs::syscall::gkfs_stat(rel_path, buf)); } return syscall_no_intercept(SYS_lstat, rel_path.c_str(), buf); } Loading @@ -109,7 +110,7 @@ int hook_fstat(unsigned int fd, struct stat* buf) { if (CTX->file_map()->exist(fd)) { auto path = CTX->file_map()->get(fd)->path(); return with_errno(gkfs::func::stat(path, buf)); return with_errno(gkfs::syscall::gkfs_stat(path, buf)); } return syscall_no_intercept(SYS_fstat, fd, buf); } Loading Loading @@ -137,7 +138,7 @@ int hook_fstatat(int dirfd, const char* cpath, struct stat* buf, int flags) { return -ENOTDIR; case RelativizeStatus::internal: return with_errno(gkfs::func::stat(resolved, buf)); return with_errno(gkfs::syscall::gkfs_stat(resolved, buf)); default: LOG(ERROR, "{}() relativize status unknown: {}", __func__); Loading @@ -151,7 +152,7 @@ int hook_read(unsigned int fd, void* buf, size_t count) { __func__, fd, fmt::ptr(buf), count); if (CTX->file_map()->exist(fd)) { return with_errno(gkfs::func::read(fd, buf, count)); return with_errno(gkfs::syscall::gkfs_read(fd, buf, count)); } return syscall_no_intercept(SYS_read, fd, buf, count); } Loading @@ -162,7 +163,7 @@ int hook_pread(unsigned int fd, char* buf, size_t count, loff_t pos) { __func__, fd, fmt::ptr(buf), count, pos); if (CTX->file_map()->exist(fd)) { return with_errno(gkfs::func::pread_ws(fd, buf, count, pos)); return with_errno(gkfs::syscall::gkfs_pread_ws(fd, buf, count, pos)); } /* Since kernel 2.6: pread() became pread64(), and pwrite() became pwrite64(). */ return syscall_no_intercept(SYS_pread64, fd, buf, count, pos); Loading @@ -174,7 +175,7 @@ int hook_write(unsigned int fd, const char* buf, size_t count) { __func__, fd, fmt::ptr(buf), count); if (CTX->file_map()->exist(fd)) { return with_errno(gkfs::func::write(fd, buf, count)); return with_errno(gkfs::syscall::gkfs_write(fd, buf, count)); } return syscall_no_intercept(SYS_write, fd, buf, count); } Loading @@ -185,7 +186,7 @@ int hook_pwrite(unsigned int fd, const char* buf, size_t count, loff_t pos) { __func__, fd, fmt::ptr(buf), count, pos); if (CTX->file_map()->exist(fd)) { return with_errno(gkfs::func::pwrite_ws(fd, buf, count, pos)); return with_errno(gkfs::syscall::gkfs_pwrite_ws(fd, buf, count, pos)); } /* Since kernel 2.6: pread() became pread64(), and pwrite() became pwrite64(). */ return syscall_no_intercept(SYS_pwrite64, fd, buf, count, pos); Loading @@ -197,7 +198,7 @@ int hook_writev(unsigned long fd, const struct iovec* iov, unsigned long iovcnt) __func__, fd, fmt::ptr(iov), iovcnt); if (CTX->file_map()->exist(fd)) { return with_errno(gkfs::func::writev(fd, iov, iovcnt)); return with_errno(gkfs::syscall::gkfs_writev(fd, iov, iovcnt)); } return syscall_no_intercept(SYS_writev, fd, iov, iovcnt); } Loading Loading @@ -240,9 +241,9 @@ int hook_unlinkat(int dirfd, const char* cpath, int flags) { case RelativizeStatus::internal: if (flags & AT_REMOVEDIR) { return with_errno(gkfs::func::rmdir(resolved)); return with_errno(gkfs::syscall::gkfs_rmdir(resolved)); } else { return with_errno(gkfs::func::rm_node(resolved)); return with_errno(gkfs::syscall::gkfs_remove(resolved)); } default: Loading Loading @@ -292,7 +293,7 @@ int hook_access(const char* path, int mask) { std::string rel_path; if (CTX->relativize_path(path, rel_path)) { auto ret = gkfs::func::access(rel_path, mask); auto ret = gkfs::syscall::gkfs_access(rel_path, mask); if (ret < 0) { return -errno; } Loading @@ -319,7 +320,7 @@ int hook_faccessat(int dirfd, const char* cpath, int mode) { return -ENOTDIR; case RelativizeStatus::internal: return with_errno(gkfs::func::access(resolved, mode)); return with_errno(gkfs::syscall::gkfs_access(resolved, mode)); default: LOG(ERROR, "{}() relativize status unknown: {}", __func__); Loading @@ -333,7 +334,7 @@ off_t hook_lseek(unsigned int fd, off_t offset, unsigned int whence) { __func__, fd, offset, whence); if (CTX->file_map()->exist(fd)) { auto off_ret = gkfs::func::lseek(fd, static_cast<off64_t>(offset), whence); auto off_ret = gkfs::syscall::gkfs_lseek(fd, static_cast<off64_t>(offset), whence); if (off_ret > std::numeric_limits<off_t>::max()) { return -EOVERFLOW; } else if (off_ret < 0) { Loading @@ -352,7 +353,7 @@ int hook_truncate(const char* path, long length) { std::string rel_path; if (CTX->relativize_path(path, rel_path)) { return with_errno(gkfs::func::truncate(rel_path, length)); return with_errno(gkfs::syscall::gkfs_truncate(rel_path, length)); } return syscall_no_intercept(SYS_truncate, rel_path.c_str(), length); } Loading @@ -364,7 +365,7 @@ int hook_ftruncate(unsigned int fd, unsigned long length) { if (CTX->file_map()->exist(fd)) { auto path = CTX->file_map()->get(fd)->path(); return with_errno(gkfs::func::truncate(path, length)); return with_errno(gkfs::syscall::gkfs_truncate(path, length)); } return syscall_no_intercept(SYS_ftruncate, fd, length); } Loading @@ -375,7 +376,7 @@ int hook_dup(unsigned int fd) { __func__, fd); if (CTX->file_map()->exist(fd)) { return with_errno(gkfs::func::dup(fd)); return with_errno(gkfs::syscall::gkfs_dup(fd)); } return syscall_no_intercept(SYS_dup, fd); } Loading @@ -386,7 +387,7 @@ int hook_dup2(unsigned int oldfd, unsigned int newfd) { __func__, oldfd, newfd); if (CTX->file_map()->exist(oldfd)) { return with_errno(gkfs::func::dup2(oldfd, newfd)); return with_errno(gkfs::syscall::gkfs_dup2(oldfd, newfd)); } return syscall_no_intercept(SYS_dup2, oldfd, newfd); } Loading @@ -411,7 +412,7 @@ int hook_getdents(unsigned int fd, struct linux_dirent* dirp, unsigned int count __func__, fd, fmt::ptr(dirp), count); if (CTX->file_map()->exist(fd)) { return with_errno(gkfs::func::getdents(fd, dirp, count)); return with_errno(gkfs::syscall::gkfs_getdents(fd, dirp, count)); } return syscall_no_intercept(SYS_getdents, fd, dirp, count); } Loading @@ -423,7 +424,7 @@ int hook_getdents64(unsigned int fd, struct linux_dirent64* dirp, unsigned int c __func__, fd, fmt::ptr(dirp), count); if (CTX->file_map()->exist(fd)) { return with_errno(gkfs::func::getdents64(fd, dirp, count)); return with_errno(gkfs::syscall::gkfs_getdents64(fd, dirp, count)); } return syscall_no_intercept(SYS_getdents64, fd, dirp, count); } Loading @@ -447,7 +448,7 @@ int hook_mkdirat(int dirfd, const char* cpath, mode_t mode) { return -ENOTDIR; case RelativizeStatus::internal: return with_errno(gkfs::func::mk_node(resolved, mode | S_IFDIR)); return with_errno(gkfs::syscall::gkfs_create(resolved, mode | S_IFDIR)); default: LOG(ERROR, "{}() relativize status unknown: {}", __func__); Loading Loading @@ -503,7 +504,7 @@ int hook_chdir(const char* path) { bool internal = CTX->relativize_path(path, rel_path); if (internal) { //path falls in our namespace auto md = gkfs::func::metadata(rel_path); auto md = gkfs::util::get_metadata(rel_path); if (md == nullptr) { LOG(ERROR, "{}() path does not exists", __func__); return -ENOENT; Loading Loading @@ -619,11 +620,11 @@ int hook_fcntl(unsigned int fd, unsigned int cmd, unsigned long arg) { case F_DUPFD: LOG(DEBUG, "{}() F_DUPFD on fd {}", __func__, fd); return with_errno(gkfs::func::dup(fd)); return with_errno(gkfs::syscall::gkfs_dup(fd)); case F_DUPFD_CLOEXEC: LOG(DEBUG, "{}() F_DUPFD_CLOEXEC on fd {}", __func__, fd); ret = gkfs::func::dup(fd); ret = gkfs::syscall::gkfs_dup(fd); if (ret == -1) { return -errno; } Loading Loading @@ -736,7 +737,7 @@ int hook_statfs(const char* path, struct statfs* buf) { std::string rel_path; if (CTX->relativize_path(path, rel_path)) { return with_errno(gkfs::func::statfs(buf)); return with_errno(gkfs::syscall::gkfs_statfs(buf)); } return syscall_no_intercept(SYS_statfs, rel_path.c_str(), buf); } Loading @@ -747,7 +748,7 @@ int hook_fstatfs(unsigned int fd, struct statfs* buf) { __func__, fd, fmt::ptr(buf)); if (CTX->file_map()->exist(fd)) { return with_errno(gkfs::func::statfs(buf)); return with_errno(gkfs::syscall::gkfs_statfs(buf)); } return syscall_no_intercept(SYS_fstatfs, fd, buf); } src/client/preload_util.cpp +70 −37 File changed.Preview size limit exceeded, changes collapsed. Show changes Loading
include/client/gkfs_functions.hpp +34 −38 Original line number Diff line number Diff line Loading @@ -36,77 +36,73 @@ using sys_statfs = struct statfs; using sys_statvfs = struct statvfs; namespace gkfs { namespace func { namespace syscall { int gkfs_open(const std::string& path, mode_t mode, int flags); std::shared_ptr<gkfs::metadata::Metadata> metadata(const std::string& path, bool follow_links = false); int gkfs_create(const std::string& path, mode_t mode); int check_parent_dir(const std::string& path); int gkfs_remove(const std::string& path); int open(const std::string& path, mode_t mode, int flags); int gkfs_access(const std::string& path, int mask, bool follow_links = true); int mk_node(const std::string& path, mode_t mode); int gkfs_stat(const std::string& path, struct stat* buf, bool follow_links = true); int rm_node(const std::string& path); int gkfs_statfs(sys_statfs* buf); int access(const std::string& path, int mask, bool follow_links = true); int gkfs_statvfs(sys_statvfs* buf); int stat(const std::string& path, struct stat* buf, bool follow_links = true); off64_t gkfs_lseek(unsigned int fd, off64_t offset, unsigned int whence); int statfs(sys_statfs* buf); off64_t gkfs_lseek(std::shared_ptr<OpenFile> gkfs_fd, off64_t offset, unsigned int whence); int statvfs(sys_statvfs* buf); int gkfs_truncate(const std::string& path, off_t offset); off64_t lseek(unsigned int fd, off64_t offset, unsigned int whence); int gkfs_truncate(const std::string& path, off_t old_size, off_t new_size); off64_t lseek(std::shared_ptr<OpenFile> gkfs_fd, off64_t offset, unsigned int whence); int gkfs_dup(int oldfd); int truncate(const std::string& path, off_t offset); int truncate(const std::string& path, off_t old_size, off_t new_size); int dup(int oldfd); int dup2(int oldfd, int newfd); int gkfs_dup2(int oldfd, int newfd); #ifdef HAS_SYMLINKS int mk_symlink(const std::string& path, const std::string& target_path); int gkfs_mk_symlink(const std::string& path, const std::string& target_path); int readlink(const std::string& path, char* buf, int bufsize); int gkfs_readlink(const std::string& path, char* buf, int bufsize); #endif ssize_t pwrite(std::shared_ptr<OpenFile> file, ssize_t gkfs_pwrite(std::shared_ptr<OpenFile> file, const char* buf, size_t count, off64_t offset); ssize_t pwrite_ws(int fd, const void* buf, size_t count, off64_t offset); ssize_t gkfs_pwrite_ws(int fd, const void* buf, size_t count, off64_t offset); ssize_t write(int fd, const void* buf, size_t count); ssize_t gkfs_write(int fd, const void* buf, size_t count); ssize_t pwritev(int fd, const struct iovec* iov, int iovcnt, off_t offset); ssize_t gkfs_pwritev(int fd, const struct iovec* iov, int iovcnt, off_t offset); ssize_t writev(int fd, const struct iovec* iov, int iovcnt); ssize_t gkfs_writev(int fd, const struct iovec* iov, int iovcnt); ssize_t pread(std::shared_ptr<OpenFile> file, char* buf, size_t count, off64_t offset); ssize_t gkfs_pread(std::shared_ptr<OpenFile> file, char* buf, size_t count, off64_t offset); ssize_t pread_ws(int fd, void* buf, size_t count, off64_t offset); ssize_t gkfs_pread_ws(int fd, void* buf, size_t count, off64_t offset); ssize_t read(int fd, void* buf, size_t count); ssize_t gkfs_read(int fd, void* buf, size_t count); int opendir(const std::string& path); int gkfs_opendir(const std::string& path); int getdents(unsigned int fd, int gkfs_getdents(unsigned int fd, struct linux_dirent* dirp, unsigned int count); int getdents64(unsigned int fd, int gkfs_getdents64(unsigned int fd, struct linux_dirent64* dirp, unsigned int count); int rmdir(const std::string& path); } } int gkfs_rmdir(const std::string& path); } // namespace syscall } // namespace gkfs #endif //GEKKOFS_GKFS_FUNCTIONS_HPP
include/client/preload_util.hpp +5 −2 Original line number Diff line number Diff line Loading @@ -48,12 +48,15 @@ constexpr typename std::underlying_type<E>::type to_underlying(E e) { return static_cast<typename std::underlying_type<E>::type>(e); } std::shared_ptr<gkfs::metadata::Metadata> get_metadata(const std::string& path, bool follow_links = false); int metadata_to_stat(const std::string& path, const gkfs::metadata::Metadata& md, struct stat& attr); std::vector<std::pair<std::string, std::string>> load_hostfile(const std::string& lfpath); void load_hosts(); } } } // namespace util } // namespace gkfs #endif //GEKKOFS_PRELOAD_UTIL_HPP
src/client/gkfs_functions.cpp +65 −77 Original line number Diff line number Diff line Loading @@ -34,31 +34,12 @@ extern "C" { using namespace std; std::shared_ptr<gkfs::metadata::Metadata> gkfs::func::metadata(const string& path, bool follow_links) { std::string attr; auto err = gkfs::rpc::forward_stat(path, attr); if (err) { return nullptr; } #ifdef HAS_SYMLINKS if (follow_links) { gkfs::metadata::Metadata md{attr}; while (md.is_link()) { err = gkfs::rpc::forward_stat(md.target_path(), attr); if (err) { return nullptr; } md = gkfs::metadata::Metadata{attr}; } } #endif return make_shared<gkfs::metadata::Metadata>(attr); } namespace { int gkfs::func::check_parent_dir(const std::string& path) { int check_parent_dir(const std::string& path) { #if CREATE_CHECK_PARENTS auto p_comp = path::dirname(path); auto md = gkfs::func::metadata(p_comp); auto p_comp = gkfs::path::dirname(path); auto md = gkfs::util::get_metadata(p_comp); if (!md) { if (errno == ENOENT) { LOG(DEBUG, "Parent component does not exist: '{}'", p_comp); Loading @@ -75,8 +56,12 @@ int gkfs::func::check_parent_dir(const std::string& path) { #endif // CREATE_CHECK_PARENTS return 0; } } // namespace int gkfs::func::open(const std::string& path, mode_t mode, int flags) { namespace gkfs { namespace syscall { int gkfs_open(const std::string& path, mode_t mode, int flags) { if (flags & O_PATH) { LOG(ERROR, "`O_PATH` flag is not supported"); Loading @@ -91,7 +76,7 @@ int gkfs::func::open(const std::string& path, mode_t mode, int flags) { } bool exists = true; auto md = gkfs::func::metadata(path); auto md = gkfs::util::get_metadata(path); if (!md) { if (errno == ENOENT) { exists = false; Loading @@ -118,7 +103,7 @@ int gkfs::func::open(const std::string& path, mode_t mode, int flags) { } // no access check required here. If one is using our FS they have the permissions. if (gkfs::func::mk_node(path, mode | S_IFREG)) { if (gkfs_create(path, mode | S_IFREG)) { LOG(ERROR, "Error creating non-existent file: '{}'", strerror(errno)); return -1; } Loading @@ -138,12 +123,12 @@ int gkfs::func::open(const std::string& path, mode_t mode, int flags) { errno = ELOOP; return -1; } return gkfs::func::open(md->target_path(), mode, flags); return gkfs_open(md->target_path(), mode, flags); } #endif if (S_ISDIR(md->mode())) { return gkfs::func::opendir(path); return gkfs_opendir(path); } Loading @@ -151,7 +136,7 @@ int gkfs::func::open(const std::string& path, mode_t mode, int flags) { assert(S_ISREG(md->mode())); if ((flags & O_TRUNC) && ((flags & O_RDWR) || (flags & O_WRONLY))) { if (gkfs::func::truncate(path, md->size(), 0)) { if (gkfs_truncate(path, md->size(), 0)) { LOG(ERROR, "Error truncating file"); return -1; } Loading @@ -161,7 +146,7 @@ int gkfs::func::open(const std::string& path, mode_t mode, int flags) { return CTX->file_map()->add(std::make_shared<OpenFile>(path, flags)); } int gkfs::func::mk_node(const std::string& path, mode_t mode) { int gkfs_create(const std::string& path, mode_t mode) { //file type must be set switch (mode & S_IFMT) { Loading Loading @@ -195,8 +180,8 @@ int gkfs::func::mk_node(const std::string& path, mode_t mode) { * @param path * @return */ int gkfs::func::rm_node(const std::string& path) { auto md = gkfs::func::metadata(path); int gkfs_remove(const std::string& path) { auto md = gkfs::util::get_metadata(path); if (!md) { return -1; } Loading @@ -204,8 +189,8 @@ int gkfs::func::rm_node(const std::string& path) { return gkfs::rpc::forward_remove(path, !has_data, md->size()); } int gkfs::func::access(const std::string& path, const int mask, bool follow_links) { auto md = gkfs::func::metadata(path, follow_links); int gkfs_access(const std::string& path, const int mask, bool follow_links) { auto md = gkfs::util::get_metadata(path, follow_links); if (!md) { errno = ENOENT; return -1; Loading @@ -213,8 +198,8 @@ int gkfs::func::access(const std::string& path, const int mask, bool follow_link return 0; } int gkfs::func::stat(const string& path, struct stat* buf, bool follow_links) { auto md = gkfs::func::metadata(path, follow_links); int gkfs_stat(const string& path, struct stat* buf, bool follow_links) { auto md = gkfs::util::get_metadata(path, follow_links); if (!md) { return -1; } Loading @@ -222,7 +207,7 @@ int gkfs::func::stat(const string& path, struct stat* buf, bool follow_links) { return 0; } int gkfs::func::statfs(sys_statfs* buf) { int gkfs_statfs(sys_statfs* buf) { auto blk_stat = gkfs::rpc::forward_get_chunk_stat(); buf->f_type = 0; buf->f_bsize = blk_stat.chunk_size; Loading @@ -239,7 +224,7 @@ int gkfs::func::statfs(sys_statfs* buf) { return 0; } int gkfs::func::statvfs(sys_statvfs* buf) { int gkfs_statvfs(sys_statvfs* buf) { init_ld_env_if_needed(); auto blk_stat = gkfs::rpc::forward_get_chunk_stat(); buf->f_bsize = blk_stat.chunk_size; Loading @@ -257,11 +242,11 @@ int gkfs::func::statvfs(sys_statvfs* buf) { return 0; } off_t gkfs::func::lseek(unsigned int fd, off_t offset, unsigned int whence) { return gkfs::func::lseek(CTX->file_map()->get(fd), offset, whence); off_t gkfs_lseek(unsigned int fd, off_t offset, unsigned int whence) { return gkfs_lseek(CTX->file_map()->get(fd), offset, whence); } off_t gkfs::func::lseek(shared_ptr<OpenFile> gkfs_fd, off_t offset, unsigned int whence) { off_t gkfs_lseek(shared_ptr<OpenFile> gkfs_fd, off_t offset, unsigned int whence) { switch (whence) { case SEEK_SET: gkfs_fd->pos(offset); Loading Loading @@ -297,7 +282,7 @@ off_t gkfs::func::lseek(shared_ptr<OpenFile> gkfs_fd, off_t offset, unsigned int return gkfs_fd->pos(); } int gkfs::func::truncate(const std::string& path, off_t old_size, off_t new_size) { int gkfs_truncate(const std::string& path, off_t old_size, off_t new_size) { assert(new_size >= 0); assert(new_size <= old_size); Loading @@ -317,7 +302,7 @@ int gkfs::func::truncate(const std::string& path, off_t old_size, off_t new_size return 0; } int gkfs::func::truncate(const std::string& path, off_t length) { int gkfs_truncate(const std::string& path, off_t length) { /* TODO CONCURRENCY: * At the moment we first ask the length to the metadata-server in order to * know which data-server have data to be deleted. Loading @@ -332,7 +317,7 @@ int gkfs::func::truncate(const std::string& path, off_t length) { return -1; } auto md = gkfs::func::metadata(path, true); auto md = gkfs::util::get_metadata(path, true); if (!md) { return -1; } Loading @@ -342,18 +327,18 @@ int gkfs::func::truncate(const std::string& path, off_t length) { errno = EINVAL; return -1; } return gkfs::func::truncate(path, size, length); return gkfs_truncate(path, size, length); } int gkfs::func::dup(const int oldfd) { int gkfs_dup(const int oldfd) { return CTX->file_map()->dup(oldfd); } int gkfs::func::dup2(const int oldfd, const int newfd) { int gkfs_dup2(const int oldfd, const int newfd) { return CTX->file_map()->dup2(oldfd, newfd); } ssize_t gkfs::func::pwrite(std::shared_ptr<OpenFile> file, const char* buf, size_t count, off64_t offset) { ssize_t gkfs_pwrite(std::shared_ptr<OpenFile> file, const char* buf, size_t count, off64_t offset) { if (file->type() != FileType::regular) { assert(file->type() == FileType::directory); LOG(WARNING, "Cannot read from directory"); Loading @@ -377,9 +362,9 @@ ssize_t gkfs::func::pwrite(std::shared_ptr<OpenFile> file, const char* buf, size return ret; // return written size or -1 as error } ssize_t gkfs::func::pwrite_ws(int fd, const void* buf, size_t count, off64_t offset) { ssize_t gkfs_pwrite_ws(int fd, const void* buf, size_t count, off64_t offset) { auto file = CTX->file_map()->get(fd); return gkfs::func::pwrite(file, reinterpret_cast<const char*>(buf), count, offset); return gkfs_pwrite(file, reinterpret_cast<const char*>(buf), count, offset); } /* Write counts bytes starting from current file position Loading @@ -387,12 +372,12 @@ ssize_t gkfs::func::pwrite_ws(int fd, const void* buf, size_t count, off64_t off * * Same as write syscall. */ ssize_t gkfs::func::write(int fd, const void* buf, size_t count) { ssize_t gkfs_write(int fd, const void* buf, size_t count) { auto gkfs_fd = CTX->file_map()->get(fd); auto pos = gkfs_fd->pos(); //retrieve the current offset if (gkfs_fd->get_flag(OpenFile_flags::append)) gkfs::func::lseek(gkfs_fd, 0, SEEK_END); auto ret = gkfs::func::pwrite(gkfs_fd, reinterpret_cast<const char*>(buf), count, pos); gkfs_lseek(gkfs_fd, 0, SEEK_END); auto ret = gkfs_pwrite(gkfs_fd, reinterpret_cast<const char*>(buf), count, pos); // Update offset in file descriptor in the file map if (ret > 0) { gkfs_fd->pos(pos + count); Loading @@ -400,7 +385,7 @@ ssize_t gkfs::func::write(int fd, const void* buf, size_t count) { return ret; } ssize_t gkfs::func::pwritev(int fd, const struct iovec* iov, int iovcnt, off_t offset) { ssize_t gkfs_pwritev(int fd, const struct iovec* iov, int iovcnt, off_t offset) { auto file = CTX->file_map()->get(fd); auto pos = offset; // keep truck of current position Loading @@ -412,7 +397,7 @@ ssize_t gkfs::func::pwritev(int fd, const struct iovec* iov, int iovcnt, off_t o continue; } auto buf = (iov + i)->iov_base; ret = gkfs::func::pwrite(file, reinterpret_cast<char*>(buf), count, pos); ret = gkfs_pwrite(file, reinterpret_cast<char*>(buf), count, pos); if (ret == -1) { break; } Loading @@ -430,11 +415,11 @@ ssize_t gkfs::func::pwritev(int fd, const struct iovec* iov, int iovcnt, off_t o return written; } ssize_t gkfs::func::writev(int fd, const struct iovec* iov, int iovcnt) { ssize_t gkfs_writev(int fd, const struct iovec* iov, int iovcnt) { auto gkfs_fd = CTX->file_map()->get(fd); auto pos = gkfs_fd->pos(); // retrieve the current offset auto ret = gkfs::func::pwritev(fd, iov, iovcnt, pos); auto ret = gkfs_pwritev(fd, iov, iovcnt, pos); assert(ret != 0); if (ret < 0) { return -1; Loading @@ -443,7 +428,7 @@ ssize_t gkfs::func::writev(int fd, const struct iovec* iov, int iovcnt) { return ret; } ssize_t gkfs::func::pread(std::shared_ptr<OpenFile> file, char* buf, size_t count, off64_t offset) { ssize_t gkfs_pread(std::shared_ptr<OpenFile> file, char* buf, size_t count, off64_t offset) { if (file->type() != FileType::regular) { assert(file->type() == FileType::directory); LOG(WARNING, "Cannot read from directory"); Loading @@ -463,10 +448,10 @@ ssize_t gkfs::func::pread(std::shared_ptr<OpenFile> file, char* buf, size_t coun return ret; // return read size or -1 as error } ssize_t gkfs::func::read(int fd, void* buf, size_t count) { ssize_t gkfs_read(int fd, void* buf, size_t count) { auto gkfs_fd = CTX->file_map()->get(fd); auto pos = gkfs_fd->pos(); //retrieve the current offset auto ret = gkfs::func::pread(gkfs_fd, reinterpret_cast<char*>(buf), count, pos); auto ret = gkfs_pread(gkfs_fd, reinterpret_cast<char*>(buf), count, pos); // Update offset in file descriptor in the file map if (ret > 0) { gkfs_fd->pos(pos + ret); Loading @@ -474,14 +459,14 @@ ssize_t gkfs::func::read(int fd, void* buf, size_t count) { return ret; } ssize_t gkfs::func::pread_ws(int fd, void* buf, size_t count, off64_t offset) { ssize_t gkfs_pread_ws(int fd, void* buf, size_t count, off64_t offset) { auto gkfs_fd = CTX->file_map()->get(fd); return gkfs::func::pread(gkfs_fd, reinterpret_cast<char*>(buf), count, offset); return gkfs_pread(gkfs_fd, reinterpret_cast<char*>(buf), count, offset); } int gkfs::func::opendir(const std::string& path) { int gkfs_opendir(const std::string& path) { auto md = gkfs::func::metadata(path); auto md = gkfs::util::get_metadata(path); if (!md) { return -1; } Loading @@ -496,8 +481,8 @@ int gkfs::func::opendir(const std::string& path) { return CTX->file_map()->add(open_dir); } int gkfs::func::rmdir(const std::string& path) { auto md = gkfs::func::metadata(path); int gkfs_rmdir(const std::string& path) { auto md = gkfs::util::get_metadata(path); if (!md) { LOG(DEBUG, "Path '{}' does not exist: ", path); errno = ENOENT; Loading @@ -518,7 +503,7 @@ int gkfs::func::rmdir(const std::string& path) { return gkfs::rpc::forward_remove(path, true, 0); } int gkfs::func::getdents(unsigned int fd, int gkfs_getdents(unsigned int fd, struct linux_dirent* dirp, unsigned int count) { Loading Loading @@ -571,7 +556,7 @@ int gkfs::func::getdents(unsigned int fd, } int gkfs::func::getdents64(unsigned int fd, int gkfs_getdents64(unsigned int fd, struct linux_dirent64* dirp, unsigned int count) { Loading Loading @@ -624,14 +609,14 @@ int gkfs::func::getdents64(unsigned int fd, #ifdef HAS_SYMLINKS int gkfs::func::mk_symlink(const std::string& path, const std::string& target_path) { int gkfs_mk_symlink(const std::string& path, const std::string& target_path) { init_ld_env_if_needed(); /* The following check is not POSIX compliant. * In POSIX the target is not checked at all. * Here if the target is a directory we raise a NOTSUP error. * So that application know we don't support link to directory. */ auto target_md = gkfs::func::metadata(target_path, false); auto target_md = gkfs::util::get_metadata(target_path, false); if (target_md != nullptr) { auto trg_mode = target_md->mode(); if (!(S_ISREG(trg_mode) || S_ISLNK(trg_mode))) { Loading @@ -646,7 +631,7 @@ int gkfs::func::mk_symlink(const std::string& path, const std::string& target_pa return -1; } auto link_md = gkfs::func::metadata(path, false); auto link_md = gkfs::util::get_metadata(path, false); if (link_md != nullptr) { LOG(DEBUG, "Link exists: '{}'", path); errno = EEXIST; Loading @@ -656,9 +641,9 @@ int gkfs::func::mk_symlink(const std::string& path, const std::string& target_pa return gkfs::rpc::forward_mk_symlink(path, target_path); } int gkfs::func::readlink(const std::string& path, char* buf, int bufsize) { int gkfs_readlink(const std::string& path, char* buf, int bufsize) { init_ld_env_if_needed(); auto md = gkfs::func::metadata(path, false); auto md = gkfs::util::get_metadata(path, false); if (md == nullptr) { LOG(DEBUG, "Named link doesn't exist"); return -1; Loading @@ -680,4 +665,7 @@ int gkfs::func::readlink(const std::string& path, char* buf, int bufsize) { return path_size; } } // namespace syscall } // namespace gkfs #endif No newline at end of file
src/client/hooks.cpp +28 −27 Original line number Diff line number Diff line Loading @@ -13,6 +13,7 @@ #include <client/hooks.hpp> #include <client/preload.hpp> #include <client/preload_util.hpp> #include <client/logging.hpp> #include <client/gkfs_functions.hpp> #include <client/path.hpp> Loading Loading @@ -51,7 +52,7 @@ int hook_openat(int dirfd, const char* cpath, int flags, mode_t mode) { return -ENOTDIR; case RelativizeStatus::internal: return with_errno(gkfs::func::open(resolved, mode, flags)); return with_errno(gkfs::syscall::gkfs_open(resolved, mode, flags)); default: LOG(ERROR, "{}() relativize status unknown: {}", __func__); Loading Loading @@ -85,7 +86,7 @@ int hook_stat(const char* path, struct stat* buf) { std::string rel_path; if (CTX->relativize_path(path, rel_path, false)) { return with_errno(gkfs::func::stat(rel_path, buf)); return with_errno(gkfs::syscall::gkfs_stat(rel_path, buf)); } return syscall_no_intercept(SYS_stat, rel_path.c_str(), buf); } Loading @@ -97,7 +98,7 @@ int hook_lstat(const char* path, struct stat* buf) { std::string rel_path; if (CTX->relativize_path(path, rel_path)) { return with_errno(gkfs::func::stat(rel_path, buf)); return with_errno(gkfs::syscall::gkfs_stat(rel_path, buf)); } return syscall_no_intercept(SYS_lstat, rel_path.c_str(), buf); } Loading @@ -109,7 +110,7 @@ int hook_fstat(unsigned int fd, struct stat* buf) { if (CTX->file_map()->exist(fd)) { auto path = CTX->file_map()->get(fd)->path(); return with_errno(gkfs::func::stat(path, buf)); return with_errno(gkfs::syscall::gkfs_stat(path, buf)); } return syscall_no_intercept(SYS_fstat, fd, buf); } Loading Loading @@ -137,7 +138,7 @@ int hook_fstatat(int dirfd, const char* cpath, struct stat* buf, int flags) { return -ENOTDIR; case RelativizeStatus::internal: return with_errno(gkfs::func::stat(resolved, buf)); return with_errno(gkfs::syscall::gkfs_stat(resolved, buf)); default: LOG(ERROR, "{}() relativize status unknown: {}", __func__); Loading @@ -151,7 +152,7 @@ int hook_read(unsigned int fd, void* buf, size_t count) { __func__, fd, fmt::ptr(buf), count); if (CTX->file_map()->exist(fd)) { return with_errno(gkfs::func::read(fd, buf, count)); return with_errno(gkfs::syscall::gkfs_read(fd, buf, count)); } return syscall_no_intercept(SYS_read, fd, buf, count); } Loading @@ -162,7 +163,7 @@ int hook_pread(unsigned int fd, char* buf, size_t count, loff_t pos) { __func__, fd, fmt::ptr(buf), count, pos); if (CTX->file_map()->exist(fd)) { return with_errno(gkfs::func::pread_ws(fd, buf, count, pos)); return with_errno(gkfs::syscall::gkfs_pread_ws(fd, buf, count, pos)); } /* Since kernel 2.6: pread() became pread64(), and pwrite() became pwrite64(). */ return syscall_no_intercept(SYS_pread64, fd, buf, count, pos); Loading @@ -174,7 +175,7 @@ int hook_write(unsigned int fd, const char* buf, size_t count) { __func__, fd, fmt::ptr(buf), count); if (CTX->file_map()->exist(fd)) { return with_errno(gkfs::func::write(fd, buf, count)); return with_errno(gkfs::syscall::gkfs_write(fd, buf, count)); } return syscall_no_intercept(SYS_write, fd, buf, count); } Loading @@ -185,7 +186,7 @@ int hook_pwrite(unsigned int fd, const char* buf, size_t count, loff_t pos) { __func__, fd, fmt::ptr(buf), count, pos); if (CTX->file_map()->exist(fd)) { return with_errno(gkfs::func::pwrite_ws(fd, buf, count, pos)); return with_errno(gkfs::syscall::gkfs_pwrite_ws(fd, buf, count, pos)); } /* Since kernel 2.6: pread() became pread64(), and pwrite() became pwrite64(). */ return syscall_no_intercept(SYS_pwrite64, fd, buf, count, pos); Loading @@ -197,7 +198,7 @@ int hook_writev(unsigned long fd, const struct iovec* iov, unsigned long iovcnt) __func__, fd, fmt::ptr(iov), iovcnt); if (CTX->file_map()->exist(fd)) { return with_errno(gkfs::func::writev(fd, iov, iovcnt)); return with_errno(gkfs::syscall::gkfs_writev(fd, iov, iovcnt)); } return syscall_no_intercept(SYS_writev, fd, iov, iovcnt); } Loading Loading @@ -240,9 +241,9 @@ int hook_unlinkat(int dirfd, const char* cpath, int flags) { case RelativizeStatus::internal: if (flags & AT_REMOVEDIR) { return with_errno(gkfs::func::rmdir(resolved)); return with_errno(gkfs::syscall::gkfs_rmdir(resolved)); } else { return with_errno(gkfs::func::rm_node(resolved)); return with_errno(gkfs::syscall::gkfs_remove(resolved)); } default: Loading Loading @@ -292,7 +293,7 @@ int hook_access(const char* path, int mask) { std::string rel_path; if (CTX->relativize_path(path, rel_path)) { auto ret = gkfs::func::access(rel_path, mask); auto ret = gkfs::syscall::gkfs_access(rel_path, mask); if (ret < 0) { return -errno; } Loading @@ -319,7 +320,7 @@ int hook_faccessat(int dirfd, const char* cpath, int mode) { return -ENOTDIR; case RelativizeStatus::internal: return with_errno(gkfs::func::access(resolved, mode)); return with_errno(gkfs::syscall::gkfs_access(resolved, mode)); default: LOG(ERROR, "{}() relativize status unknown: {}", __func__); Loading @@ -333,7 +334,7 @@ off_t hook_lseek(unsigned int fd, off_t offset, unsigned int whence) { __func__, fd, offset, whence); if (CTX->file_map()->exist(fd)) { auto off_ret = gkfs::func::lseek(fd, static_cast<off64_t>(offset), whence); auto off_ret = gkfs::syscall::gkfs_lseek(fd, static_cast<off64_t>(offset), whence); if (off_ret > std::numeric_limits<off_t>::max()) { return -EOVERFLOW; } else if (off_ret < 0) { Loading @@ -352,7 +353,7 @@ int hook_truncate(const char* path, long length) { std::string rel_path; if (CTX->relativize_path(path, rel_path)) { return with_errno(gkfs::func::truncate(rel_path, length)); return with_errno(gkfs::syscall::gkfs_truncate(rel_path, length)); } return syscall_no_intercept(SYS_truncate, rel_path.c_str(), length); } Loading @@ -364,7 +365,7 @@ int hook_ftruncate(unsigned int fd, unsigned long length) { if (CTX->file_map()->exist(fd)) { auto path = CTX->file_map()->get(fd)->path(); return with_errno(gkfs::func::truncate(path, length)); return with_errno(gkfs::syscall::gkfs_truncate(path, length)); } return syscall_no_intercept(SYS_ftruncate, fd, length); } Loading @@ -375,7 +376,7 @@ int hook_dup(unsigned int fd) { __func__, fd); if (CTX->file_map()->exist(fd)) { return with_errno(gkfs::func::dup(fd)); return with_errno(gkfs::syscall::gkfs_dup(fd)); } return syscall_no_intercept(SYS_dup, fd); } Loading @@ -386,7 +387,7 @@ int hook_dup2(unsigned int oldfd, unsigned int newfd) { __func__, oldfd, newfd); if (CTX->file_map()->exist(oldfd)) { return with_errno(gkfs::func::dup2(oldfd, newfd)); return with_errno(gkfs::syscall::gkfs_dup2(oldfd, newfd)); } return syscall_no_intercept(SYS_dup2, oldfd, newfd); } Loading @@ -411,7 +412,7 @@ int hook_getdents(unsigned int fd, struct linux_dirent* dirp, unsigned int count __func__, fd, fmt::ptr(dirp), count); if (CTX->file_map()->exist(fd)) { return with_errno(gkfs::func::getdents(fd, dirp, count)); return with_errno(gkfs::syscall::gkfs_getdents(fd, dirp, count)); } return syscall_no_intercept(SYS_getdents, fd, dirp, count); } Loading @@ -423,7 +424,7 @@ int hook_getdents64(unsigned int fd, struct linux_dirent64* dirp, unsigned int c __func__, fd, fmt::ptr(dirp), count); if (CTX->file_map()->exist(fd)) { return with_errno(gkfs::func::getdents64(fd, dirp, count)); return with_errno(gkfs::syscall::gkfs_getdents64(fd, dirp, count)); } return syscall_no_intercept(SYS_getdents64, fd, dirp, count); } Loading @@ -447,7 +448,7 @@ int hook_mkdirat(int dirfd, const char* cpath, mode_t mode) { return -ENOTDIR; case RelativizeStatus::internal: return with_errno(gkfs::func::mk_node(resolved, mode | S_IFDIR)); return with_errno(gkfs::syscall::gkfs_create(resolved, mode | S_IFDIR)); default: LOG(ERROR, "{}() relativize status unknown: {}", __func__); Loading Loading @@ -503,7 +504,7 @@ int hook_chdir(const char* path) { bool internal = CTX->relativize_path(path, rel_path); if (internal) { //path falls in our namespace auto md = gkfs::func::metadata(rel_path); auto md = gkfs::util::get_metadata(rel_path); if (md == nullptr) { LOG(ERROR, "{}() path does not exists", __func__); return -ENOENT; Loading Loading @@ -619,11 +620,11 @@ int hook_fcntl(unsigned int fd, unsigned int cmd, unsigned long arg) { case F_DUPFD: LOG(DEBUG, "{}() F_DUPFD on fd {}", __func__, fd); return with_errno(gkfs::func::dup(fd)); return with_errno(gkfs::syscall::gkfs_dup(fd)); case F_DUPFD_CLOEXEC: LOG(DEBUG, "{}() F_DUPFD_CLOEXEC on fd {}", __func__, fd); ret = gkfs::func::dup(fd); ret = gkfs::syscall::gkfs_dup(fd); if (ret == -1) { return -errno; } Loading Loading @@ -736,7 +737,7 @@ int hook_statfs(const char* path, struct statfs* buf) { std::string rel_path; if (CTX->relativize_path(path, rel_path)) { return with_errno(gkfs::func::statfs(buf)); return with_errno(gkfs::syscall::gkfs_statfs(buf)); } return syscall_no_intercept(SYS_statfs, rel_path.c_str(), buf); } Loading @@ -747,7 +748,7 @@ int hook_fstatfs(unsigned int fd, struct statfs* buf) { __func__, fd, fmt::ptr(buf)); if (CTX->file_map()->exist(fd)) { return with_errno(gkfs::func::statfs(buf)); return with_errno(gkfs::syscall::gkfs_statfs(buf)); } return syscall_no_intercept(SYS_fstatfs, fd, buf); }
src/client/preload_util.cpp +70 −37 File changed.Preview size limit exceeded, changes collapsed. Show changes