We don't actually need to calculate or store the ancestor chain unless we're renaming
This commit is contained in:
parent
222ef46d8d
commit
45895d8d4f
@ -191,17 +191,15 @@ optional<unique_ref<fspp::Node>> CryDevice::Load(const bf::path &path) {
|
||||
|
||||
if (path.parent_path().empty()) {
|
||||
//We are asked to load the base directory '/'.
|
||||
return optional<unique_ref<fspp::Node>>(make_unique_ref<CryDir>(this, none, none, _rootBlobId, std::vector<BlockId>()));
|
||||
return optional<unique_ref<fspp::Node>>(make_unique_ref<CryDir>(this, none, none, _rootBlobId));
|
||||
}
|
||||
|
||||
auto parentWithAncestors = LoadDirBlobWithAncestors(path.parent_path());
|
||||
auto parentWithAncestors = LoadDirBlobWithAncestors(path.parent_path(), none);
|
||||
if (parentWithAncestors == none) {
|
||||
return none;
|
||||
}
|
||||
auto parent = std::move(parentWithAncestors->blob);
|
||||
auto grandparent = std::move(parentWithAncestors->parent);
|
||||
auto ancestors = std::move(parentWithAncestors->ancestors);
|
||||
ancestors.push_back(parent->blockId()); // parent's ancestors don't contain parent yet, but parent is our ancestor
|
||||
|
||||
auto optEntry = parent->GetChild(path.filename().string());
|
||||
if (optEntry == boost::none) {
|
||||
@ -211,17 +209,17 @@ optional<unique_ref<fspp::Node>> CryDevice::Load(const bf::path &path) {
|
||||
|
||||
switch(entry.type()) {
|
||||
case fspp::Dir::EntryType::DIR:
|
||||
return optional<unique_ref<fspp::Node>>(make_unique_ref<CryDir>(this, std::move(parent), std::move(grandparent), entry.blockId(), std::move(ancestors)));
|
||||
return optional<unique_ref<fspp::Node>>(make_unique_ref<CryDir>(this, std::move(parent), std::move(grandparent), entry.blockId()));
|
||||
case fspp::Dir::EntryType::FILE:
|
||||
return optional<unique_ref<fspp::Node>>(make_unique_ref<CryFile>(this, std::move(parent), std::move(grandparent), entry.blockId(), std::move(ancestors)));
|
||||
return optional<unique_ref<fspp::Node>>(make_unique_ref<CryFile>(this, std::move(parent), std::move(grandparent), entry.blockId()));
|
||||
case fspp::Dir::EntryType::SYMLINK:
|
||||
return optional<unique_ref<fspp::Node>>(make_unique_ref<CrySymlink>(this, std::move(parent), std::move(grandparent), entry.blockId(), std::move(ancestors)));
|
||||
return optional<unique_ref<fspp::Node>>(make_unique_ref<CrySymlink>(this, std::move(parent), std::move(grandparent), entry.blockId()));
|
||||
}
|
||||
ASSERT(false, "Switch/case not exhaustive");
|
||||
}
|
||||
|
||||
optional<CryDevice::DirBlobWithAncestors> CryDevice::LoadDirBlobWithAncestors(const bf::path &path) {
|
||||
auto blob = LoadBlobWithAncestors(path);
|
||||
optional<CryDevice::DirBlobWithAncestors> CryDevice::LoadDirBlobWithAncestors(const bf::path &path, boost::optional<std::vector<BlockId>*> append_ancestors_to) {
|
||||
auto blob = LoadBlobWithAncestors(path, std::move(append_ancestors_to));
|
||||
if (blob == none) {
|
||||
return none;
|
||||
}
|
||||
@ -229,11 +227,10 @@ optional<CryDevice::DirBlobWithAncestors> CryDevice::LoadDirBlobWithAncestors(co
|
||||
if (dir == none) {
|
||||
throw FuseErrnoException(ENOTDIR); // Loaded blob is not a directory
|
||||
}
|
||||
return DirBlobWithAncestors{std::move(*dir), std::move(blob->parent), std::move(blob->ancestors)};
|
||||
return DirBlobWithAncestors{std::move(*dir), std::move(blob->parent)};
|
||||
}
|
||||
|
||||
optional<CryDevice::BlobWithAncestors> CryDevice::LoadBlobWithAncestors(const bf::path &path) {
|
||||
std::vector<blockstore::BlockId> ancestors;
|
||||
optional<CryDevice::BlobWithAncestors> CryDevice::LoadBlobWithAncestors(const bf::path &path, boost::optional<std::vector<BlockId>*> append_ancestors_to) {
|
||||
optional<unique_ref<DirBlobRef>> parentBlob = none;
|
||||
optional<unique_ref<FsBlobRef>> currentBlobOpt = _fsBlobStore->load(_rootBlobId);
|
||||
if (currentBlobOpt == none) {
|
||||
@ -244,7 +241,9 @@ optional<CryDevice::BlobWithAncestors> CryDevice::LoadBlobWithAncestors(const bf
|
||||
ASSERT(currentBlob->parentPointer() == BlockId::Null(), "Root Blob should have a nullptr as parent");
|
||||
|
||||
for (const bf::path &component : path.relative_path()) {
|
||||
ancestors.push_back(currentBlob->blockId());
|
||||
if (append_ancestors_to != boost::none) {
|
||||
(*append_ancestors_to)->push_back(currentBlob->blockId());
|
||||
}
|
||||
auto currentDir = dynamic_pointer_move<DirBlobRef>(currentBlob);
|
||||
if (currentDir == none) {
|
||||
throw FuseErrnoException(ENOTDIR); // Path component is not a dir
|
||||
@ -265,7 +264,7 @@ optional<CryDevice::BlobWithAncestors> CryDevice::LoadBlobWithAncestors(const bf
|
||||
ASSERT(currentBlob->parentPointer() == (*parentBlob)->blockId(), "Blob has wrong parent pointer");
|
||||
}
|
||||
|
||||
return BlobWithAncestors{std::move(currentBlob), std::move(parentBlob), std::move(ancestors)};
|
||||
return BlobWithAncestors{std::move(currentBlob), std::move(parentBlob)};
|
||||
|
||||
//TODO (I think this is resolved, but I should test it)
|
||||
// Running the python script, waiting for "Create files in sequential order...", then going into dir ~/tmp/cryfs-mount-.../Bonnie.../ and calling "ls"
|
||||
|
@ -31,9 +31,8 @@ public:
|
||||
struct DirBlobWithAncestors {
|
||||
cpputils::unique_ref<parallelaccessfsblobstore::DirBlobRef> blob;
|
||||
boost::optional<cpputils::unique_ref<parallelaccessfsblobstore::DirBlobRef>> parent;
|
||||
std::vector<blockstore::BlockId> ancestors;
|
||||
};
|
||||
boost::optional<DirBlobWithAncestors> LoadDirBlobWithAncestors(const boost::filesystem::path &path);
|
||||
boost::optional<DirBlobWithAncestors> LoadDirBlobWithAncestors(const boost::filesystem::path &path, boost::optional<std::vector<blockstore::BlockId>*> append_ancestors_to);
|
||||
void RemoveBlob(const blockstore::BlockId &blockId);
|
||||
|
||||
void onFsAction(std::function<void()> callback);
|
||||
@ -69,9 +68,8 @@ private:
|
||||
struct BlobWithAncestors {
|
||||
cpputils::unique_ref<parallelaccessfsblobstore::FsBlobRef> blob;
|
||||
boost::optional<cpputils::unique_ref<parallelaccessfsblobstore::DirBlobRef>> parent;
|
||||
std::vector<blockstore::BlockId> ancestors;
|
||||
};
|
||||
boost::optional<BlobWithAncestors> LoadBlobWithAncestors(const boost::filesystem::path &path);
|
||||
boost::optional<BlobWithAncestors> LoadBlobWithAncestors(const boost::filesystem::path &path, boost::optional<std::vector<blockstore::BlockId>*> append_ancestors_to);
|
||||
|
||||
DISALLOW_COPY_AND_ASSIGN(CryDevice);
|
||||
};
|
||||
|
@ -28,8 +28,8 @@ using cryfs::parallelaccessfsblobstore::DirBlobRef;
|
||||
|
||||
namespace cryfs {
|
||||
|
||||
CryDir::CryDir(CryDevice *device, optional<unique_ref<DirBlobRef>> parent, optional<unique_ref<DirBlobRef>> grandparent, const BlockId &blockId, std::vector<BlockId> ancestors)
|
||||
: CryNode(device, std::move(parent), std::move(grandparent), blockId, std::move(ancestors)) {
|
||||
CryDir::CryDir(CryDevice *device, optional<unique_ref<DirBlobRef>> parent, optional<unique_ref<DirBlobRef>> grandparent, const BlockId &blockId)
|
||||
: CryNode(device, std::move(parent), std::move(grandparent), blockId) {
|
||||
}
|
||||
|
||||
CryDir::~CryDir() {
|
||||
|
@ -10,7 +10,7 @@ namespace cryfs {
|
||||
|
||||
class CryDir final: public fspp::Dir, public CryNode {
|
||||
public:
|
||||
CryDir(CryDevice *device, boost::optional<cpputils::unique_ref<parallelaccessfsblobstore::DirBlobRef>> parent, boost::optional<cpputils::unique_ref<parallelaccessfsblobstore::DirBlobRef>> grandparent, const blockstore::BlockId &blockId, std::vector<blockstore::BlockId> ancestors);
|
||||
CryDir(CryDevice *device, boost::optional<cpputils::unique_ref<parallelaccessfsblobstore::DirBlobRef>> parent, boost::optional<cpputils::unique_ref<parallelaccessfsblobstore::DirBlobRef>> grandparent, const blockstore::BlockId &blockId);
|
||||
~CryDir();
|
||||
|
||||
//TODO return type variance to CryFile/CryDir?
|
||||
|
@ -18,8 +18,8 @@ using cryfs::parallelaccessfsblobstore::FileBlobRef;
|
||||
|
||||
namespace cryfs {
|
||||
|
||||
CryFile::CryFile(CryDevice *device, unique_ref<DirBlobRef> parent, optional<unique_ref<DirBlobRef>> grandparent, const BlockId &blockId, std::vector<BlockId> ancestors)
|
||||
: CryNode(device, std::move(parent), std::move(grandparent), blockId, std::move(ancestors)) {
|
||||
CryFile::CryFile(CryDevice *device, unique_ref<DirBlobRef> parent, optional<unique_ref<DirBlobRef>> grandparent, const BlockId &blockId)
|
||||
: CryNode(device, std::move(parent), std::move(grandparent), blockId) {
|
||||
}
|
||||
|
||||
CryFile::~CryFile() {
|
||||
|
@ -11,7 +11,7 @@ namespace cryfs {
|
||||
|
||||
class CryFile final: public fspp::File, public CryNode {
|
||||
public:
|
||||
CryFile(CryDevice *device, cpputils::unique_ref<parallelaccessfsblobstore::DirBlobRef> parent, boost::optional<cpputils::unique_ref<parallelaccessfsblobstore::DirBlobRef>> grandparent, const blockstore::BlockId &blockId, std::vector<blockstore::BlockId> ancestors);
|
||||
CryFile(CryDevice *device, cpputils::unique_ref<parallelaccessfsblobstore::DirBlobRef> parent, boost::optional<cpputils::unique_ref<parallelaccessfsblobstore::DirBlobRef>> grandparent, const blockstore::BlockId &blockId);
|
||||
~CryFile();
|
||||
|
||||
cpputils::unique_ref<fspp::OpenFile> open(fspp::openflags_t flags) override;
|
||||
|
@ -18,6 +18,7 @@ using cpputils::dynamic_pointer_move;
|
||||
using boost::optional;
|
||||
using boost::none;
|
||||
using std::shared_ptr;
|
||||
using std::vector;
|
||||
using cryfs::parallelaccessfsblobstore::FsBlobRef;
|
||||
using cryfs::parallelaccessfsblobstore::DirBlobRef;
|
||||
using namespace cpputils::logging;
|
||||
@ -27,11 +28,10 @@ using fspp::fuse::FuseErrnoException;
|
||||
|
||||
namespace cryfs {
|
||||
|
||||
CryNode::CryNode(CryDevice *device, optional<unique_ref<DirBlobRef>> parent, optional<unique_ref<DirBlobRef>> grandparent, const BlockId &blockId, std::vector<BlockId> ancestors)
|
||||
CryNode::CryNode(CryDevice *device, optional<unique_ref<DirBlobRef>> parent, optional<unique_ref<DirBlobRef>> grandparent, const BlockId &blockId)
|
||||
: _device(device),
|
||||
_parent(none),
|
||||
_grandparent(none),
|
||||
_ancestors(std::move(ancestors)),
|
||||
_blockId(blockId) {
|
||||
|
||||
ASSERT(parent != none || grandparent == none, "Grandparent can only be set when parent is not none");
|
||||
@ -88,15 +88,15 @@ void CryNode::rename(const bf::path &to) {
|
||||
throw FuseErrnoException(EBUSY);
|
||||
}
|
||||
|
||||
auto targetParentAndAncestors = _device->LoadDirBlobWithAncestors(to.parent_path());
|
||||
vector<BlockId> targetAncestors;
|
||||
auto targetParentAndAncestors = _device->LoadDirBlobWithAncestors(to.parent_path(), &targetAncestors);
|
||||
if (targetParentAndAncestors == none) {
|
||||
// Target parent directory doesn't exist
|
||||
throw FuseErrnoException(ENOENT);
|
||||
}
|
||||
auto targetParent = std::move(targetParentAndAncestors->blob);
|
||||
auto targetGrandparent = std::move(targetParentAndAncestors->parent);
|
||||
auto targetAncestors = std::move(targetParentAndAncestors->ancestors);
|
||||
targetAncestors.push_back(targetParent->blockId()); // targetParent is not an ancestor of the targetParent, but it's a target ancestor
|
||||
targetAncestors.push_back(targetParent->blockId()); // targetParent is not an ancestor of the targetParent, so it wasn't filled in, but it's a target ancestor
|
||||
|
||||
if (std::find(targetAncestors.begin(), targetAncestors.end(), _blockId) != targetAncestors.end()) {
|
||||
// We are trying to move a node into one of its subdirectories. This is not allowed.
|
||||
|
@ -15,7 +15,7 @@ public:
|
||||
virtual ~CryNode();
|
||||
|
||||
// TODO grandparent is only needed to set the timestamps of the parent directory on rename and remove. Delete grandparent parameter once we store timestamps in the blob itself instead of in the directory listing.
|
||||
CryNode(CryDevice *device, boost::optional<cpputils::unique_ref<parallelaccessfsblobstore::DirBlobRef>> parent, boost::optional<cpputils::unique_ref<parallelaccessfsblobstore::DirBlobRef>> grandparent, const blockstore::BlockId &blockId, std::vector<blockstore::BlockId> ancestors);
|
||||
CryNode(CryDevice *device, boost::optional<cpputils::unique_ref<parallelaccessfsblobstore::DirBlobRef>> parent, boost::optional<cpputils::unique_ref<parallelaccessfsblobstore::DirBlobRef>> grandparent, const blockstore::BlockId &blockId);
|
||||
|
||||
void access(int mask) const override;
|
||||
stat_info stat() const override;
|
||||
@ -51,7 +51,6 @@ private:
|
||||
CryDevice *_device;
|
||||
boost::optional<std::shared_ptr<parallelaccessfsblobstore::DirBlobRef>> _parent;
|
||||
boost::optional<cpputils::unique_ref<parallelaccessfsblobstore::DirBlobRef>> _grandparent;
|
||||
std::vector<blockstore::BlockId> _ancestors; // [n-1] is the parent, [n-2] is the grandparent, ..., [0] is the file system root,
|
||||
blockstore::BlockId _blockId;
|
||||
|
||||
DISALLOW_COPY_AND_ASSIGN(CryNode);
|
||||
|
@ -21,8 +21,8 @@ using cryfs::parallelaccessfsblobstore::DirBlobRef;
|
||||
|
||||
namespace cryfs {
|
||||
|
||||
CrySymlink::CrySymlink(CryDevice *device, unique_ref<DirBlobRef> parent, optional<unique_ref<DirBlobRef>> grandparent, const BlockId &blockId, std::vector<blockstore::BlockId> ancestors)
|
||||
: CryNode(device, std::move(parent), std::move(grandparent), blockId, std::move(ancestors)) {
|
||||
CrySymlink::CrySymlink(CryDevice *device, unique_ref<DirBlobRef> parent, optional<unique_ref<DirBlobRef>> grandparent, const BlockId &blockId)
|
||||
: CryNode(device, std::move(parent), std::move(grandparent), blockId) {
|
||||
}
|
||||
|
||||
CrySymlink::~CrySymlink() {
|
||||
|
@ -11,7 +11,7 @@ namespace cryfs {
|
||||
|
||||
class CrySymlink final: public fspp::Symlink, public CryNode {
|
||||
public:
|
||||
CrySymlink(CryDevice *device, cpputils::unique_ref<parallelaccessfsblobstore::DirBlobRef> parent, boost::optional<cpputils::unique_ref<parallelaccessfsblobstore::DirBlobRef>> grandparent, const blockstore::BlockId &blockId, std::vector<blockstore::BlockId> ancestors);
|
||||
CrySymlink(CryDevice *device, cpputils::unique_ref<parallelaccessfsblobstore::DirBlobRef> parent, boost::optional<cpputils::unique_ref<parallelaccessfsblobstore::DirBlobRef>> grandparent, const blockstore::BlockId &blockId);
|
||||
~CrySymlink();
|
||||
|
||||
boost::filesystem::path target() override;
|
||||
|
Loading…
Reference in New Issue
Block a user