chia_protocol/
weight_proof.rs

1use chia_sha2::Sha256;
2use chia_streamable_macro::streamable;
3use chia_traits::{Result, Streamable};
4use std::io::Cursor;
5
6use crate::Bytes32;
7use crate::EndOfSubSlotBundle;
8use crate::HeaderBlock;
9use crate::ProofOfSpace;
10use crate::RewardChainBlock;
11use crate::utils::{parse, stream, update_digest};
12use crate::{VDFInfo, VDFProof};
13
14#[streamable(no_streamable)]
15pub struct SubEpochData {
16    reward_chain_hash: Bytes32,
17    num_blocks_overflow: u8,
18    new_sub_slot_iters: Option<u64>,
19    new_difficulty: Option<u64>,
20    challenge_merkle_root: Option<Bytes32>,
21}
22impl Streamable for SubEpochData {
23    fn update_digest(&self, digest: &mut Sha256) {
24        self.reward_chain_hash.update_digest(digest);
25        self.num_blocks_overflow.update_digest(digest);
26        self.new_sub_slot_iters.update_digest(digest);
27        update_digest(
28            self.new_difficulty.as_ref(),
29            self.challenge_merkle_root.as_ref(),
30            digest,
31        );
32    }
33
34    fn stream(&self, out: &mut Vec<u8>) -> Result<()> {
35        self.reward_chain_hash.stream(out)?;
36        self.num_blocks_overflow.stream(out)?;
37        self.new_sub_slot_iters.stream(out)?;
38        stream(
39            self.new_difficulty.as_ref(),
40            self.challenge_merkle_root.as_ref(),
41            out,
42        )
43    }
44
45    fn parse<const TRUSTED: bool>(input: &mut Cursor<&[u8]>) -> Result<Self> {
46        let rch = <Bytes32 as Streamable>::parse::<TRUSTED>(input)?;
47        let nbo = <u8 as Streamable>::parse::<TRUSTED>(input)?;
48        let nssi = <Option<u64> as Streamable>::parse::<TRUSTED>(input)?;
49        let (nd, challenge_merkle_root) = parse::<TRUSTED, u64, Bytes32>(input)?;
50        Ok(Self {
51            reward_chain_hash: rch,
52            num_blocks_overflow: nbo,
53            new_sub_slot_iters: nssi,
54            new_difficulty: nd,
55            challenge_merkle_root,
56        })
57    }
58}
59
60// number of challenge blocks
61// Average iters for challenge blocks
62// |--A-R----R-------R--------R------R----R----------R-----R--R---|       Honest difficulty 1000
63//           0.16
64
65//  compute total reward chain blocks
66// |----------------------------A---------------------------------|       Attackers chain 1000
67//                            0.48
68// total number of challenge blocks == total number of reward chain blocks
69
70#[streamable]
71pub struct SubSlotData {
72    proof_of_space: Option<ProofOfSpace>,
73    cc_signage_point: Option<VDFProof>,
74    cc_infusion_point: Option<VDFProof>,
75    icc_infusion_point: Option<VDFProof>,
76    cc_sp_vdf_info: Option<VDFInfo>,
77    signage_point_index: Option<u8>,
78    cc_slot_end: Option<VDFProof>,
79    icc_slot_end: Option<VDFProof>,
80    cc_slot_end_info: Option<VDFInfo>,
81    icc_slot_end_info: Option<VDFInfo>,
82    cc_ip_vdf_info: Option<VDFInfo>,
83    icc_ip_vdf_info: Option<VDFInfo>,
84    total_iters: Option<u128>,
85}
86
87#[cfg(feature = "py-bindings")]
88use pyo3::prelude::*;
89
90#[cfg_attr(feature = "py-bindings", pymethods)]
91impl SubSlotData {
92    pub fn is_end_of_slot(&self) -> bool {
93        self.cc_slot_end_info.is_some()
94    }
95
96    pub fn is_challenge(&self) -> bool {
97        self.proof_of_space.is_some()
98    }
99}
100
101#[streamable]
102pub struct SubEpochChallengeSegment {
103    sub_epoch_n: u32,
104    sub_slots: Vec<SubSlotData>,
105    rc_slot_end_info: Option<VDFInfo>,
106}
107
108#[streamable]
109pub struct SubEpochSegments {
110    challenge_segments: Vec<SubEpochChallengeSegment>,
111}
112
113// this is used only for serialization to database
114#[streamable]
115pub struct RecentChainData {
116    recent_chain_data: Vec<HeaderBlock>,
117}
118
119#[streamable]
120pub struct ProofBlockHeader {
121    finished_sub_slots: Vec<EndOfSubSlotBundle>,
122    reward_chain_block: RewardChainBlock,
123}
124
125#[streamable]
126pub struct WeightProof {
127    sub_epochs: Vec<SubEpochData>,
128    sub_epoch_segments: Vec<SubEpochChallengeSegment>, // sampled sub epoch
129    recent_chain_data: Vec<HeaderBlock>,
130}