aboutsummaryrefslogtreecommitdiff
path: root/zenstore/include
diff options
context:
space:
mode:
Diffstat (limited to 'zenstore/include')
-rw-r--r--zenstore/include/zenstore/CAS.h36
-rw-r--r--zenstore/include/zenstore/caslog.h4
-rw-r--r--zenstore/include/zenstore/cidstore.h7
-rw-r--r--zenstore/include/zenstore/gc.h88
4 files changed, 111 insertions, 24 deletions
diff --git a/zenstore/include/zenstore/CAS.h b/zenstore/include/zenstore/CAS.h
index 86e7e78d9..5b508baa0 100644
--- a/zenstore/include/zenstore/CAS.h
+++ b/zenstore/include/zenstore/CAS.h
@@ -11,6 +11,7 @@
#include <zencore/timer.h>
#include <atomic>
+#include <concepts>
#include <filesystem>
#include <functional>
#include <memory>
@@ -19,6 +20,9 @@
namespace zen {
+class GcContext;
+class CasGc;
+
struct CasStoreConfiguration
{
// Root directory for CAS store
@@ -45,29 +49,22 @@ public:
inline [[nodiscard]] bool IsEmpty() const { return m_ChunkSet.empty(); }
inline [[nodiscard]] size_t GetSize() const { return m_ChunkSet.size(); }
+ inline void FilterChunks(std::span<const IoHash> Candidates, std::invocable<const IoHash&> auto MatchFunc)
+ {
+ for (const IoHash& Candidate : Candidates)
+ {
+ if (ContainsChunk(Candidate))
+ {
+ MatchFunc(Candidate);
+ }
+ }
+ }
+
private:
// Q: should we protect this with a lock, or is that a higher level concern?
std::unordered_set<IoHash> m_ChunkSet;
};
-/** Garbage Collection context object
- */
-
-class GcContext
-{
-public:
- GcContext();
- ~GcContext();
-
- void ContributeCids(std::span<const IoHash> Cid);
- void ContributeCas(std::span<const IoHash> Hash);
-
-private:
- struct GcState;
-
- std::unique_ptr<GcState> m_State;
-};
-
/** Context object for data scrubbing
*
* Data scrubbing is when we traverse stored data to validate it and
@@ -116,13 +113,14 @@ public:
virtual void FilterChunks(CasChunkSet& InOutChunks) = 0;
virtual void Flush() = 0;
virtual void Scrub(ScrubContext& Ctx) = 0;
+ virtual void GarbageCollect(GcContext& GcCtx) = 0;
protected:
CasStoreConfiguration m_Config;
uint64_t m_LastScrubTime = 0;
};
-ZENCORE_API CasStore* CreateCasStore();
+ZENCORE_API CasStore* CreateCasStore(CasGc& Gc);
void CAS_forcelink();
diff --git a/zenstore/include/zenstore/caslog.h b/zenstore/include/zenstore/caslog.h
index 00b987383..bb9d07726 100644
--- a/zenstore/include/zenstore/caslog.h
+++ b/zenstore/include/zenstore/caslog.h
@@ -27,6 +27,7 @@ public:
void Replay(std::function<void(const void*)>&& Handler);
void Flush();
void Close();
+ uint64_t GetLogSize();
private:
struct FileHeader
@@ -57,6 +58,8 @@ template<typename T>
class TCasLogFile : public CasLogFile
{
public:
+ void Open(std::filesystem::path FileName, bool IsCreate) { CasLogFile::Open(FileName, sizeof(T), IsCreate); }
+
// This should be called before the Replay() is called to do some basic sanity checking
bool Initialize() { return true; }
@@ -76,7 +79,6 @@ public:
CasLogFile::Append(&Record, sizeof Record);
}
- void Open(std::filesystem::path FileName, bool IsCreate) { CasLogFile::Open(FileName, sizeof(T), IsCreate); }
};
} // namespace zen
diff --git a/zenstore/include/zenstore/cidstore.h b/zenstore/include/zenstore/cidstore.h
index 5f567e7fc..a69569bd2 100644
--- a/zenstore/include/zenstore/cidstore.h
+++ b/zenstore/include/zenstore/cidstore.h
@@ -4,10 +4,13 @@
#include "zenstore.h"
-#include <tsl/robin_map.h>
#include <zencore/iohash.h>
#include <zenstore/CAS.h>
+ZEN_THIRD_PARTY_INCLUDES_START
+#include <tsl/robin_map.h>
+ZEN_THIRD_PARTY_INCLUDES_END
+
namespace std::filesystem {
class path;
}
@@ -54,6 +57,8 @@ public:
// TODO: add batch filter support
+ IoHash RemapCid(const IoHash& DecompressedId);
+
private:
struct Impl;
std::unique_ptr<Impl> m_Impl;
diff --git a/zenstore/include/zenstore/gc.h b/zenstore/include/zenstore/gc.h
index 055843547..560642803 100644
--- a/zenstore/include/zenstore/gc.h
+++ b/zenstore/include/zenstore/gc.h
@@ -3,26 +3,108 @@
#pragma once
#include <zencore/iohash.h>
+#include <zencore/thread.h>
#include <span>
+#include <functional>
+
+#define ZEN_USE_REF_TRACKING 0 // This is not currently functional
namespace zen {
class CasStore;
+class CasGc;
+class CidStore;
struct IoHash;
+/** Garbage Collection context object
+ */
+
+class GcContext
+{
+public:
+ GcContext();
+ ~GcContext();
+
+ void ContributeCids(std::span<const IoHash> Cid);
+ void ContributeCas(std::span<const IoHash> Hash);
+
+ void IterateCids(std::function<void(const IoHash&)> Callback);
+
+ void FilterCids(std::span<const IoHash> Cid, std::function<void(const IoHash&)> KeepFunc);
+ void FilterCas(std::span<const IoHash> Cas, std::function<void(const IoHash&)> KeepFunc);
+
+ bool IsDeletionMode() const;
+ void SetDeletionMode(bool NewState);
+
+private:
+ struct GcState;
+
+ std::unique_ptr<GcState> m_State;
+};
+
+/** GC root contributor
+
+ Higher level data structures provide roots for the garbage collector,
+ which ultimately determine what is garbage and what data we need to
+ retain.
+
+ */
+
+class GcContributor
+{
+public:
+ GcContributor(CasGc& Gc);
+ ~GcContributor();
+
+ virtual void GatherReferences(GcContext& GcCtx) = 0;
+
+protected:
+ CasGc& m_Gc;
+};
+
+/** GC storage provider
+ */
+
+class GcStorage
+{
+public:
+ GcStorage(CasGc& Gc);
+ ~GcStorage();
+
+ virtual void CollectGarbage(GcContext& GcCtx) = 0;
+
+private:
+ CasGc& m_Gc;
+};
+
+/** GC orchestrator
+ */
+
class CasGc
{
public:
- CasGc(CasStore& Store);
+ CasGc();
~CasGc();
+ void AddGcContributor(GcContributor* Contributor);
+ void RemoveGcContributor(GcContributor* Contributor);
+
+ void AddGcStorage(GcStorage* Contributor);
+ void RemoveGcStorage(GcStorage* Contributor);
+
void CollectGarbage();
- void OnNewReferences(std::span<IoHash> Hashes);
+ void SetCidStore(CidStore* Cids);
+ void OnNewCidReferences(std::span<IoHash> Hashes);
+ void OnCommittedCidReferences(std::span<IoHash> Hashes);
+ void OnDroppedCidReferences(std::span<IoHash> Hashes);
private:
- CasStore& m_CasStore;
+ RwLock m_Lock;
+ std::vector<GcContributor*> m_GcContribs;
+ std::vector<GcStorage*> m_GcStorage;
+ CidStore* m_CidStore;
};
} // namespace zen