CCF
Loading...
Searching...
No Matches
untyped_map.h
Go to the documentation of this file.
1// Copyright (c) Microsoft Corporation. All rights reserved.
2// Licensed under the Apache 2.0 License.
3#pragma once
4
7#include "ccf/pal/locking.h"
8#include "ds/dl_list.h"
10#include "kv/kv_serialiser.h"
11#include "kv/kv_types.h"
13
14#include <functional>
15#include <list>
16#include <optional>
17#include <unordered_set>
18
19namespace ccf::kv::untyped
20{
22 {
23 LocalCommit() = default;
25 version(v),
26 state(std::move(s)),
27 writes(std::move(w))
28 {}
29
33 LocalCommit* next = nullptr;
34 LocalCommit* prev = nullptr;
35 };
37
38 struct Roll
39 {
40 std::unique_ptr<LocalCommits> commits;
42
44
46 {
47 commits->clear();
48 commits->insert_back(create_new_local_commit(0, State(), Write()));
49 }
50
51 template <typename... Args>
53 {
55 if (c == nullptr)
56 {
57 // NOLINTNEXTLINE(cppcoreguidelines-owning-memory)
58 c = new LocalCommit(std::forward<Args>(args)...);
59 }
60 else
61 {
62 c->~LocalCommit();
63 new (c) LocalCommit(std::forward<Args>(args)...);
64 }
65 return c;
66 }
67 };
68
69 class Map : public AbstractMap
70 {
71 public:
75
77
80
81 private:
82 AbstractStore* store;
83 Roll roll;
84 CommitHook global_hook = nullptr;
85 MapHook hook = nullptr;
86 std::list<std::pair<Version, Write>> commit_deltas;
88 const SecurityDomain security_domain;
89
90 static State deserialize_map_snapshot(
91 std::span<const uint8_t> serialized_state)
92 {
93 State map;
94 const uint8_t* data = serialized_state.data();
95 size_t size = serialized_state.size();
96
97 while (size != 0)
98 {
99 // Deserialize the key
100 size_t key_size = size;
101 K key = map::deserialize<K>(data, size);
102 key_size -= size;
103 serialized::skip(data, size, map::get_padding(key_size));
104
105 // Deserialize the value
106 size_t value_size = size;
107 VersionV value = map::deserialize<VersionV>(data, size);
108 value_size -= size;
109 serialized::skip(data, size, map::get_padding(value_size));
110
111 // Version was previously signed, with negative values indicating
112 // deletions. Maintain ability to parse those snapshots, but do not
113 // retain these deletions locally.
114 if ((int64_t)value.version >= 0)
115 {
116 map = map.put(key, value);
117 }
118 }
119 return map;
120 }
121
122 public:
124 {
125 protected:
127
129
131
132 bool changes = false;
133 bool committed_writes = false;
134
135 public:
136 HandleCommitter(Map& m, ChangeSet& change_set_) :
137 map(m),
138 change_set(change_set_)
139 {}
140
141 // Commit-related methods
142 bool has_writes() override
143 {
144 return committed_writes || change_set.has_writes();
145 }
146
147 bool prepare() override
148 {
149 auto& map_roll = map.get_roll();
150
151 // If the parent map has rolled back since this transaction began, this
152 // transaction must fail.
153 if (change_set.rollback_counter != map_roll.rollback_counter)
154 {
155 return false;
156 }
157
158 // If we have iterated over the map, check for a global version match.
159 // Check each key in our read set.
160 auto* current = map_roll.commits->get_tail();
161 if (
162 (change_set.read_version != NoVersion) &&
163 (change_set.read_version != current->version))
164 {
165 LOG_DEBUG_FMT("Read version {} is invalid", change_set.read_version);
166 return false;
167 }
168
169 // Check each key in our read set.
170 for (const auto& [key, value] : change_set.reads)
171 {
172 // Get the value from the current state.
173 auto search = current->state.get(key);
174
175 if (std::get<0>(value) == NoVersion)
176 {
177 // If we depend on the key not existing, it must be absent.
178 if (search.has_value())
179 {
180 LOG_DEBUG_FMT("Read depends on non-existing entry");
181 return false;
182 }
183 }
184 else
185 {
186 // If the transaction depends on the key existing, it must be
187 // present and have the the expected version. If also tracking
188 // conflicts then ensure that the read versions also match.
189 if (
190 !search.has_value() ||
191 std::get<0>(value) != search.value().version)
192 {
193 LOG_DEBUG_FMT("Read depends on invalid version of entry");
194 return false;
195 }
196 }
197 }
198
199 return true;
200 }
201
202 void commit(Version v, bool track_deletes_on_missing_keys) override
203 {
204 if (change_set.writes.empty())
205 {
206 commit_version = change_set.start_version;
207 return;
208 }
209
210 auto& map_roll = map.get_roll();
211 auto state = map_roll.commits->get_tail()->state;
212
213 // Record our commit time.
214 commit_version = v;
215 committed_writes = true;
216
217 for (const auto& [key, maybe_value] : change_set.writes)
218 {
219 if (maybe_value.has_value())
220 {
221 // Write the new value with the global version.
222 changes = true;
223 // NOLINTNEXTLINE(bugprone-unchecked-optional-access)
224 state = state.put(key, VersionV{v, v, maybe_value.value()});
225 }
226 else
227 {
228 // Delete the key if it exists
229 auto search = state.get(key);
230 if (search.has_value())
231 {
232 changes = true;
233 state = state.remove(key);
234 }
235 else if (track_deletes_on_missing_keys)
236 {
237 // track deletes even when they delete keys that don't exist in
238 // this map's state
239 changes = true;
240 }
241 }
242 }
243
244 if (changes)
245 {
246 map.roll.commits->insert_back(map.roll.create_new_local_commit(
247 v, std::move(state), change_set.writes));
248 }
249 }
250
252 {
253 // This is run separately from commit so that all commits in the Tx
254 // have been applied before map hooks are run. The maps in the Tx
255 // are still locked when post_commit is run.
256 return map.trigger_map_hook(commit_version, change_set.writes);
257 }
258
260 {
261 commit_version = v;
262 }
263 };
264
266 {
267 private:
268 const std::string name;
269 const SecurityDomain security_domain;
270 const ccf::kv::Version version;
271
272 std::unique_ptr<StateSnapshot> map_snapshot;
273
274 public:
276 std::string name_,
277 SecurityDomain security_domain_,
278 ccf::kv::Version version_,
279 std::unique_ptr<StateSnapshot>&& map_snapshot_) :
280 name(std::move(name_)),
281 security_domain(security_domain_),
282 version(version_),
283 map_snapshot(std::move(map_snapshot_))
284 {}
285
286 void serialise(KvStoreSerialiser& s) override
287 {
288 LOG_TRACE_FMT("Serialising snapshot for map: {}", name);
289 s.start_map(name, security_domain);
290 s.serialise_entry_version(version);
291
292 std::vector<uint8_t> ret(map_snapshot->get_serialized_size());
293 map_snapshot->serialize(ret.data());
294 s.serialise_raw(ret);
295 }
296
297 [[nodiscard]] SecurityDomain get_security_domain() const override
298 {
299 return security_domain;
300 }
301 };
302
303 // Public typedefs for external consumption
308
310 AbstractStore* store_,
311 const std::string& name_,
312 SecurityDomain security_domain_) :
313 AbstractMap(name_),
314 store(store_),
315 roll{std::make_unique<LocalCommits>(), 0, {}},
316 security_domain(security_domain_)
317 {
318 roll.reset_commits();
319 }
320
321 Map(const Map& that) = delete;
322
324 {
325 return static_cast<AbstractMap*>(new Map(other, name, security_domain));
326 }
327
329 const AbstractChangeSet* changes,
331 bool include_reads) override
332 {
333 const auto* const non_abstract =
334 dynamic_cast<const ccf::kv::untyped::ChangeSet*>(changes);
335 if (non_abstract == nullptr)
336 {
337 LOG_FAIL_FMT("Unable to serialise map due to type mismatch");
338 return;
339 }
340
341 const auto& change_set = *non_abstract;
342
343 s.start_map(name, security_domain);
344
345 if (include_reads)
346 {
347 s.serialise_entry_version(change_set.read_version);
348
349 s.serialise_count_header(change_set.reads.size());
350 for (const auto& [key, value] : change_set.reads)
351 {
352 s.serialise_read(key, std::get<0>(value));
353 }
354 }
355 else
356 {
357 s.serialise_entry_version(NoVersion);
359 }
360
361 uint64_t write_ctr = 0;
362 uint64_t remove_ctr = 0;
363 for (const auto& [key, maybe_value] : change_set.writes)
364 {
365 if (maybe_value.has_value())
366 {
367 ++write_ctr;
368 }
369 else
370 {
371 ++remove_ctr;
372 }
373 }
374
375 s.serialise_count_header(write_ctr);
376 for (const auto& [key, maybe_value] : change_set.writes)
377 {
378 if (maybe_value.has_value())
379 {
380 // NOLINTNEXTLINE(bugprone-unchecked-optional-access)
381 s.serialise_write(key, maybe_value.value());
382 }
383 }
384
385 s.serialise_count_header(remove_ctr);
386 for (const auto& [key, maybe_value] : change_set.writes)
387 {
388 if (!maybe_value.has_value())
389 {
390 s.serialise_remove(key);
391 }
392 }
393 }
394
396 {
397 private:
398 Map& map;
399
400 SnapshotChangeSet& change_set;
401
402 public:
404 map(m),
405 change_set(change_set_)
406 {}
407
408 bool has_writes() override
409 {
410 return true;
411 }
412
413 bool prepare() override
414 {
415 // Snapshots never conflict
416 return true;
417 }
418
419 void commit(Version v, bool track_deletes_on_missing_keys) override
420 {
421 (void)v;
422 (void)track_deletes_on_missing_keys;
423 // Version argument is ignored. The version of the roll after the
424 // snapshot is applied depends on the version of the map at which the
425 // snapshot was taken.
426 map.roll.reset_commits();
427 map.roll.rollback_counter++;
428
429 auto* r = map.roll.commits->get_head();
430
431 r->state = change_set.state;
432 r->version = change_set.version;
433
434 // Executing hooks from snapshot requires copying the entire snapshotted
435 // state so only do it if there's a hook on the table
436 if (map.hook || map.global_hook)
437 {
438 r->state.foreach([&r](const K& k, const VersionV& v) {
439 r->writes[k] = v.value;
440 return true;
441 });
442 }
443 }
444
446 {
447 auto* r = map.roll.commits->get_head();
448 return map.trigger_map_hook(change_set.version, r->writes);
449 }
450 };
451
453 {
454 // Create a new empty change set, deserialising d's contents into it.
455 auto v = d.deserialise_entry_version();
456 auto map_snapshot = d.deserialise_raw();
457
458 return std::make_unique<SnapshotChangeSet>(
459 deserialize_map_snapshot(map_snapshot), v);
460 }
461
463 {
464 return deserialise_internal(d, version);
465 }
466
468 {
469 // Create a new change set, and deserialise d's contents into it.
470 auto change_set_ptr = create_change_set(version, false);
471 if (change_set_ptr == nullptr)
472 {
474 "Failed to create change set over '{}' at {} - too early",
475 name,
476 version);
477 throw std::logic_error("Can't create change set");
478 }
479
480 auto& change_set = *change_set_ptr;
481
482 uint64_t ctr = 0;
483
484 auto rv = d.deserialise_entry_version();
485 if (rv != NoVersion)
486 {
487 change_set.read_version = rv;
488 }
489
490 ctr = d.deserialise_read_header();
491 for (size_t i = 0; i < ctr; ++i)
492 {
493 auto r = d.deserialise_read();
494 change_set.reads[std::get<0>(r)] =
495 std::make_tuple(std::get<1>(r), NoVersion);
496 }
497
498 ctr = d.deserialise_write_header();
499 for (size_t i = 0; i < ctr; ++i)
500 {
501 auto w = d.deserialise_write();
502 change_set.writes[std::get<0>(w)] = std::get<1>(w);
503 }
504
506 for (size_t i = 0; i < ctr; ++i)
507 {
508 auto r = d.deserialise_remove();
509 change_set.writes[r] = std::nullopt;
510 }
511
512 return change_set_ptr;
513 }
514
515 std::unique_ptr<AbstractCommitter> create_committer(
516 AbstractChangeSet* changes) override
517 {
518 auto* non_abstract = dynamic_cast<ChangeSet*>(changes);
519 if (non_abstract == nullptr)
520 {
521 throw std::logic_error("Type confusion error");
522 }
523
524 auto* snapshot_change_set =
525 dynamic_cast<SnapshotChangeSet*>(non_abstract);
526 if (snapshot_change_set != nullptr)
527 {
528 return std::make_unique<SnapshotHandleCommitter>(
529 *this, *snapshot_change_set);
530 }
531
532 return std::make_unique<HandleCommitter>(*this, *non_abstract);
533 }
534
540 {
541 return store;
542 }
543
544 void set_map_hook(const MapHook& hook_)
545 {
546 hook = hook_;
547 }
548
550 {
551 hook = nullptr;
552 }
553
558 void set_global_hook(const CommitHook& hook_)
559 {
560 global_hook = hook_;
561 }
562
566 {
567 global_hook = nullptr;
568 }
569
575 {
576 return security_domain;
577 }
578
579 bool operator==(const Map& that) const
580 {
581 if (name != that.name)
582 {
583 return false;
584 }
585
586 auto* state1 = roll.commits->get_tail();
587 auto* state2 = that.roll.commits->get_tail();
588
589 if (state1->version != state2->version)
590 {
591 return false;
592 }
593
594 size_t count = 0;
595 state2->state.foreach([&count](const K&, const VersionV&) {
596 count++;
597 return true;
598 });
599
600 size_t i = 0;
601 bool ok =
602 state1->state.foreach([&state2, &i](const K& k, const VersionV& v) {
603 auto search = state2->state.get(k);
604
605 if (search.has_value())
606 {
607 auto& found = search.value();
608 if (found.version != v.version)
609 {
610 return false;
611 }
612 if (found.value != v.value)
613 {
614 return false;
615 }
616 }
617 else
618 {
619 return false;
620 }
621
622 i++;
623 return true;
624 });
625
626 if (i != count)
627 {
628 ok = false;
629 }
630
631 return ok;
632 }
633
634#ifndef __cpp_impl_three_way_comparison
635 bool operator!=(const Map& that) const
636 {
637 return !(*this == that);
638 }
639#endif
640
641 std::unique_ptr<AbstractMap::Snapshot> snapshot(Version v) override
642 {
643 // This takes a snapshot of the state of the map at the last entry
644 // committed at or before this version. The Map expects to be locked while
645 // taking the snapshot.
646 auto* r = roll.commits->get_head();
647
648 for (auto* current = roll.commits->get_tail(); current != nullptr;
649 current = current->prev)
650 {
651 if (current->version <= v)
652 {
653 r = current;
654 break;
655 }
656 }
657
658 return std::make_unique<Snapshot>(
659 name, security_domain, r->version, r->state.make_snapshot());
660 }
661
662 void compact(Version v) override
663 {
664 // This discards available rollback state before version v, and
665 // populates the commit_deltas to be passed to the global commit hook,
666 // if there is one, up to version v. The Map expects to be locked during
667 // compaction.
668 while (roll.commits->get_head() != roll.commits->get_tail())
669 {
670 auto* r = roll.commits->get_head();
671
672 // Globally committed but not discardable.
673 if (r->version == v)
674 {
675 // We know that write set is not empty.
676 if (global_hook)
677 {
678 commit_deltas.emplace_back(r->version, std::move(r->writes));
679 }
680 return;
681 }
682
683 // Discardable, so move to commit_deltas.
684 if (global_hook && !r->writes.empty())
685 {
686 commit_deltas.emplace_back(r->version, std::move(r->writes));
687 }
688
689 // Stop if the next state may be rolled back or is the only state.
690 // This ensures there is always a state present.
691 if (r->next->version > v)
692 {
693 return;
694 }
695
696 auto* c = roll.commits->pop();
697 roll.empty_commits.insert(c);
698 }
699
700 // There is only one roll. We may need to call the commit hook.
701 auto* r = roll.commits->get_head();
702
703 if (global_hook && !r->writes.empty())
704 {
705 commit_deltas.emplace_back(r->version, std::move(r->writes));
706 }
707 }
708
709 void post_compact() override
710 {
711 if (global_hook)
712 {
713 for (auto& [version, writes] : commit_deltas)
714 {
716 "Executing global hook on table {} at version {}",
717 get_name(),
718 version);
719 global_hook(version, writes);
720 }
721 }
722
723 commit_deltas.clear();
724 }
725
726 void rollback(Version v) override
727 {
728 // This rolls the current state back to version v.
729 // The Map expects to be locked during rollback.
730 bool advance = false;
731
732 while (roll.commits->get_head() != roll.commits->get_tail())
733 {
734 auto* r = roll.commits->get_tail();
735
736 // The initial empty state has v = 0, so will not be discarded if it
737 // is present.
738 if (r->version <= v)
739 {
740 break;
741 }
742
743 advance = true;
744 auto* c = roll.commits->pop_tail();
745 roll.empty_commits.insert(c);
746 }
747
748 if (advance)
749 {
750 roll.rollback_counter++;
751 }
752 }
753
754 void clear() override
755 {
756 // This discards all entries in the roll and resets the rollback
757 // counter. The Map expects to be locked before clearing it.
758 roll.reset_commits();
759 roll.rollback_counter = 0;
760 }
761
762 void lock() override
763 {
764 sl.lock();
765 }
766
767 void unlock() override
768 {
769 sl.unlock();
770 }
771
772 // NOLINTNEXTLINE(bugprone-exception-escape)
773 void swap(AbstractMap* map_) override
774 {
775 auto* map = dynamic_cast<Map*>(map_);
776 if (map == nullptr)
777 {
778 throw std::logic_error(
779 "Attempted to swap maps with incompatible types");
780 }
781
782 std::swap(roll, map->roll);
783 }
784
786 Version version, bool track_deletes_on_missing_keys)
787 {
788 lock();
789
790 ChangeSetPtr changes = nullptr;
791
792 // Find the last entry committed at or before this version.
793 for (auto* current = roll.commits->get_tail(); current != nullptr;
794 current = current->prev)
795 {
796 if (current->version <= version)
797 {
799 if (track_deletes_on_missing_keys)
800 {
801 writes = current->writes;
802 }
803 changes = std::make_unique<untyped::ChangeSet>(
804 roll.rollback_counter,
805 current->state,
806 roll.commits->get_head()->state,
807 writes,
808 current->version);
809 break;
810 }
811 }
812
813 // Returning nullptr is allowed, and indicates that we have no suitable
814 // version - the version requested is _earlier_ than anything in the
815 // roll
816
817 unlock();
818 return changes;
819 }
820
822 {
823 return roll;
824 }
825
827 {
828 if (hook && !writes.empty())
829 {
831 "Executing local hook on table {} at version {}",
832 get_name(),
833 version);
834 return hook(version, writes);
835 }
836 return nullptr;
837 }
838 };
839}
Definition kv_types.h:520
Definition kv_types.h:528
Definition kv_types.h:544
Definition kv_types.h:541
Definition kv_types.h:610
Definition generic_serialise_wrapper.h:239
std::tuple< SerialisedKey, Version > deserialise_read()
Definition generic_serialise_wrapper.h:416
std::vector< uint8_t > deserialise_raw()
Definition generic_serialise_wrapper.h:435
std::tuple< SerialisedKey, SerialisedValue > deserialise_write()
Definition generic_serialise_wrapper.h:428
uint64_t deserialise_write_header()
Definition generic_serialise_wrapper.h:423
uint64_t deserialise_remove_header()
Definition generic_serialise_wrapper.h:445
uint64_t deserialise_read_header()
Definition generic_serialise_wrapper.h:411
Version deserialise_entry_version()
Definition generic_serialise_wrapper.h:406
SerialisedKey deserialise_remove()
Definition generic_serialise_wrapper.h:450
Definition generic_serialise_wrapper.h:20
void serialise_count_header(uint64_t ctr)
Definition generic_serialise_wrapper.h:124
void serialise_remove(const SerialisedKey &k)
Definition generic_serialise_wrapper.h:141
void serialise_raw(const std::vector< uint8_t > &raw)
Definition generic_serialise_wrapper.h:108
void start_map(const std::string &name, SecurityDomain domain)
Definition generic_serialise_wrapper.h:92
void serialise_entry_version(const Version &version)
Definition generic_serialise_wrapper.h:119
void serialise_read(const SerialisedKey &k, const Version &version)
Definition generic_serialise_wrapper.h:129
void serialise_write(const SerialisedKey &k, const SerialisedValue &v)
Definition generic_serialise_wrapper.h:135
Definition untyped_map_diff.h:19
Definition untyped_map_handle.h:18
Definition untyped_map.h:124
void commit(Version v, bool track_deletes_on_missing_keys) override
Definition untyped_map.h:202
bool prepare() override
Definition untyped_map.h:147
Version commit_version
Definition untyped_map.h:130
bool changes
Definition untyped_map.h:132
bool committed_writes
Definition untyped_map.h:133
void set_commit_version(Version v)
Definition untyped_map.h:259
ConsensusHookPtr post_commit() override
Definition untyped_map.h:251
Map & map
Definition untyped_map.h:126
ChangeSet & change_set
Definition untyped_map.h:128
HandleCommitter(Map &m, ChangeSet &change_set_)
Definition untyped_map.h:136
bool has_writes() override
Definition untyped_map.h:142
bool prepare() override
Definition untyped_map.h:413
SnapshotHandleCommitter(Map &m, SnapshotChangeSet &change_set_)
Definition untyped_map.h:403
bool has_writes() override
Definition untyped_map.h:408
void commit(Version v, bool track_deletes_on_missing_keys) override
Definition untyped_map.h:419
ConsensusHookPtr post_commit() override
Definition untyped_map.h:445
Definition untyped_map.h:266
Snapshot(std::string name_, SecurityDomain security_domain_, ccf::kv::Version version_, std::unique_ptr< StateSnapshot > &&map_snapshot_)
Definition untyped_map.h:275
void serialise(KvStoreSerialiser &s) override
Definition untyped_map.h:286
SecurityDomain get_security_domain() const override
Definition untyped_map.h:297
Definition untyped_map.h:70
Map(const Map &that)=delete
ChangeSetPtr deserialise_changes(KvStoreDeserialiser &d, Version version)
Definition untyped_map.h:462
void swap(AbstractMap *map_) override
Definition untyped_map.h:773
std::unique_ptr< AbstractCommitter > create_committer(AbstractChangeSet *changes) override
Definition untyped_map.h:515
void compact(Version v) override
Definition untyped_map.h:662
ConsensusHookPtr trigger_map_hook(Version version, const Write &writes)
Definition untyped_map.h:826
ChangeSetPtr deserialise_internal(KvStoreDeserialiser &d, Version version)
Definition untyped_map.h:467
bool operator==(const Map &that) const
Definition untyped_map.h:579
Map(AbstractStore *store_, const std::string &name_, SecurityDomain security_domain_)
Definition untyped_map.h:309
SecurityDomain get_security_domain() override
Definition untyped_map.h:574
void unlock() override
Definition untyped_map.h:767
ccf::kv::untyped::CommitHook CommitHook
Definition untyped_map.h:78
AbstractMap * clone(AbstractStore *other) override
Definition untyped_map.h:323
void clear() override
Definition untyped_map.h:754
void set_global_hook(const CommitHook &hook_)
Definition untyped_map.h:558
ccf::kv::untyped::SerialisedEntry V
Definition untyped_map.h:73
void serialise_changes(const AbstractChangeSet *changes, KvStoreSerialiser &s, bool include_reads) override
Definition untyped_map.h:328
ccf::kv::untyped::SerialisedKeyHasher H
Definition untyped_map.h:74
ChangeSetPtr create_change_set(Version version, bool track_deletes_on_missing_keys)
Definition untyped_map.h:785
ccf::kv::untyped::MapHook MapHook
Definition untyped_map.h:79
Roll & get_roll()
Definition untyped_map.h:821
bool operator!=(const Map &that) const
Definition untyped_map.h:635
ccf::kv::untyped::State::Snapshot StateSnapshot
Definition untyped_map.h:76
ccf::kv::untyped::SerialisedEntry K
Definition untyped_map.h:72
void unset_global_hook()
Definition untyped_map.h:565
ChangeSetPtr deserialise_snapshot_changes(KvStoreDeserialiser &d)
Definition untyped_map.h:452
void lock() override
Definition untyped_map.h:762
void set_map_hook(const MapHook &hook_)
Definition untyped_map.h:544
AbstractStore * get_store() override
Definition untyped_map.h:539
void unset_map_hook()
Definition untyped_map.h:549
void post_compact() override
Definition untyped_map.h:709
void rollback(Version v) override
Definition untyped_map.h:726
std::unique_ptr< AbstractMap::Snapshot > snapshot(Version v) override
Definition untyped_map.h:641
Snapshot< K, VersionV, H > Snapshot
Definition champ_map.h:431
T * pop()
Definition dl_list.h:64
#define LOG_TRACE_FMT
Definition internal_logger.h:13
#define LOG_DEBUG_FMT
Definition internal_logger.h:14
#define LOG_FAIL_FMT
Definition internal_logger.h:16
Definition untyped.h:12
ccf::kv::CommitHook< Write > CommitHook
Definition untyped.h:18
ccf::ByteVector SerialisedEntry
Definition untyped_change_set.h:19
std::hash< SerialisedEntry > SerialisedKeyHasher
Definition untyped_change_set.h:20
std::map< ccf::kv::serialisers::SerialisedEntry, std::optional< ccf::kv::serialisers::SerialisedEntry > > Write
Definition untyped.h:16
std::unique_ptr< ChangeSet > ChangeSetPtr
Definition untyped_change_set.h:78
ccf::kv::MapHook< Write > MapHook
Definition untyped.h:19
champ::Map< K, VersionV, H > State
Definition untyped_change_set.h:29
std::unique_ptr< ConsensusHook > ConsensusHookPtr
Definition hooks.h:21
SecurityDomain
Definition kv_types.h:216
uint64_t Version
Definition version.h:8
std::mutex Mutex
Definition locking.h:12
Definition map_serializers.h:11
void skip(const uint8_t *&data, size_t &size, size_t skip)
Definition serialized.h:165
STL namespace.
std::string name
Definition get_name.h:12
Definition version_v.h:11
V value
Definition version_v.h:14
Version version
Definition version_v.h:12
Definition untyped_change_set.h:43
ccf::kv::untyped::Read reads
Definition untyped_change_set.h:54
const size_t rollback_counter
Definition untyped_change_set.h:48
bool has_writes() const override
Definition untyped_change_set.h:72
Version read_version
Definition untyped_change_set.h:53
const Version start_version
Definition untyped_change_set.h:51
ccf::kv::untyped::Write writes
Definition untyped_change_set.h:55
Definition untyped_map.h:22
State state
Definition untyped_map.h:31
LocalCommit * next
Definition untyped_map.h:33
LocalCommit(Version v, State &&s, Write w)
Definition untyped_map.h:24
LocalCommit * prev
Definition untyped_map.h:34
Version version
Definition untyped_map.h:30
Write writes
Definition untyped_map.h:32
Definition untyped_map.h:39
LocalCommits empty_commits
Definition untyped_map.h:43
LocalCommit * create_new_local_commit(Args &&... args)
Definition untyped_map.h:52
void reset_commits()
Definition untyped_map.h:45
size_t rollback_counter
Definition untyped_map.h:41
std::unique_ptr< LocalCommits > commits
Definition untyped_map.h:40
Definition untyped_change_set.h:83
const ccf::kv::untyped::State state
Definition untyped_change_set.h:84
const Version version
Definition untyped_change_set.h:85