@@ -16,6 +16,7 @@ use crate::block::{
1616 BlockInfo ,
1717 BlockNumber ,
1818 BlockTimestamp ,
19+ GasPrice ,
1920 GasPricePerToken ,
2021 StarknetVersion ,
2122} ;
@@ -47,6 +48,11 @@ static STARKNET_BLOCK_HASH0: LazyLock<Felt> = LazyLock::new(|| {
4748pub static STARKNET_BLOCK_HASH1 : LazyLock < Felt > = LazyLock :: new ( || {
4849 ascii_as_felt ( "STARKNET_BLOCK_HASH1" ) . expect ( "ascii_as_felt failed for 'STARKNET_BLOCK_HASH1'" )
4950} ) ;
51+ // TODO(SNIP-35): Consult protocol team on the correct block hash constant name and version
52+ // number for SNIP-35. Using "STARKNET_BLOCK_HASH2" and V0_14_4 as placeholders.
53+ pub static STARKNET_BLOCK_HASH2 : LazyLock < Felt > = LazyLock :: new ( || {
54+ ascii_as_felt ( "STARKNET_BLOCK_HASH2" ) . expect ( "ascii_as_felt failed for 'STARKNET_BLOCK_HASH2'" )
55+ } ) ;
5056pub static STARKNET_GAS_PRICES0 : LazyLock < Felt > = LazyLock :: new ( || {
5157 ascii_as_felt ( "STARKNET_GAS_PRICES0" ) . expect ( "ascii_as_felt failed for 'STARKNET_GAS_PRICES0'" )
5258} ) ;
@@ -56,13 +62,21 @@ pub static STARKNET_GAS_PRICES0: LazyLock<Felt> = LazyLock::new(|| {
5662pub enum BlockHashVersion {
5763 V0_13_2 ,
5864 V0_13_4 ,
65+ // TODO(SNIP-35): Consult protocol team on the correct version for SNIP-35 block hash.
66+ // V0_14_4 is a placeholder — the actual version depends on the release schedule.
67+ V0_14_4 ,
5968}
6069
6170impl From < BlockHashVersion > for StarknetVersion {
6271 fn from ( value : BlockHashVersion ) -> Self {
6372 match value {
6473 BlockHashVersion :: V0_13_2 => StarknetVersion :: V0_13_2 ,
6574 BlockHashVersion :: V0_13_4 => StarknetVersion :: V0_13_4 ,
75+ // TODO(SNIP-35): Map to the real StarknetVersion once the protocol team assigns one.
76+ // For now, V0_14_4 is only used internally and never converted to StarknetVersion.
77+ BlockHashVersion :: V0_14_4 => {
78+ panic ! ( "V0_14_4 BlockHashVersion cannot be converted to StarknetVersion yet" )
79+ }
6680 }
6781 }
6882}
@@ -77,6 +91,8 @@ impl TryFrom<StarknetVersion> for BlockHashVersion {
7791 // Starknet versions 0.13.2 and 0.13.3 both have the same block hash mechanism.
7892 Ok ( Self :: V0_13_2 )
7993 } else {
94+ // TODO(SNIP-35): When the protocol team assigns a StarknetVersion for SNIP-35,
95+ // add a branch here: `else if value < V_SNIP35.into() { V0_13_4 } else { V0_14_4 }`.
8096 Ok ( Self :: V0_13_4 )
8197 }
8298 }
@@ -90,6 +106,7 @@ impl From<BlockHashVersion> for BlockHashConstant {
90106 match block_hash_version {
91107 BlockHashVersion :: V0_13_2 => * STARKNET_BLOCK_HASH0 ,
92108 BlockHashVersion :: V0_13_4 => * STARKNET_BLOCK_HASH1 ,
109+ BlockHashVersion :: V0_14_4 => * STARKNET_BLOCK_HASH2 ,
93110 }
94111 }
95112}
@@ -218,6 +235,8 @@ pub struct PartialBlockHashComponents {
218235 pub sequencer : SequencerContractAddress ,
219236 pub timestamp : BlockTimestamp ,
220237 pub starknet_version : StarknetVersion ,
238+ /// SNIP-35: proposer's recommended fee for future blocks.
239+ pub fee_proposal : GasPrice ,
221240}
222241
223242impl PartialBlockHashComponents {
@@ -231,6 +250,7 @@ impl PartialBlockHashComponents {
231250 sequencer : SequencerContractAddress ( block_info. sequencer_address ) ,
232251 timestamp : block_info. block_timestamp ,
233252 starknet_version : block_info. starknet_version ,
253+ fee_proposal : GasPrice :: default ( ) ,
234254 }
235255 }
236256}
@@ -250,35 +270,39 @@ pub fn calculate_block_hash(
250270 let block_hash_version: BlockHashVersion =
251271 partial_block_hash_components. starknet_version . try_into ( ) ?;
252272 let block_commitments = & partial_block_hash_components. header_commitments ;
253- Ok ( BlockHash (
254- HashChain :: new ( )
255- . chain ( & block_hash_version. clone ( ) . into ( ) )
256- . chain ( & partial_block_hash_components. block_number . 0 . into ( ) )
257- . chain ( & state_root. 0 )
258- . chain ( & partial_block_hash_components. sequencer . 0 )
259- . chain ( & partial_block_hash_components. timestamp . 0 . into ( ) )
260- . chain ( & block_commitments. concatenated_counts )
261- . chain ( & block_commitments. state_diff_commitment . 0 . 0 )
262- . chain ( & block_commitments. transaction_commitment . 0 )
263- . chain ( & block_commitments. event_commitment . 0 )
264- . chain ( & block_commitments. receipt_commitment . 0 )
265- . chain_iter (
266- gas_prices_to_hash (
267- & partial_block_hash_components. l1_gas_price ,
268- & partial_block_hash_components. l1_data_gas_price ,
269- & partial_block_hash_components. l2_gas_price ,
270- & block_hash_version,
271- )
272- . iter ( ) ,
273- )
274- . chain (
275- & Felt :: try_from ( & partial_block_hash_components. starknet_version )
276- . expect ( "Expect ASCII version" ) ,
273+ let mut hash_chain = HashChain :: new ( )
274+ . chain ( & block_hash_version. clone ( ) . into ( ) )
275+ . chain ( & partial_block_hash_components. block_number . 0 . into ( ) )
276+ . chain ( & state_root. 0 )
277+ . chain ( & partial_block_hash_components. sequencer . 0 )
278+ . chain ( & partial_block_hash_components. timestamp . 0 . into ( ) )
279+ . chain ( & block_commitments. concatenated_counts )
280+ . chain ( & block_commitments. state_diff_commitment . 0 . 0 )
281+ . chain ( & block_commitments. transaction_commitment . 0 )
282+ . chain ( & block_commitments. event_commitment . 0 )
283+ . chain ( & block_commitments. receipt_commitment . 0 )
284+ . chain_iter (
285+ gas_prices_to_hash (
286+ & partial_block_hash_components. l1_gas_price ,
287+ & partial_block_hash_components. l1_data_gas_price ,
288+ & partial_block_hash_components. l2_gas_price ,
289+ & block_hash_version,
277290 )
278- . chain ( & Felt :: ZERO )
279- . chain ( & previous_block_hash. 0 )
280- . get_poseidon_hash ( ) ,
281- ) )
291+ . iter ( ) ,
292+ )
293+ . chain (
294+ & Felt :: try_from ( & partial_block_hash_components. starknet_version )
295+ . expect ( "Expect ASCII version" ) ,
296+ )
297+ . chain ( & Felt :: ZERO )
298+ . chain ( & previous_block_hash. 0 ) ;
299+
300+ // SNIP-35: include fee_proposal in block hash for V0_14_4+.
301+ if block_hash_version >= BlockHashVersion :: V0_14_4 {
302+ hash_chain = hash_chain. chain ( & partial_block_hash_components. fee_proposal . 0 . into ( ) ) ;
303+ }
304+
305+ Ok ( BlockHash ( hash_chain. get_poseidon_hash ( ) ) )
282306}
283307
284308/// Calculates the commitments of the transactions data for the block hash.
0 commit comments