jam_std_common/safrole/
mod.rs

1//! Primitives for Safrole consensus.
2
3use crate::{bandersnatch, ed25519, Entropy, EpochPeriod, ValKeyset};
4use jam_types::{BoundedVec, FixedVec, Slot};
5use scale::{Decode, Encode, MaxEncodedLen};
6
7pub mod ticket;
8
9/// Index of an epoch.
10pub type EpochIndex = Slot;
11
12pub type EpochKeys = FixedVec<EpochKeySet, jam_types::ValCount>;
13pub type FallbackKeys = FixedVec<bandersnatch::Public, EpochPeriod>;
14pub type EpochTickets = FixedVec<ticket::TicketBody, EpochPeriod>;
15pub type EpochTicketsAccumulator = BoundedVec<ticket::TicketBody, EpochPeriod>;
16
17/// A pair of bandersnatch and ed25519 key for the validator.
18#[derive(Debug, Clone, PartialEq, Eq, Encode, Decode, MaxEncodedLen)]
19pub struct EpochKeySet {
20	/// Bandersnatch key.
21	pub bandersnatch: bandersnatch::Public,
22	/// Ed25519 key.
23	pub ed25519: ed25519::Public,
24}
25
26impl From<&ValKeyset> for EpochKeySet {
27	fn from(keyset: &ValKeyset) -> Self {
28		Self { bandersnatch: keyset.bandersnatch, ed25519: keyset.ed25519 }
29	}
30}
31
32/// Information about the next epoch.
33///
34/// This is mandatory in the first block of each epoch.
35#[derive(Debug, Clone, PartialEq, Eq, Encode, Decode, MaxEncodedLen)]
36pub struct NextEpochDescriptor {
37	/// Next epoch entropy value.
38	pub entropy: Entropy,
39	/// Entropy used to generate tickets for target epoch's slot.
40	pub tickets_entropy: Entropy,
41	/// Validators list.
42	pub validators: EpochKeys,
43}
44
45#[derive(Encode, Decode, Debug, Clone)]
46pub enum TicketOrKey {
47	Ticket(ticket::TicketBody),
48	Key(bandersnatch::Public),
49}
50
51impl TicketOrKey {
52	pub fn ticket(self) -> Option<ticket::TicketBody> {
53		match self {
54			TicketOrKey::Ticket(t) => Some(t),
55			TicketOrKey::Key(_) => None,
56		}
57	}
58}
59
60#[derive(Encode, Decode, Debug, Clone, PartialEq, Eq)]
61pub enum TicketsOrKeys {
62	Tickets(EpochTickets),
63	Keys(FallbackKeys),
64}
65
66impl TicketsOrKeys {
67	pub fn tickets(&self) -> Option<&EpochTickets> {
68		match self {
69			Self::Tickets(t) => Some(t),
70			Self::Keys(_) => None,
71		}
72	}
73	pub fn get(&self, i: Slot) -> Option<TicketOrKey> {
74		Some(match self {
75			Self::Tickets(t) => TicketOrKey::Ticket(*t.get(i as usize)?),
76			Self::Keys(k) => TicketOrKey::Key(*k.get(i as usize)?),
77		})
78	}
79}