8 #include "scale/scale.hpp" 13 case E::REQUIRED_DIGESTS_NOT_FOUND:
14 return "the block must contain at least BABE " 15 "header and seal digests";
16 case E::NO_TRAILING_SEAL_DIGEST:
17 return "the block must contain a seal digest as the last digest";
18 case E::MULTIPLE_EPOCH_CHANGE_DIGESTS:
19 return "the block contains multiple epoch change digests";
20 case E::NEXT_EPOCH_DIGEST_DOES_NOT_EXIST:
21 return "next epoch digest does not exist";
23 return "unknown error";
31 if (block_header.
digest.size() < 2) {
34 const auto &digests = block_header.
digest;
37 auto seal_opt = getFromVariant<primitives::Seal>(digests.back());
38 if (not seal_opt.has_value()) {
42 OUTCOME_TRY(babe_seal_res, scale::decode<Seal>(seal_opt->get().data));
44 for (
const auto &digest :
46 if (
auto pre_runtime_opt = getFromVariant<primitives::PreRuntime>(digest);
47 pre_runtime_opt.has_value()) {
49 scale::decode<BabeBlockHeader>(pre_runtime_opt->get().data);
52 return {babe_seal_res, header.value()};
63 outcome::result<EpochDigest> epoch_digest =
66 for (
const auto &log : header.
digest) {
71 auto consensus_log_res =
72 scale::decode<primitives::BabeDigest>(consensus.data);
73 if (not consensus_log_res) {
78 consensus_log_res.value(),
80 if (not epoch_digest) {
81 epoch_digest =
static_cast<EpochDigest>(next_epoch);
outcome::result< std::pair< Seal, BabeBlockHeader > > getBabeDigests(const primitives::BlockHeader &block_header)
Data are corresponding to the epoch.
outcome::result< EpochDigest > getNextEpochDigest(const primitives::BlockHeader &header)
ConsensusEngineId consensus_engine_id
gsl::span< const uint8_t > make_span(const rocksdb::Slice &s)
OUTCOME_CPP_DEFINE_CATEGORY(kagome::consensus, DigestError, e)