From f097f6473095fa04ff52ac7ee33a8dc435144a6f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Roman=20Smr=C5=BE?= Date: Wed, 29 Nov 2023 20:27:38 +0100 Subject: Avoid storing zero references and objects --- include/erebos/storage.h | 4 ++++ src/network/protocol.cpp | 2 +- src/storage.cpp | 29 +++++++++++++++++++++++++---- 3 files changed, 30 insertions(+), 5 deletions(-) diff --git a/include/erebos/storage.h b/include/erebos/storage.h index 3feb22b..48bedd7 100644 --- a/include/erebos/storage.h +++ b/include/erebos/storage.h @@ -174,6 +174,7 @@ public: PartialRef & operator=(PartialRef &&) = default; static PartialRef create(const PartialStorage &, const Digest &); + static PartialRef zcreate(const PartialStorage &); const Digest & digest() const; @@ -234,6 +235,7 @@ private: ptr(ptr) {} public: + RecordT(): RecordT(std::vector {}) {} RecordT(const std::vector &); RecordT(std::vector &&); std::vector encode() const; @@ -420,6 +422,8 @@ public: std::vector encode() const; static ObjectT load(const typename S::Ref &); + operator bool() const; + std::optional> asRecord() const; std::optional asBlob() const; diff --git a/src/network/protocol.cpp b/src/network/protocol.cpp index 8e0de61..02c3dae 100644 --- a/src/network/protocol.cpp +++ b/src/network/protocol.cpp @@ -134,7 +134,7 @@ NetworkProtocol::Connection NetworkProtocol::connect(sockaddr_in6 addr) connections.push_back(conn.get()); vector header { - Header::Initiation { Digest(array {}) }, + Header::Initiation { Digest::of(Object(Record())) }, Header::AnnounceSelf { self->ref()->digest() }, Header::Version { defaultVersion }, }; diff --git a/src/storage.cpp b/src/storage.cpp index 366fe71..19f35a9 100644 --- a/src/storage.cpp +++ b/src/storage.cpp @@ -746,7 +746,11 @@ optional PartialStorage::loadObject(const Digest & digest) const } PartialRef PartialStorage::storeObject(const PartialObject & obj) const -{ return ref(p->storeBytes(obj.encode())); } +{ + if (not obj) + return PartialRef::zcreate(*this); + return ref(p->storeBytes(obj.encode())); +} PartialRef PartialStorage::storeObject(const PartialRecord & val) const { return storeObject(PartialObject(val)); } @@ -775,6 +779,8 @@ Ref Storage::storeObject(const Blob & val) const template optional Storage::Priv::copy(const typename S::Ref & pref, vector * missing) const { + if (pref.digest().isZero()) + return pref.digest(); if (backend->contains(pref.digest())) return pref.digest(); if (pref) @@ -787,6 +793,9 @@ optional Storage::Priv::copy(const typename S::Ref & pref, vector optional Storage::Priv::copy(const ObjectT & pobj, vector * missing) const { + if (not pobj) + return Digest(array {}); + bool fail = false; if (auto rec = pobj.asRecord()) for (const auto & r : rec->items().asRef()) @@ -948,6 +957,11 @@ PartialRef PartialRef::create(const PartialStorage & st, const Digest & digest) return PartialRef(shared_ptr(p)); } +PartialRef PartialRef::zcreate(const PartialStorage & st) +{ + return create(st, Digest(array {})); +} + const Digest & PartialRef::digest() const { return p->digest; @@ -1421,9 +1435,6 @@ vector RecordT::encodeInner() const vector res; auto inserter = std::back_inserter(res); for (const auto & item : *ptr) { - copy(item.name.begin(), item.name.end(), inserter); - inserter = ':'; - string type; string value; @@ -1451,6 +1462,8 @@ vector RecordT::encodeInner() const value = string(*x); } else if (auto x = item.asRef()) { type = "r"; + if (x->digest().isZero()) + continue; value = string(x->digest()); } else if (auto x = item.asUnknown()) { type = x->type; @@ -1459,6 +1472,8 @@ vector RecordT::encodeInner() const throw runtime_error("unhandeled record item type"); } + copy(item.name.begin(), item.name.end(), inserter); + inserter = ':'; copy(type.begin(), type.end(), inserter); inserter = ' '; @@ -1598,6 +1613,12 @@ ObjectT ObjectT::load(const typename S::Ref & ref) return *ref; } +template +ObjectT::operator bool() const +{ + return not holds_alternative(content); +} + template optional> ObjectT::asRecord() const { -- cgit v1.2.3