From ca66cebf1a42cc16997e7782bb45f6f3c0fcd29f Mon Sep 17 00:00:00 2001 From: Antonio SJ Musumeci Date: Thu, 13 Nov 2025 21:47:02 -0600 Subject: [PATCH] checkpoint --- src/follow_symlinks_enum.hpp | 9 +++++ src/fs_stat.cpp | 70 ++++++++++++++++++++++++++++++++++++ src/func_getattr_base.hpp | 35 ++++++++++++++++++ src/func_getattr_ff.cpp | 42 ++++++++++++++++++++++ src/func_getattr_ff.hpp | 23 ++++++++++++ 5 files changed, 179 insertions(+) create mode 100644 src/follow_symlinks_enum.hpp create mode 100644 src/fs_stat.cpp create mode 100644 src/func_getattr_base.hpp create mode 100644 src/func_getattr_ff.cpp create mode 100644 src/func_getattr_ff.hpp diff --git a/src/follow_symlinks_enum.hpp b/src/follow_symlinks_enum.hpp new file mode 100644 index 00000000..c708b898 --- /dev/null +++ b/src/follow_symlinks_enum.hpp @@ -0,0 +1,9 @@ +#pragma once + +enum class FollowSymlinksEnum + { + NEVER, + DIRECTORY, + REGULAR, + ALL + }; diff --git a/src/fs_stat.cpp b/src/fs_stat.cpp new file mode 100644 index 00000000..c894a403 --- /dev/null +++ b/src/fs_stat.cpp @@ -0,0 +1,70 @@ +#include "fs_stat.hpp" +#include "fs_lstat.hpp" + +static +void +_set_stat_if_leads_to_dir(const char *path_, + struct stat *st_) +{ + int rv; + struct stat st; + + rv = fs::stat(path_,&st); + if(rv < 0) + return; + + if(S_ISDIR(st.st_mode)) + *st_ = st; + + return; +} + +static +void +_set_stat_if_leads_to_reg(const char *path_, + struct stat *st_) +{ + int rv; + struct stat st; + + rv = fs::stat(path_,&st); + if(rv < 0) + return; + + if(S_ISREG(st.st_mode)) + *st_ = st; + + return; +} + +int +fs::stat(const char *path_, + struct stat *st_, + FollowSymlinksEnum follow_) +{ + int rv; + + switch(follow_) + { + case FollowSymlinksEnum::NEVER: + rv = fs::lstat(path_,st_); + break; + case FollowSymlinksEnum::DIRECTORY: + rv = fs::lstat(path_,st_); + if(S_ISLNK(st_->st_mode)) + _set_stat_if_leads_to_dir(path_,st_); + break; + case FollowSymlinksEnum::REGULAR: + rv = fs::lstat(path_,st_); + if(S_ISLNK(st_->st_mode)) + _set_stat_if_leads_to_reg(path_,st_); + break; + case FollowSymlinksEnum::ALL: + rv = fs::stat(path_,st_); + if(rv != 0) + rv = fs::lstat(path_,st_); + break; + } + + return rv; +} diff --git a/src/func_getattr_base.hpp b/src/func_getattr_base.hpp new file mode 100644 index 00000000..6f89b750 --- /dev/null +++ b/src/func_getattr_base.hpp @@ -0,0 +1,35 @@ +#pragma once + +#include "follow_symlinks_enum.hpp" + +#include "fs_path.hpp" +#include "branches.hpp" +#include "int_types.h" + +#include "fuse.h" + +#include + +#include +#include +#include + +namespace Func2 +{ + class GetAttrBase + { + public: + GetAttrBase() {} + ~GetAttrBase() {} + + public: + virtual std::string_view name() const = 0; + + public: + virtual int operator()(const Branches &branches, + const fs::path &fusepath, + struct stat *st, + const FollowSymlinksEnum follow_symlinks, + const s64 symlinkify_timeout) = 0; + }; +} diff --git a/src/func_getattr_ff.cpp b/src/func_getattr_ff.cpp new file mode 100644 index 00000000..6bd02572 --- /dev/null +++ b/src/func_getattr_ff.cpp @@ -0,0 +1,42 @@ +#include "func_getattr_ff.hpp" + +#include "fs_stat.hpp" +#include "fs_inode.hpp" +#include "symlinkify.hpp" + + +std::string_view +Func2::GetAttrFF::name() const +{ + return "ff"; +} + +int +Func2::GetAttrFF::operator()(const Branches &branches_, + const fs::path &fusepath_, + struct stat *st_, + const FollowSymlinksEnum follow_symlinks_, + const s64 symlinkify_timeout_) +{ + int rv; + fs::path fullpath; + + for(const auto &branch : branches_) + { + fullpath = branch.path; + fullpath += fusepath_; + rv = fs::stat(fullpath.string(),st_,follow_symlinks_); + if(rv != 0) + continue; + + symlinkify::convert_if_can_be_symlink(fullpath, + st_, + symlinkify_timeout_); + + fs::inode::calc(branch.path,fusepath_.string(),st_); + + return 0; + } + + return -ENOENT; +} diff --git a/src/func_getattr_ff.hpp b/src/func_getattr_ff.hpp new file mode 100644 index 00000000..e3d4b18f --- /dev/null +++ b/src/func_getattr_ff.hpp @@ -0,0 +1,23 @@ +#pragma once + +#include "func_getattr_base.hpp" + +namespace Func2 +{ + class GetAttrFF : public GetAttrBase + { + public: + GetAttrFF() {} + ~GetAttrFF() {} + + public: + std::string_view name() const; + + public: + int operator()(const Branches &branches, + const fs::path &fusepath, + struct stat *st, + const FollowSymlinksEnum follow_symlinks, + const s64 symlinkify_timeout); + }; +}