reth_seismic_chainspec/
lib.rs1#![doc(
4 html_logo_url = "https://raw.githubusercontent.com/paradigmxyz/reth/main/assets/reth-docs.png",
5 html_favicon_url = "https://avatars0.githubusercontent.com/u/97369466?s=256",
6 issue_tracker_base_url = "https://github.com/SeismicSystems/seismic-reth/issues/"
7)]
8#![cfg_attr(docsrs, feature(doc_cfg, doc_auto_cfg))]
9#![cfg_attr(not(feature = "std"), no_std)]
10
11use std::sync::Arc;
12
13use alloy_chains::Chain;
14use alloy_consensus::constants::DEV_GENESIS_HASH;
15use alloy_primitives::{b256, B256, U256};
16use reth_chainspec::{make_genesis_header, ChainSpec, DEV_HARDFORKS};
17use reth_primitives_traits::{sync::LazyLock, SealedHeader};
18use reth_seismic_forks::{SEISMIC_DEV_HARDFORKS, SEISMIC_MAINNET_HARDFORKS};
19
20pub const SEISMIC_MAINNET_GENESIS_HASH: B256 =
23 b256!("0xd548d4a126d72e43d893b3826c07ad24bddbaeee267489baff2f73fff2ac0976");
24
25pub const SEISMIC_DEV_GENESIS_HASH: B256 =
29 b256!("0x655cc1ecc77fe1eab4b1e62a1f461b7fddc9b06109b5ab3e9dc68c144b30c773");
30
31pub static SEISMIC_DEV: LazyLock<Arc<ChainSpec>> = LazyLock::new(|| {
33 let genesis = serde_json::from_str(include_str!("../res/genesis/dev.json"))
34 .expect("Can't deserialize Dev testnet genesis json");
35 let hardforks = SEISMIC_DEV_HARDFORKS.clone();
36 ChainSpec {
37 chain: Chain::from_id(5124),
38 genesis_header: SealedHeader::new(
39 make_genesis_header(&genesis, &hardforks),
40 SEISMIC_DEV_GENESIS_HASH,
41 ),
42 genesis,
43 paris_block_and_final_difficulty: Some((0, U256::from(0))),
44 hardforks: DEV_HARDFORKS.clone(),
45 ..Default::default()
46 }
47 .into()
48});
49
50pub static SEISMIC_DEV_OLD: LazyLock<Arc<ChainSpec>> = LazyLock::new(|| {
53 let genesis = serde_json::from_str(include_str!("../res/genesis/dev.json"))
54 .expect("Can't deserialize Dev testnet genesis json");
55 let hardforks = SEISMIC_DEV_HARDFORKS.clone();
56 ChainSpec {
57 chain: Chain::from_id(5124),
58 genesis_header: SealedHeader::new(
59 make_genesis_header(&genesis, &hardforks),
60 DEV_GENESIS_HASH,
61 ),
62 genesis,
63 paris_block_and_final_difficulty: Some((0, U256::from(0))),
64 hardforks: DEV_HARDFORKS.clone(),
65 ..Default::default()
66 }
67 .into()
68});
69
70pub static SEISMIC_MAINNET: LazyLock<Arc<ChainSpec>> = LazyLock::new(|| {
72 let genesis = serde_json::from_str(include_str!("../res/genesis/mainnet.json"))
73 .expect("Can't deserialize Mainnet genesis json");
74 let hardforks = SEISMIC_MAINNET_HARDFORKS.clone();
75 let mut spec = ChainSpec {
76 chain: Chain::from_id(5123),
77 genesis_header: SealedHeader::new(
78 make_genesis_header(&genesis, &hardforks),
79 SEISMIC_MAINNET_GENESIS_HASH,
80 ),
81 genesis,
82 paris_block_and_final_difficulty: Some((0, U256::from(0))),
83 hardforks,
84 ..Default::default()
85 };
86 spec.genesis.config.dao_fork_support = true;
87 spec.into()
88});
89
90pub fn is_chain_seismic(chain: &Chain) -> bool {
92 chain.id() == SEISMIC_MAINNET.chain.id() || chain.id() == SEISMIC_DEV.chain.id()
93}
94
95#[cfg(test)]
96mod tests {
97 use crate::*;
98 use alloy_consensus::constants::MAINNET_GENESIS_HASH;
99 use reth_chainspec::MAINNET;
100 use reth_ethereum_forks::EthereumHardfork;
101 use reth_seismic_forks::SeismicHardfork;
102
103 #[test]
104 fn seismic_mainnet_genesis() {
105 let genesis = SEISMIC_MAINNET.genesis_header();
106 let eth_genesis = MAINNET.genesis_header();
107 assert_ne!(
108 genesis.hash_slow(),
109 eth_genesis.hash_slow(),
110 "Seismic spec should not match eth genesis"
111 );
112 assert_eq!(
113 genesis.hash_slow(),
114 SEISMIC_MAINNET_GENESIS_HASH,
115 "Seismic spec has correct genesis hash"
116 );
117 }
118
119 #[test]
121 fn latest_seismic_mainnet_fork_id_with_builder() {
122 let seismic_mainnet = &SEISMIC_MAINNET;
123 assert_eq!(
124 seismic_mainnet.hardfork_fork_id(SeismicHardfork::Mercury).unwrap(),
125 seismic_mainnet.latest_fork_id()
126 )
127 }
128
129 #[test]
131 fn display_hardforks() {
132 let content = SEISMIC_MAINNET.display_hardforks().to_string();
133 let eth_mainnet = EthereumHardfork::mainnet();
134 for (eth_hf, _) in eth_mainnet {
135 assert!(content.contains(eth_hf.name()), "missing hardfork {eth_hf}");
136 }
137 assert!(content.contains("Mercury"));
138 }
139
140 #[test]
141 fn genesis_header_hash() {
142 let expected = MAINNET_GENESIS_HASH;
144 let genesis =
145 serde_json::from_str(include_str!("../../../chainspec/res/genesis/mainnet.json"))
146 .expect("Can't deserialize Mainnet genesis json");
147 let hardforks = EthereumHardfork::mainnet().into();
148 let genesis_header = make_genesis_header(&genesis, &hardforks);
149 let actual_hash = genesis_header.hash_slow();
150 assert_eq!(actual_hash, expected);
151
152 let expected = SEISMIC_MAINNET_GENESIS_HASH;
154 let genesis = serde_json::from_str(include_str!("../res/genesis/mainnet.json")) .expect("Can't deserialize Seismic Mainnet genesis json");
156 let hardforks = SEISMIC_MAINNET_HARDFORKS.clone();
157 let genesis_header = make_genesis_header(&genesis, &hardforks);
158 let actual_hash = genesis_header.hash_slow();
159 assert_eq!(actual_hash, expected);
160
161 let expected = SEISMIC_DEV_GENESIS_HASH;
163 let genesis = serde_json::from_str(include_str!("../res/genesis/dev.json"))
164 .expect("Can't deserialize Seismic devnet genesis json");
165 let hardforks = SEISMIC_DEV_HARDFORKS.clone();
166 let genesis_header = make_genesis_header(&genesis, &hardforks);
167 let actual_hash = genesis_header.hash_slow();
168 assert_eq!(actual_hash, expected);
169 }
170}