kona_genesis/chain/
hardfork.rs

1//! Contains the hardfork configuration for the chain.
2
3/// Hardfork configuration.
4///
5/// See: <https://github.com/ethereum-optimism/superchain-registry/blob/8ff62ada16e14dd59d0fb94ffb47761c7fa96e01/ops/internal/config/chain.go#L102-L110>
6#[derive(Debug, Copy, Clone, Default, Hash, Eq, PartialEq)]
7#[cfg_attr(feature = "arbitrary", derive(arbitrary::Arbitrary))]
8#[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))]
9#[cfg_attr(feature = "serde", serde(deny_unknown_fields))]
10pub struct HardForkConfig {
11    /// `regolith_time` sets the activation time of the Regolith network-upgrade:
12    /// a pre-mainnet Bedrock change that addresses findings of the Sherlock contest related to
13    /// deposit attributes. "Regolith" is the loose deposited rock that sits on top of Bedrock.
14    /// Active if regolith_time != None && L2 block timestamp >= Some(regolith_time), inactive
15    /// otherwise.
16    #[cfg_attr(feature = "serde", serde(skip_serializing_if = "Option::is_none"))]
17    pub regolith_time: Option<u64>,
18    /// `canyon_time` sets the activation time of the Canyon network upgrade.
19    /// Active if `canyon_time` != None && L2 block timestamp >= Some(canyon_time), inactive
20    /// otherwise.
21    #[cfg_attr(feature = "serde", serde(skip_serializing_if = "Option::is_none"))]
22    pub canyon_time: Option<u64>,
23    /// `delta_time` sets the activation time of the Delta network upgrade.
24    /// Active if `delta_time` != None && L2 block timestamp >= Some(delta_time), inactive
25    /// otherwise.
26    #[cfg_attr(feature = "serde", serde(skip_serializing_if = "Option::is_none"))]
27    pub delta_time: Option<u64>,
28    /// `ecotone_time` sets the activation time of the Ecotone network upgrade.
29    /// Active if `ecotone_time` != None && L2 block timestamp >= Some(ecotone_time), inactive
30    /// otherwise.
31    #[cfg_attr(feature = "serde", serde(skip_serializing_if = "Option::is_none"))]
32    pub ecotone_time: Option<u64>,
33    /// `fjord_time` sets the activation time of the Fjord network upgrade.
34    /// Active if `fjord_time` != None && L2 block timestamp >= Some(fjord_time), inactive
35    /// otherwise.
36    #[cfg_attr(feature = "serde", serde(skip_serializing_if = "Option::is_none"))]
37    pub fjord_time: Option<u64>,
38    /// `granite_time` sets the activation time for the Granite network upgrade.
39    /// Active if `granite_time` != None && L2 block timestamp >= Some(granite_time), inactive
40    /// otherwise.
41    #[cfg_attr(feature = "serde", serde(skip_serializing_if = "Option::is_none"))]
42    pub granite_time: Option<u64>,
43    /// `holocene_time` sets the activation time for the Holocene network upgrade.
44    /// Active if `holocene_time` != None && L2 block timestamp >= Some(holocene_time), inactive
45    /// otherwise.
46    #[cfg_attr(feature = "serde", serde(skip_serializing_if = "Option::is_none"))]
47    pub holocene_time: Option<u64>,
48    /// `pectra_blob_schedule_time` sets the activation time for the activation of the Pectra blob
49    /// fee schedule for the L1 block info transaction. This is an optional fork, only present
50    /// on OP Stack sepolia chains that observed the L1 Pectra network upgrade with `op-node`
51    /// <=v1.11.1 sequencing the network.
52    ///
53    /// Active if `pectra_blob_schedule_time` != None && L2 block timestamp >=
54    /// Some(pectra_blob_schedule_time), inactive otherwise.
55    #[cfg_attr(feature = "serde", serde(skip_serializing_if = "Option::is_none"))]
56    pub pectra_blob_schedule_time: Option<u64>,
57    /// `isthmus_time` sets the activation time for the Isthmus network upgrade.
58    /// Active if `isthmus_time` != None && L2 block timestamp >= Some(isthmus_time), inactive
59    /// otherwise.
60    #[cfg_attr(feature = "serde", serde(skip_serializing_if = "Option::is_none"))]
61    pub isthmus_time: Option<u64>,
62    /// `interop_time` sets the activation time for the Interop network upgrade.
63    /// Active if `interop_time` != None && L2 block timestamp >= Some(interop_time), inactive
64    /// otherwise.
65    #[cfg_attr(feature = "serde", serde(skip_serializing_if = "Option::is_none"))]
66    pub interop_time: Option<u64>,
67}
68
69#[cfg(test)]
70#[cfg(feature = "serde")]
71mod tests {
72    use super::*;
73
74    #[test]
75    fn test_hardforks_deserialize_json() {
76        let raw: &str = r#"
77        {
78            "canyon_time": 1699981200,
79            "delta_time": 1703203200,
80            "ecotone_time": 1708534800,
81            "fjord_time": 1716998400,
82            "granite_time": 1723478400,
83            "holocene_time":1732633200
84        }
85        "#;
86
87        let hardforks = HardForkConfig {
88            regolith_time: None,
89            canyon_time: Some(1699981200),
90            delta_time: Some(1703203200),
91            ecotone_time: Some(1708534800),
92            fjord_time: Some(1716998400),
93            granite_time: Some(1723478400),
94            holocene_time: Some(1732633200),
95            pectra_blob_schedule_time: None,
96            isthmus_time: None,
97            interop_time: None,
98        };
99
100        let deserialized: HardForkConfig = serde_json::from_str(raw).unwrap();
101        assert_eq!(hardforks, deserialized);
102    }
103
104    #[test]
105    fn test_hardforks_deserialize_new_field_fail_json() {
106        let raw: &str = r#"
107        {
108            "canyon_time": 1704992401,
109            "delta_time": 1708560000,
110            "ecotone_time": 1710374401,
111            "fjord_time": 1720627201,
112            "granite_time": 1726070401,
113            "holocene_time": 1736445601,
114            "new_field": 0
115        }
116        "#;
117
118        let err = serde_json::from_str::<HardForkConfig>(raw).unwrap_err();
119        assert_eq!(err.classify(), serde_json::error::Category::Data);
120    }
121
122    #[test]
123    fn test_hardforks_deserialize_toml() {
124        let raw: &str = r#"
125        canyon_time =  1699981200 # Tue 14 Nov 2023 17:00:00 UTC
126        delta_time =   1703203200 # Fri 22 Dec 2023 00:00:00 UTC
127        ecotone_time = 1708534800 # Wed 21 Feb 2024 17:00:00 UTC
128        fjord_time =   1716998400 # Wed 29 May 2024 16:00:00 UTC
129        granite_time = 1723478400 # Mon Aug 12 16:00:00 UTC 2024
130        holocene_time = 1732633200 # Tue Nov 26 15:00:00 UTC 2024
131        "#;
132
133        let hardforks = HardForkConfig {
134            regolith_time: None,
135            canyon_time: Some(1699981200),
136            delta_time: Some(1703203200),
137            ecotone_time: Some(1708534800),
138            fjord_time: Some(1716998400),
139            granite_time: Some(1723478400),
140            holocene_time: Some(1732633200),
141            pectra_blob_schedule_time: None,
142            isthmus_time: None,
143            interop_time: None,
144        };
145
146        let deserialized: HardForkConfig = toml::from_str(raw).unwrap();
147        assert_eq!(hardforks, deserialized);
148    }
149
150    #[test]
151    fn test_hardforks_deserialize_new_field_fail_toml() {
152        let raw: &str = r#"
153        canyon_time =  1699981200 # Tue 14 Nov 2023 17:00:00 UTC
154        delta_time =   1703203200 # Fri 22 Dec 2023 00:00:00 UTC
155        ecotone_time = 1708534800 # Wed 21 Feb 2024 17:00:00 UTC
156        fjord_time =   1716998400 # Wed 29 May 2024 16:00:00 UTC
157        granite_time = 1723478400 # Mon Aug 12 16:00:00 UTC 2024
158        holocene_time = 1732633200 # Tue Nov 26 15:00:00 UTC 2024
159        new_field_time = 1732633200 # Tue Nov 26 15:00:00 UTC 2024
160        "#;
161        toml::from_str::<HardForkConfig>(raw).unwrap_err();
162    }
163}