20#include <unordered_map>
21#include <unordered_set>
23#if defined(__APPLE__) || defined(__linux__)
24#include <sys/random.h>
33#if defined(__APPLE__) || defined(__linux__)
34 std::array<unsigned char, 16> bytes{};
35 if (::getentropy(bytes.data(), bytes.size()))
36 throw std::system_error(errno, std::generic_category(),
"Everett identity entropy");
37 constexpr char digits[] =
"0123456789abcdef";
38 std::string text(32,
'0');
39 for (std::size_t i = 0; i != bytes.size(); ++i) {
40 text[i * 2] = digits[bytes[i] >> 4]; text[i * 2 + 1] = digits[bytes[i] & 15];
44 throw std::system_error(std::make_error_code(std::errc::operation_not_supported),
"Everett identity entropy");
49 template <
class P,
class Family = binary_runtime_family<P>>
struct stored_runtime {
58 template <
class P,
class Ids = random_
object_
ids,
class Ops = sqlite_catalog_ops,
class Family = binary_runtime_family<P>>
struct runtime_store {
69 using mapped_type = std::remove_const_t<typename mapped_pointer::element_type>;
72 static_assert(std::is_same_v<P, typename Family::policy_type>);
82 if (db.schema_version() != 4)
throw std::invalid_argument(
"named runtime needs catalog version 4");
91 std::filesystem::path
const &
root() const && = delete;
96 return head ? std::optional<stored_type>{
restore(std::move(*head))} : std::nullopt;
98 std::optional<stored_type>
find_save(std::string_view name) {
101 return head ? std::optional<stored_type>{
restore(std::move(*head))} : std::nullopt;
108 catch (...) {
failed_ =
true;
throw; }
111 std::span<std::byte const> semantic = {}) {
115 auto checkpoint = codec_type::encode(source, semantic,
120 }
catch (...) {
failed_ =
true;
throw; }
123 std::span<std::byte const> semantic = {}) {
127 auto checkpoint = codec_type::encode(source, semantic,
132 if (!
published.published)
throw std::runtime_error(
"named Everett session was advanced by another connection");
134 }
catch (...) {
failed_ =
true;
throw; }
139 catch (...) {
failed_ =
true;
throw; }
144 catch (...) {
failed_ =
true;
throw; }
157 void require_active()
const {
if (
failed())
throw std::logic_error(
"failed Everett runtime store; reopen it"); }
165 std::unordered_map<std::string, native_pointer>
natives;
166 std::unordered_map<std::string, pair_type>
pairs;
170 auto found =
natives.find(
id.hex());
172 if (
restricted)
throw std::invalid_argument(
"checkpoint native has no durable pin");
173 auto value = native_type::from_mapped(
mapped.
native(
id));
175 found =
natives.emplace(
id.hex(), std::move(value)).first;
177 return found->second;
180 if (
auto found =
pairs.find(
id.index.hex()); found !=
pairs.end()) {
181 if (found->second->mapped()->identity() != id)
182 throw std::invalid_argument(
"checkpoint index has another native identity");
183 return found->second;
186 throw std::invalid_argument(
"checkpoint pair has no durable pin");
189 std::vector<mapped_pointer> pending;
191 for (
auto p = physical; p; p = p->main_target()) {
192 if (
auto known =
pairs.find(p->identity().index.hex()); known !=
pairs.end()) { result = known->second;
break; }
193 pending.push_back(p);
195 for (
auto i = pending.rbegin(); i != pending.rend(); ++i) {
197 result = node_type::from_mapped_parts(p,
native(p->identity().native), result,
198 p->index_object()->secondary_id() ?
native(*p->index_object()->secondary_id()) :
native_pointer{});
199 pairs.emplace(p->identity().index.hex(), result);
205 auto [found, inserted] =
natives.try_emplace(
id.hex(), value);
206 return inserted || found->second == value;
209 auto const &
id = value->mapped()->identity();
210 auto [found, inserted] =
pairs.try_emplace(
id.index.hex(), value);
211 return inserted || found->second == value;
216 std::vector<typename registry_type::native_root>
natives;
223 if (!pair)
return std::nullopt;
224 result.
pairs.push_back(std::move(pair));
226 pair = loaded.pair(
id);
227 if (!pair)
return std::nullopt;
228 result.
pairs.push_back(std::move(pair));
231 auto native = loaded.native(
id);
232 if (!
native)
return std::nullopt;
241 if (!value)
throw std::invalid_argument(
"checkpoint pair has no durable pin");
246 if (!value)
throw std::invalid_argument(
"checkpoint native has no durable pin");
254 return {std::move(head), std::move(restored.snapshot), std::move(restored.semantic)};
264 bool coherent =
true;
265 codec_type::collect(*source, [&](
pair_type const & pair) {
266 if (pair) coherent = candidates.
seed_root(graph.mapped_pair(pair)) && coherent;
276 if (!selected)
throw std::logic_error(
"published root has no prepared owner");
277 if (
retained_.
replace(std::move(selected->pairs), std::move(selected->natives)))
281 if (
retained_.
replace(std::move(selected->pairs), std::move(selected->natives)))
290 if (!selected)
throw std::logic_error(
"durable root has no mapped owner");
293 if (!
replacement.replace(std::move(selected->pairs), std::move(selected->natives)))
294 throw std::invalid_argument(
"mapped checkpoint has conflicting facade identities");
298 return {std::move(head), std::move(restored.snapshot), std::move(restored.semantic)};
302 std::vector<pair_type>
roots;
303 std::vector<native_pointer> native_roots;
304 std::unordered_set<node_type const *> seen_pairs;
305 std::unordered_set<native_type const *> seen_natives;
306 codec_type::collect(source, [&](
pair_type value) {
307 if (value && seen_pairs.insert(value.get()).second)
roots.push_back(std::move(value));
309 if (value && seen_natives.insert(value.get()).second) native_roots.push_back(std::move(value));
312 (void)graph.prepare_ready(
roots, native_roots);
317 for (
auto const & pair :
roots) (
void)graph.ensure_pair(pair);
318 for (
auto const &
native : native_roots) (
void)graph.ensure_native(
native);
319 auto primary = graph.pair_id(source.query_root().head());
321 for (
auto const & pair :
roots) retained.
pairs.push_back(graph.pair_id(pair));
322 for (
auto const &
native : native_roots) retained.
natives.push_back(graph.native_id(
native));
catalog_auxiliary_roots canonical_auxiliary(catalog_auxiliary_roots value, blob_identity const &primary)
Definition sqlite_catalog.h:136
void identity(bytes &out, object_id const &value)
Definition sqlite_catalog.h:117
Definition active_engine.h:18
Selects runtime checkpoint codecs and encodes binary admission intervals.
Seals new runtime owners once and stops at acknowledged shared dependencies.
Retains one publication's exact owner closure without revisiting shared suffixes.
Stores retained roots, timeline generations and exact file graphs in optional SQLite metadata.
Definition sqlite_catalog.h:71
std::vector< blob_identity > pairs
Definition sqlite_catalog.h:72
std::vector< object_id > natives
Definition sqlite_catalog.h:73
Definition sqlite_catalog.h:39
Definition sqlite_catalog.h:76
catalog_auxiliary_roots auxiliary
Definition sqlite_catalog.h:79
catalog_timeline_head timeline
Definition sqlite_catalog.h:77
std::vector< std::byte > checkpoint
Definition sqlite_catalog.h:78
blob_identity head
Definition sqlite_catalog.h:60
native_pointer native(object_id const &id)
Definition mapped_cola.h:221
pair_type pair(blob_identity const &head)
Definition mapped_cola.h:227
Definition object_path.h:38
Definition runtime_store.h:31
object_id operator()() const
Definition runtime_store.h:32
Definition runtime_checkpoint.h:62
Definition runtime_store.h:300
catalog_auxiliary_roots auxiliary
Definition runtime_store.h:300
blob_identity head
Definition runtime_store.h:300
Definition runtime_store.h:237
pair_type pair(blob_identity const &id) const
Definition runtime_store.h:239
registry_type const & retained
Definition runtime_store.h:238
native_pointer native(object_id const &id) const
Definition runtime_store.h:244
Definition runtime_store.h:162
pair_type pair(blob_identity const &id)
Definition runtime_store.h:179
native_pointer native(object_id const &id)
Definition runtime_store.h:169
runtime_store & store
Definition runtime_store.h:163
bool restricted
Definition runtime_store.h:167
bool seed_root(pair_type value)
Definition runtime_store.h:208
bool seed_native(object_id const &id, native_pointer value)
Definition runtime_store.h:204
resolver(runtime_store &value)
Definition runtime_store.h:168
std::unordered_map< std::string, pair_type > pairs
Definition runtime_store.h:166
mapped_resolver mapped
Definition runtime_store.h:164
std::unordered_map< std::string, native_pointer > natives
Definition runtime_store.h:165
Definition runtime_store.h:214
std::vector< pair_type > pairs
Definition runtime_store.h:215
std::vector< typename registry_type::native_root > natives
Definition runtime_store.h:216
Definition runtime_graph_sealer.h:22
void clear() noexcept
Definition runtime_registry.h:80
native_pointer native(object_id const &id) const
Definition runtime_registry.h:54
pair_type pair(blob_identity const &id) const
Definition runtime_registry.h:47
bool replace(std::vector< pair_type > pairs, std::vector< native_root > natives)
Definition runtime_registry.h:64
Definition runtime_store.h:58
auto sealer()
Definition runtime_store.h:159
stored_type publish(catalog_session_head const &expected, snapshot_type const &source, std::span< std::byte const > semantic={})
Definition runtime_store.h:122
Family family_type
Definition runtime_store.h:60
std::optional< stored_type > find_save(std::string_view name)
Definition runtime_store.h:98
typename Family::node_type node_type
Definition runtime_store.h:64
stored_type create_session(std::string_view name, snapshot_type const &source, std::span< std::byte const > semantic={})
Definition runtime_store.h:110
typename node_type::pair_type pair_type
Definition runtime_store.h:66
stored_type restore(catalog_session_head head, snapshot_type const *source=nullptr)
Definition runtime_store.h:260
typename node_type::native_pointer native_pointer
Definition runtime_store.h:67
runtime_store & operator=(runtime_store const &)=delete
stored_type decode_retained(catalog_session_head head)
Definition runtime_store.h:250
typename Family::native_type native_type
Definition runtime_store.h:65
P policy_type
Definition runtime_store.h:59
Ids ids_
Definition runtime_store.h:152
typename Family::snapshot_type snapshot_type
Definition runtime_store.h:62
persisted persist(snapshot_type const &source)
Definition runtime_store.h:301
runtime_store(catalog_type catalog, Ids ids)
Definition runtime_store.h:156
void prepare(snapshot_type const &source)
Definition runtime_store.h:105
void save(std::string_view name, catalog_session_head const &source)
Definition runtime_store.h:141
stored_type fork(std::string_view name, catalog_session_head const &source)
Definition runtime_store.h:136
std::string operation()
Definition runtime_store.h:158
static runtime_store open(std::filesystem::path const &root, Ids ids={}, catalog_options options={}, Ops ops={})
Definition runtime_store.h:79
std::string last_operation_
Definition runtime_store.h:154
bool failed_
Definition runtime_store.h:153
bool failed() const noexcept
Definition runtime_store.h:89
std::string const & last_operation() const noexcept
Definition runtime_store.h:146
registry_type retained_
Definition runtime_store.h:150
static runtime_store create(std::filesystem::path const &root, Ids ids={}, catalog_options options={}, Ops ops={})
Definition runtime_store.h:74
runtime_store(runtime_store const &)=delete
catalog_type catalog_
Definition runtime_store.h:151
static std::optional< roots > retained_roots(catalog_session_head const &head, Resolver &loaded)
Definition runtime_store.h:218
std::filesystem::path const & root() const &&=delete
std::optional< stored_type > find(std::string_view name)
Definition runtime_store.h:93
std::filesystem::path const & root() const &noexcept
Definition runtime_store.h:90
std::remove_const_t< typename mapped_pointer::element_type > mapped_type
Definition runtime_store.h:69
runtime_store(runtime_store &&) noexcept(std::is_nothrow_move_constructible_v< Ids >)=default
void require_active() const
Definition runtime_store.h:157
decltype(std::declval< node_type const & >().mapped()) mapped_pointer
Definition runtime_store.h:68
Definition sqlite_catalog.h:351
std::optional< catalog_session_head > find_session(std::string_view name) const
Definition sqlite_catalog.h:925
static sqlite_catalog create_sessions(std::filesystem::path const &root, object_id const &identity, catalog_options options={}, Ops ops={})
Definition sqlite_catalog.h:375
static sqlite_catalog open(std::filesystem::path const &root, catalog_options options={}, Ops ops={})
Definition sqlite_catalog.h:379
std::filesystem::path const & root() const &noexcept
Definition sqlite_catalog.h:396
void save_session(std::string_view op, std::string_view name, catalog_session_head const &source)
Definition sqlite_catalog.h:999
bool poisoned() const noexcept
Definition sqlite_catalog.h:391
catalog_session_head create_session(std::string_view op, std::string_view name, blob_identity const &head, std::span< std::byte const > checkpoint, catalog_auxiliary_roots auxiliary={})
Definition sqlite_catalog.h:934
std::optional< catalog_session_head > find_saved_session(std::string_view name) const
Definition sqlite_catalog.h:1018
catalog_session_head fork_session(std::string_view op, std::string_view name, catalog_session_head const &source)
Definition sqlite_catalog.h:980
catalog_session_publication publish_session(std::string_view op, catalog_session_head const &expected, blob_identity const &candidate, std::span< std::byte const > checkpoint, catalog_auxiliary_roots auxiliary={})
Definition sqlite_catalog.h:950
Definition runtime_store.h:49
catalog_session_head head
Definition runtime_store.h:50
Family::snapshot_type snapshot
Definition runtime_store.h:51
std::vector< std::byte > semantic
Definition runtime_store.h:52