diff options
Diffstat (limited to 'netfs/daemon/daemonVolume.cpp')
-rw-r--r-- | netfs/daemon/daemonVolume.cpp | 243 |
1 files changed, 243 insertions, 0 deletions
diff --git a/netfs/daemon/daemonVolume.cpp b/netfs/daemon/daemonVolume.cpp new file mode 100644 index 0000000..b87958b --- /dev/null +++ b/netfs/daemon/daemonVolume.cpp @@ -0,0 +1,243 @@ +#include "pch.hpp" +#include <errno.h> +#include <map> +#include <unistd.h> +#include <sys/stat.h> +#include <limits.h> +#include <fcntl.h> +#include <typeConvert.h> +#include "daemonVolume.h" +#include "daemonFile.h" +#include "daemonDirectory.h" + +extern std::map<Ice::Int, int> files; + +VolumeServer::VolumeServer(const boost::filesystem::path & r) : + root(r) +{ +} + +VolumeServer::~VolumeServer() +{ +} + +void +VolumeServer::disconnect(const Ice::Current & ice) +{ + ice.adapter->remove(ice.id); +} + +Ice::Int +VolumeServer::access(const NetFS::ReqEnv & re, const std::string & path, Ice::Int mode, const Ice::Current &) +{ + TempPrivs tp(re, &uentries, &gentries); + boost::filesystem::path p = root / path; + return ::access(p.string().c_str(), mode); +} + +NetFS::Attr +VolumeServer::getattr(const NetFS::ReqEnv & re, const std::string & path, const Ice::Current &) +{ + TempPrivs tp(re, &uentries, &gentries); + struct stat s; + boost::filesystem::path p = root / path; + if (::lstat(p.string().c_str(), &s) != 0) { + throw NetFS::SystemError(errno); + } + NetFS::Attr a; + a << StatSource { s, boost::bind(&UserEntCache::getName, &uentries, _1), boost::bind(&GroupEntCache::getName, &gentries, _1) }; + return a; +} + +void +VolumeServer::symlink(const NetFS::ReqEnv & re, const std::string & path1, const std::string & path2, const Ice::Current &) +{ + TempPrivs tp(re, &uentries, &gentries); + errno = 0; + boost::filesystem::path p = root / path2; + if (::symlink(path1.c_str(), p.string().c_str()) != 0) { + throw NetFS::SystemError(errno); + } +} + +void +VolumeServer::link(const NetFS::ReqEnv & re, const std::string & path1, const std::string & path2, const Ice::Current &) +{ + TempPrivs tp(re, &uentries, &gentries); + errno = 0; + boost::filesystem::path p1 = root / path1; + boost::filesystem::path p2 = root / path2; + if (::link(p1.string().c_str(), p2.string().c_str()) != 0) { + throw NetFS::SystemError(errno); + } +} + +void +VolumeServer::rename(const NetFS::ReqEnv & re, const std::string & from, const std::string & to, const Ice::Current &) +{ + TempPrivs tp(re, &uentries, &gentries); + errno = 0; + boost::filesystem::path f = root / from; + boost::filesystem::path t = root / to; + if (::rename(f.string().c_str(), t.string().c_str()) != 0) { + throw NetFS::SystemError(errno); + } +} + +std::string +VolumeServer::readlink(const NetFS::ReqEnv & re, const std::string & path, const Ice::Current &) +{ + TempPrivs tp(re, &uentries, &gentries); + errno = 0; + char buf[PATH_MAX]; + boost::filesystem::path p = root / path; + ssize_t rc = ::readlink(p.string().c_str(), buf, PATH_MAX); + if (rc == -1) { + throw NetFS::SystemError(errno); + } + return std::string(buf, rc); +} + +void +VolumeServer::chmod(const NetFS::ReqEnv & re, const std::string & path, Ice::Int mode, const Ice::Current &) +{ + TempPrivs tp(re, &uentries, &gentries); + errno = 0; + boost::filesystem::path p = root / path; + if (::chmod(p.string().c_str(), mode) != 0) { + throw NetFS::SystemError(errno); + } +} + +void +VolumeServer::chown(const NetFS::ReqEnv & re, const std::string & path, Ice::Int uid, Ice::Int gid, const Ice::Current &) +{ + TempPrivs tp(re, &uentries, &gentries); + errno = 0; + boost::filesystem::path p = root / path; + if (::lchown(p.string().c_str(), uid, gid) != 0) { + throw NetFS::SystemError(errno); + } +} + +void +VolumeServer::utimens(const NetFS::ReqEnv & re, const std::string & path, + Ice::Long s0, Ice::Long ns0, Ice::Long s1, Ice::Long ns1, const Ice::Current&) +{ + TempPrivs tp(re, &uentries, &gentries); + errno = 0; + struct timespec times[2]; + times[0].tv_sec = s0; + times[0].tv_nsec = ns0; + times[1].tv_sec = s1; + times[1].tv_nsec = ns1; + boost::filesystem::path p = root / path; + if (::utimensat(0, p.string().c_str(), times, AT_SYMLINK_NOFOLLOW) != 0) { + throw NetFS::SystemError(errno); + } +} + +NetFS::VFS +VolumeServer::statfs(const NetFS::ReqEnv & re, const std::string & path, const Ice::Current&) +{ + TempPrivs tp(re, &uentries, &gentries); + errno = 0; + struct statvfs s; + boost::filesystem::path p = root / path; + if (::statvfs(p.string().c_str(), &s) != 0) { + throw NetFS::SystemError(errno); + } + NetFS::VFS t; + t << s; + return t; +} + +void +VolumeServer::truncate(const NetFS::ReqEnv & re, const std::string & path, Ice::Long size, const Ice::Current&) +{ + TempPrivs tp(re, &uentries, &gentries); + errno = 0; + boost::filesystem::path p = root / path; + if (::truncate(p.string().c_str(), size) != 0) { + throw NetFS::SystemError(errno); + } +} + +void +VolumeServer::unlink(const NetFS::ReqEnv & re, const std::string & path, const Ice::Current&) +{ + TempPrivs tp(re, &uentries, &gentries); + errno = 0; + boost::filesystem::path p = root / path; + if (::unlink(p.string().c_str()) != 0) { + throw NetFS::SystemError(errno); + } +} + +NetFS::ReadOnlyFilePrx +VolumeServer::openReadOnly(const NetFS::ReqEnv & re, const std::string & path, Ice::Int flags, const Ice::Current & ice) +{ + return open(re, path, flags, ice); +} + +NetFS::FilePrx +VolumeServer::open(const NetFS::ReqEnv & re, const std::string & path, Ice::Int flags, const Ice::Current & ice) +{ + TempPrivs tp(re, &uentries, &gentries); + errno = 0; + boost::filesystem::path p = root / path; + int fd = ::open(p.string().c_str(), flags); + if (fd == -1) { + throw NetFS::SystemError(errno); + } + return NetFS::FilePrx::checkedCast(ice.adapter->addWithUUID(new FileServer(fd))); +} + +NetFS::FilePrx +VolumeServer::create(const NetFS::ReqEnv & re, const std::string & path, Ice::Int flags, Ice::Int mode, const Ice::Current & ice) +{ + TempPrivs tp(re, &uentries, &gentries); + errno = 0; + boost::filesystem::path p = root / path; + int fd = ::open(p.string().c_str(), O_CREAT | flags, mode); + if (fd == -1) { + throw NetFS::SystemError(errno); + } + return NetFS::FilePrx::checkedCast(ice.adapter->addWithUUID(new FileServer(fd))); +} + +NetFS::DirectoryPrx +VolumeServer::opendir(const NetFS::ReqEnv & re, const std::string & path, const Ice::Current & ice) +{ + TempPrivs tp(re, &uentries, &gentries); + errno = 0; + boost::filesystem::path p = root / path; + DIR * od = ::opendir(p.string().c_str()); + if (!od) { + throw NetFS::SystemError(errno); + } + return NetFS::DirectoryPrx::checkedCast(ice.adapter->addWithUUID(new DirectoryServer(od))); +} + +void +VolumeServer::mkdir(const NetFS::ReqEnv & re, const std::string & path, Ice::Int mode, const Ice::Current&) +{ + TempPrivs tp(re, &uentries, &gentries); + errno = 0; + boost::filesystem::path p = root / path; + if (::mkdir(p.string().c_str(), mode) != 0) { + throw NetFS::SystemError(errno); + } +} + +void +VolumeServer::rmdir(const NetFS::ReqEnv & re, const std::string & path, const Ice::Current&) +{ + TempPrivs tp(re, &uentries, &gentries); + errno = 0; + boost::filesystem::path p = root / path; + if (::rmdir(p.string().c_str()) != 0) { + throw NetFS::SystemError(errno); + } +} + |