diff --git a/bin/citrea/src/test_rpc.rs b/bin/citrea/src/test_rpc.rs index 06c04c7f8..ebe8926f0 100644 --- a/bin/citrea/src/test_rpc.rs +++ b/bin/citrea/src/test_rpc.rs @@ -153,6 +153,10 @@ fn regular_test_helper(payload: serde_json::Value, expected: &serde_json::Value) ], phantom_data: PhantomData, pub_key: vec![], + deposit_data: vec![ + "aaaaab".as_bytes().to_vec(), + "eeeeeeeeee".as_bytes().to_vec(), + ], l1_fee_rate: 0, timestamp: 0, }, @@ -167,6 +171,7 @@ fn regular_test_helper(payload: serde_json::Value, expected: &serde_json::Value) tx_receipts: batch2_tx_receipts(), phantom_data: PhantomData, pub_key: vec![], + deposit_data: vec!["c44444".as_bytes().to_vec()], l1_fee_rate: 0, timestamp: 0, }, @@ -318,7 +323,7 @@ fn test_get_batches() { fn test_get_soft_batch() { // Get the first soft batch by number let payload = jsonrpc_req!("ledger_getSoftBatchByNumber", [1]); - let expected = jsonrpc_result!({"da_slot_height":0,"da_slot_hash":"0000000000000000000000000000000000000000000000000000000000000000","da_slot_txs_commitment":"0101010101010101010101010101010101010101010101010101010101010101","hash":"b5515a80204963f7db40e98af11aedb49a394b1c7e3d8b5b7a33346b8627444f","txs":["74783120626f6479", "74783220626f6479"],"pre_state_root":"","post_state_root":"","soft_confirmation_signature":"","pub_key":"","l1_fee_rate":0, "timestamp": 0}); + let expected = jsonrpc_result!({"da_slot_height":0,"da_slot_hash":"0000000000000000000000000000000000000000000000000000000000000000","da_slot_txs_commitment":"0101010101010101010101010101010101010101010101010101010101010101","deposit_data": ["616161616162", "65656565656565656565"],"hash":"b5515a80204963f7db40e98af11aedb49a394b1c7e3d8b5b7a33346b8627444f","txs":["74783120626f6479", "74783220626f6479"],"pre_state_root":"","post_state_root":"","soft_confirmation_signature":"","pub_key":"", "l1_fee_rate":0, "timestamp": 0}); regular_test_helper(payload, &expected); // Get the first soft batch by hash @@ -335,7 +340,7 @@ fn test_get_soft_batch() { .map(|tx_receipt| tx_receipt.body_to_save.unwrap().encode_hex::()) .collect::>(); let expected = jsonrpc_result!( - {"da_slot_height":1,"da_slot_hash":"0202020202020202020202020202020202020202020202020202020202020202","da_slot_txs_commitment":"0303030303030303030303030303030303030303030303030303030303030303","hash":"f85fe0cb36fdaeca571c896ed476b49bb3c8eff00d935293a8967e1e9a62071e","txs": txs, "pre_state_root":"","post_state_root":"","soft_confirmation_signature":"","pub_key":"","l1_fee_rate":0, "timestamp": 0} + {"da_slot_height":1,"da_slot_hash":"0202020202020202020202020202020202020202020202020202020202020202","da_slot_txs_commitment":"0303030303030303030303030303030303030303030303030303030303030303","deposit_data": ["633434343434"],"hash":"f85fe0cb36fdaeca571c896ed476b49bb3c8eff00d935293a8967e1e9a62071e","txs": txs, "pre_state_root":"","post_state_root":"","soft_confirmation_signature":"","pub_key":"","l1_fee_rate":0, "timestamp": 0} ); regular_test_helper(payload, &expected); @@ -355,8 +360,8 @@ fn test_get_soft_batch() { .collect::>(); let expected = jsonrpc_result!( [ - {"da_slot_height":0,"da_slot_hash":"0000000000000000000000000000000000000000000000000000000000000000","da_slot_txs_commitment":"0101010101010101010101010101010101010101010101010101010101010101","hash":"b5515a80204963f7db40e98af11aedb49a394b1c7e3d8b5b7a33346b8627444f","txs":["74783120626f6479", "74783220626f6479"],"pre_state_root":"","post_state_root":"","soft_confirmation_signature":"","pub_key":"","l1_fee_rate":0, "timestamp": 0}, - {"da_slot_height":1,"da_slot_hash":"0202020202020202020202020202020202020202020202020202020202020202","da_slot_txs_commitment":"0303030303030303030303030303030303030303030303030303030303030303","hash":"f85fe0cb36fdaeca571c896ed476b49bb3c8eff00d935293a8967e1e9a62071e","txs": txs, "pre_state_root":"","post_state_root":"","soft_confirmation_signature":"","pub_key":"","l1_fee_rate":0, "timestamp": 0} + {"da_slot_height":0,"da_slot_hash":"0000000000000000000000000000000000000000000000000000000000000000","da_slot_txs_commitment":"0101010101010101010101010101010101010101010101010101010101010101","deposit_data": ["616161616162", "65656565656565656565"],"hash":"b5515a80204963f7db40e98af11aedb49a394b1c7e3d8b5b7a33346b8627444f","txs":["74783120626f6479", "74783220626f6479"],"pre_state_root":"","post_state_root":"","soft_confirmation_signature":"","pub_key":"","l1_fee_rate":0, "timestamp": 0}, + {"da_slot_height":1,"da_slot_hash":"0202020202020202020202020202020202020202020202020202020202020202","da_slot_txs_commitment":"0303030303030303030303030303030303030303030303030303030303030303","deposit_data": ["633434343434"],"hash":"f85fe0cb36fdaeca571c896ed476b49bb3c8eff00d935293a8967e1e9a62071e","txs": txs, "pre_state_root":"","post_state_root":"","soft_confirmation_signature":"","pub_key":"","l1_fee_rate":0, "timestamp": 0} ] ); regular_test_helper(payload, &expected); diff --git a/bin/citrea/tests/e2e/mod.rs b/bin/citrea/tests/e2e/mod.rs index 0d0db968e..48c457a99 100644 --- a/bin/citrea/tests/e2e/mod.rs +++ b/bin/citrea/tests/e2e/mod.rs @@ -1421,7 +1421,7 @@ async fn test_system_transactons() -> Result<(), anyhow::Error> { .await; if block_num == 1 { - assert_eq!(block.transactions.len(), 2); + assert_eq!(block.transactions.len(), 3); let init_tx = &block.transactions[0]; let set_tx = &block.transactions[1]; @@ -1551,28 +1551,28 @@ async fn test_system_tx_effect_on_block_gas_limit() -> Result<(), anyhow::Error> let seq_port = seq_port_rx.await.unwrap(); let seq_test_client = make_test_client(seq_port).await; - // sys tx use 43615 + 43615 = 117196gas - // the block gas limit is 1_000_000 because the system txs gas limit is 1_000_000 + // sys tx use L1BlockHash(43615 + 73581) + Bridge(1030769) = 142504 gas + // the block gas limit is 1_500_000 because the system txs gas limit is 1_500_000 (decided with @eyusufatik and @okkothejawa as bridge init takes 1M gas) - // 1000000 - 117196 = 882804 gas left in block - // 882804 / 21000 = 42.038 so 42 ether transfer transactions can be included in the block + // 1000000 - 1147965 = 352.035 gas left in block + // 352.035 / 21000 = 16,7... so 16 ether transfer transactions can be included in the block - // send 41 ether transfer transactions + // send 16 ether transfer transactions let addr = Address::from_str("0xf39Fd6e51aad88F6F4ce6aB8827279cffFb92266").unwrap(); - for _ in 0..41 { + for _ in 0..15 { seq_test_client .send_eth(addr, None, None, None, 0u128) .await .unwrap(); } - // 42nd tx should be the last tx in the soft batch + // 16th tx should be the last tx in the soft batch let last_in_tx = seq_test_client .send_eth(addr, None, None, None, 0u128) .await; - // this tx should not be in soft batch + // 17th tx should not be in soft batch let not_in_tx = seq_test_client .send_eth(addr, None, None, None, 0u128) .await; @@ -1653,6 +1653,7 @@ async fn test_system_tx_effect_on_block_gas_limit() -> Result<(), anyhow::Error> assert!(block2.transactions.iter().any(|tx| tx == ¬_in_hash)); seq_task.abort(); + Ok(()) } diff --git a/bin/citrea/tests/evm/mod.rs b/bin/citrea/tests/evm/mod.rs index a55abd3cd..17a14913b 100644 --- a/bin/citrea/tests/evm/mod.rs +++ b/bin/citrea/tests/evm/mod.rs @@ -370,7 +370,7 @@ async fn execute(client: &Box) -> Result<(), Box ApplySoftConfirmationHooks for Runtime { self.soft_confirmation_rule_enforcer .begin_soft_confirmation_hook(soft_batch, working_set)?; - self.evm.begin_soft_confirmation_hook( - soft_batch.da_slot_hash(), - soft_batch.da_slot_height, - soft_batch.da_slot_txs_commitment(), - &soft_batch.pre_state_root(), - soft_batch.l1_fee_rate(), - soft_batch.timestamp(), - working_set, - ); + self.evm + .begin_soft_confirmation_hook(soft_batch, working_set); Ok(()) } diff --git a/crates/evm/src/call.rs b/crates/evm/src/call.rs index 2b8c5f63d..88d374408 100644 --- a/crates/evm/src/call.rs +++ b/crates/evm/src/call.rs @@ -11,7 +11,7 @@ use crate::evm::executor::{self}; use crate::evm::handler::{CitreaExternal, CitreaExternalExt}; use crate::evm::primitive_types::{BlockEnv, Receipt, TransactionSignedAndRecovered}; use crate::evm::{EvmChainConfig, RlpEvmTransaction}; -use crate::system_contracts::BitcoinLightClient; +use crate::system_contracts::{BitcoinLightClient, Bridge}; use crate::system_events::{create_system_transactions, SYSTEM_SIGNER}; use crate::{Evm, PendingTransaction, SystemEvent}; @@ -57,6 +57,12 @@ impl Evm { return; } + let bridge_contract_exists = self.accounts.get(&Bridge::address(), working_set).is_some(); + if !bridge_contract_exists { + tracing::error!("System contract not found: Bridge"); + return; + } + let system_nonce = self .accounts .get(&SYSTEM_SIGNER, working_set) diff --git a/crates/evm/src/evm/system_contracts/mod.rs b/crates/evm/src/evm/system_contracts/mod.rs index 6cf235409..35bfd7582 100644 --- a/crates/evm/src/evm/system_contracts/mod.rs +++ b/crates/evm/src/evm/system_contracts/mod.rs @@ -47,3 +47,28 @@ impl BitcoinLightClient { Bytes::from(func_selector) } } + +/// Bridge wrapper. +pub struct Bridge {} + +impl Bridge { + pub(crate) fn address() -> Address { + address!("3100000000000000000000000000000000000002") + } + + pub(crate) fn initialize(data: Vec) -> Bytes { + let mut func_selector: Vec = vec![0xc1, 0x24, 0x28, 0x9c]; // initialize(uint32,bytes,bytes,uint256,address) c124289c + + func_selector.extend_from_slice(data.as_slice()); + + Bytes::from(func_selector) + } + + pub(crate) fn deposit(data: Vec) -> Bytes { + let mut func_selector: Vec = vec![0xdd, 0x95, 0xc7, 0xc6]; // deposit((bytes4,bytes2,bytes,bytes,bytes,bytes4,bytes,uint256,uint256)) dd95c7c6 + + func_selector.extend_from_slice(data.as_slice()); + + Bytes::from(func_selector) + } +} diff --git a/crates/evm/src/evm/system_events.rs b/crates/evm/src/evm/system_events.rs index 1c118c3f8..f464b2971 100644 --- a/crates/evm/src/evm/system_events.rs +++ b/crates/evm/src/evm/system_events.rs @@ -3,7 +3,7 @@ use reth_primitives::{ TransactionSignedEcRecovered, TransactionSignedNoHash, TxEip1559, U256, }; -use super::system_contracts::BitcoinLightClient; +use super::system_contracts::{BitcoinLightClient, Bridge}; /// This is a special signature to force tx.signer to be set to SYSTEM_SIGNER pub const SYSTEM_SIGNATURE: Signature = Signature { @@ -21,6 +21,8 @@ pub const SYSTEM_SIGNER: Address = address!("deaddeaddeaddeaddeaddeaddeaddeaddea pub(crate) enum SystemEvent { BitcoinLightClientInitialize(/*block number*/ u64), BitcoinLightClientSetBlockInfo(/*hash*/ [u8; 32], /*merkle root*/ [u8; 32]), + BridgeInitialize(Vec), // levels, deposit script, script suffix, required sigs count + BridgeDeposit(Vec), // version, flag, vin, vout, witness, locktime, intermediate nodes, block height, index } fn system_event_to_transaction(event: SystemEvent, nonce: u64, chain_id: u64) -> Transaction { @@ -45,6 +47,26 @@ fn system_event_to_transaction(event: SystemEvent, nonce: u64, chain_id: u64) -> max_fee_per_gas: u64::MAX as u128, ..Default::default() }, + SystemEvent::BridgeInitialize(data) => TxEip1559 { + to: TransactionKind::Call(Bridge::address()), + input: Bridge::initialize(data), + nonce, + chain_id, + value: U256::ZERO, + gas_limit: 1_500_000u64, + max_fee_per_gas: u64::MAX as u128, + ..Default::default() + }, + SystemEvent::BridgeDeposit(data) => TxEip1559 { + to: TransactionKind::Call(Bridge::address()), + input: Bridge::deposit(data), + nonce, + chain_id, + value: U256::ZERO, + gas_limit: 1_000_000u64, + max_fee_per_gas: u64::MAX as u128, + ..Default::default() + }, }; Transaction::Eip1559(body) } diff --git a/crates/evm/src/hooks.rs b/crates/evm/src/hooks.rs index 024263f34..b4b985d21 100644 --- a/crates/evm/src/hooks.rs +++ b/crates/evm/src/hooks.rs @@ -1,5 +1,6 @@ use alloy_primitives::B256; use reth_primitives::{Bloom, Bytes, U256}; +use sov_modules_api::hooks::HookSoftConfirmationInfo; use sov_modules_api::prelude::*; use sov_modules_api::{AccessoryWorkingSet, Spec, WorkingSet}; use sov_state::Storage; @@ -16,12 +17,7 @@ where #[allow(clippy::too_many_arguments)] pub fn begin_soft_confirmation_hook( &self, - da_slot_hash: [u8; 32], - da_slot_height: u64, - da_slot_txs_commitment: [u8; 32], - pre_state_root: &[u8], - l1_fee_rate: u64, - timestamp: u64, + soft_confirmation_info: &HookSoftConfirmationInfo, working_set: &mut WorkingSet, ) { let mut parent_block = self @@ -29,7 +25,7 @@ where .get(working_set) .expect("Head block should always be set"); - parent_block.header.state_root = B256::from_slice(pre_state_root); + parent_block.header.state_root = B256::from_slice(&soft_confirmation_info.pre_state_root); self.head.set(&parent_block, working_set); let sealed_parent_block = parent_block.clone().seal(); @@ -45,22 +41,58 @@ where // populate system events let mut system_events = vec![]; if let Some(last_l1_hash) = self.last_l1_hash.get(working_set) { - if last_l1_hash != da_slot_hash { + if last_l1_hash != soft_confirmation_info.da_slot_hash { // That's a new L1 block system_events.push(SystemEvent::BitcoinLightClientSetBlockInfo( - da_slot_hash, - da_slot_txs_commitment, + soft_confirmation_info.da_slot_hash, + soft_confirmation_info.da_slot_txs_commitment, )); } } else { // That's the first L2 block in the first seen L1 block. - system_events.push(SystemEvent::BitcoinLightClientInitialize(da_slot_height)); + system_events.push(SystemEvent::BitcoinLightClientInitialize( + soft_confirmation_info.da_slot_height, + )); system_events.push(SystemEvent::BitcoinLightClientSetBlockInfo( - da_slot_hash, - da_slot_txs_commitment, + soft_confirmation_info.da_slot_hash, + soft_confirmation_info.da_slot_txs_commitment, + )); + system_events.push(SystemEvent::BridgeInitialize( + // couldn't figure out how encoding worked lol + vec![ + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 31, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 160, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 128, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 102, 246, 134, 146, 192, 62, 185, 192, 101, 109, + 103, 111, 47, 75, 209, 62, 186, 64, 209, 183, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 175, 195, 32, 52, + 2, 237, 230, 131, 149, 51, 30, 39, 151, 225, 216, 253, 43, 169, 81, 56, 107, + 170, 179, 45, 20, 64, 37, 44, 50, 20, 224, 112, 143, 228, 121, 173, 32, 193, + 140, 89, 52, 128, 244, 245, 90, 63, 215, 97, 124, 157, 246, 227, 218, 188, 128, + 252, 165, 146, 127, 102, 210, 0, 80, 200, 42, 32, 18, 190, 122, 173, 32, 137, + 195, 16, 192, 123, 60, 57, 1, 86, 42, 63, 0, 12, 74, 71, 127, 203, 94, 191, + 211, 98, 222, 61, 7, 160, 191, 249, 39, 242, 145, 19, 1, 173, 32, 103, 222, + 104, 248, 235, 129, 108, 134, 57, 104, 2, 179, 137, 222, 222, 192, 23, 3, 215, + 158, 153, 16, 224, 200, 70, 244, 137, 32, 163, 227, 61, 215, 173, 32, 64, 241, + 80, 103, 2, 228, 0, 184, 209, 174, 210, 222, 5, 191, 119, 110, 109, 118, 2, 55, + 138, 176, 131, 74, 125, 119, 16, 57, 69, 74, 245, 110, 173, 81, 0, 99, 20, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 104, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, + ], )); } + soft_confirmation_info + .deposit_data + .iter() + .for_each(|deposit_data| { + system_events.push(SystemEvent::BridgeDeposit(deposit_data.clone())); + }); + let cfg = self .cfg .get(working_set) @@ -68,8 +100,8 @@ where let new_pending_env = BlockEnv { number: parent_block.header.number + 1, coinbase: cfg.coinbase, - timestamp, - prevrandao: da_slot_hash.into(), + timestamp: soft_confirmation_info.timestamp, + prevrandao: soft_confirmation_info.da_slot_hash.into(), basefee: parent_block .header .next_block_base_fee(cfg.base_fee_params) @@ -78,7 +110,8 @@ where }; self.block_env.set(&new_pending_env, working_set); - self.l1_fee_rate.set(&l1_fee_rate, working_set); + self.l1_fee_rate + .set(&soft_confirmation_info.l1_fee_rate, working_set); if !system_events.is_empty() { self.execute_system_events(system_events, working_set); @@ -94,7 +127,8 @@ where self.latest_block_hashes .remove(&U256::from(new_pending_env.number - 257), working_set); } - self.last_l1_hash.set(&da_slot_hash.into(), working_set); + self.last_l1_hash + .set(&soft_confirmation_info.da_slot_hash.into(), working_set); } /// Logic executed at the end of the slot. Here, we generate an authenticated block and set it as the new head of the chain. diff --git a/crates/evm/src/tests/call_tests.rs b/crates/evm/src/tests/call_tests.rs index 337d72ed1..596630ab0 100644 --- a/crates/evm/src/tests/call_tests.rs +++ b/crates/evm/src/tests/call_tests.rs @@ -5,6 +5,7 @@ use reth_primitives::{Address, BlockNumberOrTag, Bytes, TransactionKind, U64}; use reth_rpc_types::request::{TransactionInput, TransactionRequest}; use revm::primitives::{SpecId, KECCAK_EMPTY, U256}; use sov_modules_api::default_context::DefaultContext; +use sov_modules_api::hooks::HookSoftConfirmationInfo; use sov_modules_api::utils::generate_address; use sov_modules_api::{Context, Module, StateMapAccessor, StateVecAccessor}; @@ -50,12 +51,16 @@ fn call_multiple_test() { let l1_fee_rate = 0; evm.begin_soft_confirmation_hook( - [5u8; 32], - 1, - [42u8; 32], - &[10u8; 32], - l1_fee_rate, - 0, + &HookSoftConfirmationInfo { + da_slot_hash: [5u8; 32], + da_slot_height: 1, + da_slot_txs_commitment: [42u8; 32], + pre_state_root: [10u8; 32].to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate, + timestamp: 0, + }, &mut working_set, ); @@ -154,12 +159,16 @@ fn call_test() { let l1_fee_rate = 0; evm.begin_soft_confirmation_hook( - [5u8; 32], - 1, - [42u8; 32], - &[10u8; 32], - l1_fee_rate, - 0, + &HookSoftConfirmationInfo { + da_slot_hash: [5u8; 32], + da_slot_height: 1, + da_slot_txs_commitment: [42u8; 32], + pre_state_root: [10u8; 32].to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate, + timestamp: 0, + }, &mut working_set, ); @@ -229,12 +238,16 @@ fn failed_transaction_test() { let l1_fee_rate = 0; evm.begin_soft_confirmation_hook( - [5u8; 32], - 1, - [42u8; 32], - &[10u8; 32], - l1_fee_rate, - 0, + &HookSoftConfirmationInfo { + da_slot_hash: [5u8; 32], + da_slot_height: 1, + da_slot_txs_commitment: [42u8; 32], + pre_state_root: [10u8; 32].to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate, + timestamp: 0, + }, working_set, ); { @@ -286,12 +299,16 @@ fn self_destruct_test() { let l1_fee_rate = 0; evm.begin_soft_confirmation_hook( - [5u8; 32], - 1, - [42u8; 32], - &[10u8; 32], - l1_fee_rate, - 0, + &HookSoftConfirmationInfo { + da_slot_hash: [5u8; 32], + da_slot_height: 1, + da_slot_txs_commitment: [42u8; 32], + pre_state_root: [10u8; 32].to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate, + timestamp: 0, + }, &mut working_set, ); { @@ -342,12 +359,16 @@ fn self_destruct_test() { let l1_fee_rate = 0; evm.begin_soft_confirmation_hook( - [5u8; 32], - 2, - [42u8; 32], - &[99u8; 32], - l1_fee_rate, - 0, + &HookSoftConfirmationInfo { + da_slot_hash: [5u8; 32], + da_slot_height: 2, + da_slot_txs_commitment: [42u8; 32], + pre_state_root: [99u8; 32].to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate, + timestamp: 0, + }, &mut working_set, ); { @@ -419,12 +440,16 @@ fn test_block_hash_in_evm() { let l1_fee_rate = 0; evm.begin_soft_confirmation_hook( - [5u8; 32], - 1, - [42u8; 32], - &[10u8; 32], - l1_fee_rate, - 0, + &HookSoftConfirmationInfo { + da_slot_hash: [5u8; 32], + da_slot_height: 1, + da_slot_txs_commitment: [42u8; 32], + pre_state_root: [10u8; 32].to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate, + timestamp: 0, + }, &mut working_set, ); { @@ -450,12 +475,16 @@ fn test_block_hash_in_evm() { // generate 514 more blocks let l1_fee_rate = 0; evm.begin_soft_confirmation_hook( - [5u8; 32], - 1, - [42u8; 32], - &[99u8; 32], - l1_fee_rate, - 0, + &HookSoftConfirmationInfo { + da_slot_hash: [5u8; 32], + da_slot_height: 1, + da_slot_txs_commitment: [42u8; 32], + pre_state_root: [99u8; 32].to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate, + timestamp: 0, + }, &mut working_set, ); evm.end_soft_confirmation_hook(&mut working_set); @@ -533,12 +562,16 @@ fn test_block_gas_limit() { let l1_fee_rate = 0; evm.begin_soft_confirmation_hook( - [5u8; 32], - 1, - [42u8; 32], - &[10u8; 32], - l1_fee_rate, - 0, + &HookSoftConfirmationInfo { + da_slot_hash: [5u8; 32], + da_slot_height: 1, + da_slot_txs_commitment: [42u8; 32], + pre_state_root: [10u8; 32].to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate, + timestamp: 0, + }, &mut working_set, ); { @@ -800,12 +833,16 @@ fn test_l1_fee_success() { let (evm, mut working_set) = get_evm(&config); evm.begin_soft_confirmation_hook( - [5u8; 32], - 1, - [42u8; 32], - &[10u8; 32], - l1_fee_rate, - 0, + &HookSoftConfirmationInfo { + da_slot_hash: [5u8; 32], + da_slot_height: 1, + da_slot_txs_commitment: [42u8; 32], + pre_state_root: [10u8; 32].to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate, + timestamp: 0, + }, &mut working_set, ); { @@ -874,12 +911,16 @@ fn test_l1_fee_not_enough_funds() { let (evm, mut working_set) = get_evm(&config); evm.begin_soft_confirmation_hook( - [5u8; 32], - 1, - [42u8; 32], - &[10u8; 32], - l1_fee_rate, - 0, + &HookSoftConfirmationInfo { + da_slot_hash: [5u8; 32], + da_slot_height: 1, + da_slot_txs_commitment: [42u8; 32], + pre_state_root: [10u8; 32].to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate, + timestamp: 0, + }, &mut working_set, ); { diff --git a/crates/evm/src/tests/ef_tests/cases/blockchain_test.rs b/crates/evm/src/tests/ef_tests/cases/blockchain_test.rs index ed9550f80..01887ea8f 100644 --- a/crates/evm/src/tests/ef_tests/cases/blockchain_test.rs +++ b/crates/evm/src/tests/ef_tests/cases/blockchain_test.rs @@ -10,6 +10,7 @@ use rayon::iter::{ParallelBridge, ParallelIterator}; use reth_primitives::{SealedBlock, EMPTY_OMMER_ROOT_HASH}; use revm::primitives::SpecId; use sov_modules_api::default_context::DefaultContext; +use sov_modules_api::hooks::HookSoftConfirmationInfo; use sov_modules_api::utils::generate_address; use sov_modules_api::{Context, StateMapAccessor, StateValueAccessor, WorkingSet}; use sov_prover_storage_manager::SnapshotManager; @@ -62,7 +63,19 @@ impl BlockchainTestCase { ProverStorage, ) { // Call begin_soft_confirmation_hook - evm.begin_soft_confirmation_hook([0u8; 32], 0, [0u8; 32], root, 0, 0, &mut working_set); + evm.begin_soft_confirmation_hook( + &HookSoftConfirmationInfo { + da_slot_hash: [0u8; 32], + da_slot_height: 0, + da_slot_txs_commitment: [0u8; 32], + pre_state_root: root.to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate: 0, + timestamp: 0, + }, + &mut working_set, + ); let dummy_address = generate_address::("dummy"); let sequencer_address = generate_address::("sequencer"); diff --git a/crates/evm/src/tests/hooks_tests.rs b/crates/evm/src/tests/hooks_tests.rs index 0ab05cb1c..c44121b25 100644 --- a/crates/evm/src/tests/hooks_tests.rs +++ b/crates/evm/src/tests/hooks_tests.rs @@ -5,6 +5,7 @@ use reth_primitives::{ Address, Bloom, Bytes, Header, SealedHeader, Signature, TransactionSigned, B256, EMPTY_OMMER_ROOT_HASH, KECCAK_EMPTY, U256, }; +use sov_modules_api::hooks::HookSoftConfirmationInfo; use sov_modules_api::{StateMapAccessor, StateValueAccessor, StateVecAccessor}; use super::genesis_tests::{GENESIS_DA_TXS_COMMITMENT, TEST_CONFIG}; @@ -25,12 +26,16 @@ fn begin_soft_confirmation_hook_creates_pending_block() { let (evm, mut working_set) = get_evm(&TEST_CONFIG); let l1_fee_rate = 0; evm.begin_soft_confirmation_hook( - DA_ROOT_HASH.0, - 1, - [42u8; 32], - &[10u8; 32], - l1_fee_rate, - 54, + &HookSoftConfirmationInfo { + da_slot_hash: DA_ROOT_HASH.0, + da_slot_height: 1, + da_slot_txs_commitment: [42u8; 32], + pre_state_root: [10u8; 32].to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate, + timestamp: 54, + }, &mut working_set, ); let pending_block = evm.block_env.get(&mut working_set).unwrap(); @@ -56,12 +61,16 @@ fn end_soft_confirmation_hook_sets_head() { let l1_fee_rate = 0; evm.begin_soft_confirmation_hook( - DA_ROOT_HASH.0, - 1, - txs_commitment.into(), - &pre_state_root, - l1_fee_rate, - 54, + &HookSoftConfirmationInfo { + da_slot_hash: DA_ROOT_HASH.0, + da_slot_height: 1, + da_slot_txs_commitment: txs_commitment.into(), + pre_state_root: pre_state_root.to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate, + timestamp: 54, + }, &mut working_set, ); @@ -127,12 +136,16 @@ fn end_soft_confirmation_hook_moves_transactions_and_receipts() { let (evm, mut working_set) = get_evm(&TEST_CONFIG); let l1_fee_rate = 0; evm.begin_soft_confirmation_hook( - DA_ROOT_HASH.0, - 1, - [42u8; 32], - &[10u8; 32], - l1_fee_rate, - 0, + &HookSoftConfirmationInfo { + da_slot_hash: DA_ROOT_HASH.0, + da_slot_height: 1, + da_slot_txs_commitment: [42u8; 32], + pre_state_root: [10u8; 32].to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate, + timestamp: 0, + }, &mut working_set, ); @@ -228,12 +241,16 @@ fn finalize_hook_creates_final_block() { let l1_fee_rate = 0; evm.begin_soft_confirmation_hook( - [5u8; 32], - 1, - txs_commitment.into(), - root, - l1_fee_rate, - 54, + &HookSoftConfirmationInfo { + da_slot_hash: [5u8; 32], + da_slot_height: 1, + da_slot_txs_commitment: txs_commitment.into(), + pre_state_root: root.to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate, + timestamp: 54, + }, &mut working_set, ); @@ -254,12 +271,16 @@ fn finalize_hook_creates_final_block() { assert_eq!(evm.blocks.len(&mut accessory_state), 3); evm.begin_soft_confirmation_hook( - DA_ROOT_HASH.0, - 1, - txs_commitment.into(), - &root_hash, - l1_fee_rate, - 54, + &HookSoftConfirmationInfo { + da_slot_hash: DA_ROOT_HASH.0, + da_slot_height: 1, + da_slot_txs_commitment: txs_commitment.into(), + pre_state_root: root_hash.to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate, + timestamp: 54, + }, &mut working_set, ); @@ -336,12 +357,16 @@ fn begin_soft_confirmation_hook_appends_last_block_hashes() { let l1_fee_rate = 0; evm.begin_soft_confirmation_hook( - DA_ROOT_HASH.0, - 1, - txs_commitment.into(), - root, - l1_fee_rate, - 0, + &HookSoftConfirmationInfo { + da_slot_hash: DA_ROOT_HASH.0, + da_slot_height: 1, + da_slot_txs_commitment: txs_commitment.into(), + pre_state_root: root.to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate, + timestamp: 0, + }, &mut working_set, ); @@ -373,12 +398,16 @@ fn begin_soft_confirmation_hook_appends_last_block_hashes() { for _ in 2..257 { let l1_fee_rate = 0; evm.begin_soft_confirmation_hook( - DA_ROOT_HASH.0, - 1, - random_32_bytes, - &random_32_bytes, - l1_fee_rate, - 0, + &HookSoftConfirmationInfo { + da_slot_hash: DA_ROOT_HASH.0, + da_slot_height: 1, + da_slot_txs_commitment: random_32_bytes, + pre_state_root: random_32_bytes.to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate, + timestamp: 0, + }, &mut working_set, ); @@ -391,12 +420,16 @@ fn begin_soft_confirmation_hook_appends_last_block_hashes() { // start environment for block 258 let l1_fee_rate = 0; evm.begin_soft_confirmation_hook( - DA_ROOT_HASH.0, - 1, - random_32_bytes, - &random_32_bytes, - l1_fee_rate, - 0, + &HookSoftConfirmationInfo { + da_slot_hash: DA_ROOT_HASH.0, + da_slot_height: 1, + da_slot_txs_commitment: random_32_bytes, + pre_state_root: random_32_bytes.to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate, + timestamp: 0, + }, &mut working_set, ); diff --git a/crates/evm/src/tests/queries/evm_call_tests.rs b/crates/evm/src/tests/queries/evm_call_tests.rs index f23a3e2b1..a1ddb0d21 100644 --- a/crates/evm/src/tests/queries/evm_call_tests.rs +++ b/crates/evm/src/tests/queries/evm_call_tests.rs @@ -6,6 +6,7 @@ use reth_primitives::{Address, BlockNumberOrTag, Bytes, U64}; use reth_rpc::eth::error::RpcInvalidTransactionError; use reth_rpc_types::request::{TransactionInput, TransactionRequest}; use revm::primitives::U256; +use sov_modules_api::hooks::HookSoftConfirmationInfo; use sov_modules_api::WorkingSet; use super::C; @@ -73,12 +74,16 @@ fn test_state_change() { let random_address = Address::from_str("0x000000000000000000000000000000000000dead").unwrap(); evm.begin_soft_confirmation_hook( - [5u8; 32], - 1, - [42u8; 32], - &[10u8; 32], - 1, - 0, + &HookSoftConfirmationInfo { + da_slot_hash: [5u8; 32], + da_slot_height: 1, + da_slot_txs_commitment: [42u8; 32], + pre_state_root: [10u8; 32].to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate: 1, + timestamp: 0, + }, &mut working_set, ); diff --git a/crates/evm/src/tests/queries/log_tests.rs b/crates/evm/src/tests/queries/log_tests.rs index 509a41e38..d506fedbf 100644 --- a/crates/evm/src/tests/queries/log_tests.rs +++ b/crates/evm/src/tests/queries/log_tests.rs @@ -6,6 +6,7 @@ use reth_primitives::constants::ETHEREUM_BLOCK_GAS_LIMIT; use reth_primitives::BlockNumberOrTag; use revm::primitives::{B256, U256}; use sov_modules_api::default_context::DefaultContext; +use sov_modules_api::hooks::HookSoftConfirmationInfo; use sov_modules_api::utils::generate_address; use sov_modules_api::{Context, Module, StateVecAccessor}; @@ -69,12 +70,16 @@ fn log_filter_test_at_block_hash() { let (evm, mut working_set) = get_evm(&config); evm.begin_soft_confirmation_hook( - [5u8; 32], - 1, - [42u8; 32], - &[10u8; 32], - 1, - 0, + &HookSoftConfirmationInfo { + da_slot_hash: [5u8; 32], + da_slot_height: 1, + da_slot_txs_commitment: [42u8; 32], + pre_state_root: [10u8; 32].to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate: 1, + timestamp: 0, + }, &mut working_set, ); { @@ -271,12 +276,16 @@ fn log_filter_test_with_range() { let (evm, mut working_set) = get_evm(&config); evm.begin_soft_confirmation_hook( - [5u8; 32], - 1, - [42u8; 32], - &[10u8; 32], - 1, - 0, + &HookSoftConfirmationInfo { + da_slot_hash: [5u8; 32], + da_slot_height: 1, + da_slot_txs_commitment: [42u8; 32], + pre_state_root: [10u8; 32].to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate: 1, + timestamp: 0, + }, &mut working_set, ); { @@ -328,12 +337,16 @@ fn log_filter_test_with_range() { assert_eq!(rpc_logs.len(), 4); evm.begin_soft_confirmation_hook( - [5u8; 32], - 1, - [42u8; 32], - &[99u8; 32], - 1, - 0, + &HookSoftConfirmationInfo { + da_slot_hash: [5u8; 32], + da_slot_height: 1, + da_slot_txs_commitment: [42u8; 32], + pre_state_root: [99u8; 32].to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate: 1, + timestamp: 0, + }, &mut working_set, ); { @@ -385,12 +398,16 @@ fn test_log_limits() { let (evm, mut working_set) = get_evm(&config); evm.begin_soft_confirmation_hook( - [5u8; 32], - 1, - [42u8; 32], - &[10u8; 32], - 1, - 0, + &HookSoftConfirmationInfo { + da_slot_hash: [5u8; 32], + da_slot_height: 1, + da_slot_txs_commitment: [42u8; 32], + pre_state_root: [10u8; 32].to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate: 1, + timestamp: 0, + }, &mut working_set, ); { @@ -481,12 +498,16 @@ fn test_log_limits() { for _ in 1..100_001 { // generate 100_000 blocks to test the max block range limit evm.begin_soft_confirmation_hook( - [5u8; 32], - 1, - [42u8; 32], - &[99u8; 32], - 1, - 0, + &HookSoftConfirmationInfo { + da_slot_hash: [5u8; 32], + da_slot_height: 1, + da_slot_txs_commitment: [42u8; 32], + pre_state_root: [99u8; 32].to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate: 1, + timestamp: 0, + }, &mut working_set, ); evm.end_soft_confirmation_hook(&mut working_set); diff --git a/crates/evm/src/tests/queries/mod.rs b/crates/evm/src/tests/queries/mod.rs index 8ef7e87f1..d4de87ca8 100644 --- a/crates/evm/src/tests/queries/mod.rs +++ b/crates/evm/src/tests/queries/mod.rs @@ -8,6 +8,7 @@ use std::str::FromStr; use reth_primitives::{Address, Bytes}; use revm::primitives::{SpecId, KECCAK_EMPTY, U256}; use sov_modules_api::default_context::DefaultContext; +use sov_modules_api::hooks::HookSoftConfirmationInfo; use sov_modules_api::utils::generate_address; use sov_modules_api::{Context, Module, WorkingSet}; @@ -61,12 +62,16 @@ fn init_evm() -> (Evm, WorkingSet, TestSigner) { ); evm.begin_soft_confirmation_hook( - [5u8; 32], - 1, - [42u8; 32], - &[10u8; 32], - 1, - 24, + &HookSoftConfirmationInfo { + da_slot_hash: [5u8; 32], + da_slot_height: 1, + da_slot_txs_commitment: [42u8; 32], + pre_state_root: [10u8; 32].to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate: 1, + timestamp: 24, + }, &mut working_set, ); @@ -97,12 +102,16 @@ fn init_evm() -> (Evm, WorkingSet, TestSigner) { let mut working_set: WorkingSet = WorkingSet::new(prover_storage.clone()); evm.begin_soft_confirmation_hook( - [8u8; 32], - 1, - [42u8; 32], - &[99u8; 32], - 1, - 24, + &HookSoftConfirmationInfo { + da_slot_hash: [8u8; 32], + da_slot_height: 1, + da_slot_txs_commitment: [42u8; 32], + pre_state_root: [99u8; 32].to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate: 1, + timestamp: 24, + }, &mut working_set, ); @@ -134,12 +143,16 @@ fn init_evm() -> (Evm, WorkingSet, TestSigner) { let mut working_set: WorkingSet = WorkingSet::new(prover_storage.clone()); evm.begin_soft_confirmation_hook( - [10u8; 32], - 1, - [42u8; 32], - &[100u8; 32], - 1, - 24, + &HookSoftConfirmationInfo { + da_slot_hash: [10u8; 32], + da_slot_height: 1, + da_slot_txs_commitment: [42u8; 32], + pre_state_root: [100u8; 32].to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate: 1, + timestamp: 24, + }, &mut working_set, ); @@ -195,7 +208,19 @@ pub fn init_evm_single_block() -> (Evm, WorkingSet, TestSigner) { // .as_slice(), // ); - evm.begin_soft_confirmation_hook([1u8; 32], 1, [42u8; 32], &[0u8; 32], 1, 0, &mut working_set); + evm.begin_soft_confirmation_hook( + &HookSoftConfirmationInfo { + da_slot_hash: [1u8; 32], + da_slot_height: 1, + da_slot_txs_commitment: [42u8; 32], + pre_state_root: [0u8; 32].to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate: 1, + timestamp: 0, + }, + &mut working_set, + ); let simple_payable_contract_tx = create_contract_transaction(&dev_signer, 0, SimplePayableContract::default()); @@ -254,7 +279,19 @@ pub fn init_evm_with_caller_contract() -> (Evm, WorkingSet, TestSigner) { // .as_slice(), // ); - evm.begin_soft_confirmation_hook([1u8; 32], 1, [42u8; 32], &[0u8; 32], 1, 0, &mut working_set); + evm.begin_soft_confirmation_hook( + &HookSoftConfirmationInfo { + da_slot_hash: [1u8; 32], + da_slot_height: 1, + da_slot_txs_commitment: [42u8; 32], + pre_state_root: [0u8; 32].to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate: 1, + timestamp: 0, + }, + &mut working_set, + ); { let sender_address = generate_address::("sender"); @@ -281,7 +318,19 @@ pub fn init_evm_with_caller_contract() -> (Evm, WorkingSet, TestSigner) { let mut working_set: WorkingSet = WorkingSet::new(prover_storage.clone()); - evm.begin_soft_confirmation_hook([2u8; 32], 1, [42u8; 32], &[2u8; 32], 1, 0, &mut working_set); + evm.begin_soft_confirmation_hook( + &HookSoftConfirmationInfo { + da_slot_hash: [2u8; 32], + da_slot_height: 1, + da_slot_txs_commitment: [42u8; 32], + pre_state_root: [2u8; 32].to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate: 1, + timestamp: 0, + }, + &mut working_set, + ); { let sender_address = generate_address::("sender"); diff --git a/crates/evm/src/tests/sys_tx_tests.rs b/crates/evm/src/tests/sys_tx_tests.rs index 5a102d03f..ed8a0ac2c 100644 --- a/crates/evm/src/tests/sys_tx_tests.rs +++ b/crates/evm/src/tests/sys_tx_tests.rs @@ -6,6 +6,7 @@ use reth_primitives::{b256, hex, BlockNumberOrTag, Log}; use reth_rpc_types::{TransactionInput, TransactionRequest}; use revm::primitives::{Bytes, U256}; use sov_modules_api::default_context::DefaultContext; +use sov_modules_api::hooks::HookSoftConfirmationInfo; use sov_modules_api::utils::generate_address; use sov_modules_api::{Context, Module, StateMapAccessor, StateVecAccessor}; @@ -13,20 +14,17 @@ use crate::call::CallMessage; use crate::evm::primitive_types::Receipt; use crate::evm::system_contracts::BitcoinLightClient; use crate::smart_contracts::{BlockHashContract, LogsContract}; +use crate::system_contracts::Bridge; use crate::tests::call_tests::{ create_contract_message, create_contract_message_with_fee, get_evm_config_starting_base_fee, publish_event_message, }; use crate::tests::utils::get_evm; -use crate::{AccountData, SYSTEM_SIGNER}; +use crate::{AccountData, EvmConfig, SYSTEM_SIGNER}; type C = DefaultContext; -#[test] -fn test_sys_bitcoin_light_client() { - let (mut config, dev_signer, _) = - get_evm_config_starting_base_fee(U256::from_str("1000000").unwrap(), None, 1); - +fn config_push_contracts(config: &mut EvmConfig) { config.data.push(AccountData::new( BitcoinLightClient::address(), U256::ZERO, @@ -35,6 +33,22 @@ fn test_sys_bitcoin_light_client() { HashMap::new() )); + config.data.push(AccountData::new( + Bridge::address(), + U256::from_str("0x115EEC47F6CF7E35000000").unwrap(), + Bytes::from_static(&hex!("60806040526004361061019c5760003560e01c806387f8bf56116100ec578063d761753e1161008a578063e829558811610064578063e8295588146104b7578063ec6925a7146104d7578063ec732959146104f3578063f2fde38b1461052757600080fd5b8063d761753e1461044f578063dd95c7c614610477578063e30c39781461049757600080fd5b80639f963f59116100c65780639f963f59146103da578063b3ab15fb146103fa578063b93780f61461041a578063c124289c1461042f57600080fd5b806387f8bf56146103855780638da5cb5b146103a75780638e19899e146103c757600080fd5b80634ecf518b116101595780635e0e5b3e116101335780635e0e5b3e14610316578063715018a61461034657806379ba50971461035b5780637ea1b8081461037057600080fd5b80634ecf518b146102b4578063570ca735146102d857806359c19cee1461030157600080fd5b80630278b07d146101a1578063158ef93e146101d95780632b8a6d161461020b57806338bf282e1461023b5780633b60c5b61461026957806343e316871461029e575b600080fd5b3480156101ad57600080fd5b506101bc6001603160981b0181565b6040516001600160a01b0390911681526020015b60405180910390f35b3480156101e557600080fd5b506004546101fb90640100000000900460ff1681565b60405190151581526020016101d0565b34801561021757600080fd5b506101fb6102263660046128d4565b60086020526000908152604090205460ff1681565b34801561024757600080fd5b5061025b6102563660046128ed565b610547565b6040519081526020016101d0565b34801561027557600080fd5b506102896102843660046128d4565b6105ca565b60405163ffffffff90911681526020016101d0565b3480156102aa57600080fd5b5061025b60055481565b3480156102c057600080fd5b5060015461028990600160a01b900463ffffffff1681565b3480156102e457600080fd5b506004546101bc906501000000000090046001600160a01b031681565b61031461030f36600461290f565b6105d5565b005b34801561032257600080fd5b506101fb6103313660046128d4565b60096020526000908152604090205460ff1681565b34801561035257600080fd5b506103146106db565b34801561036757600080fd5b50610314610751565b34801561037c57600080fd5b5060035461025b565b34801561039157600080fd5b5061039a610817565b6040516101d091906129a8565b3480156103b357600080fd5b506000546101bc906001600160a01b031681565b6103146103d53660046128d4565b6108a5565b3480156103e657600080fd5b506103146103f5366004612a1d565b610947565b34801561040657600080fd5b50610314610415366004612aa8565b610a7a565b34801561042657600080fd5b5061039a610b0f565b34801561043b57600080fd5b5061031461044a366004612ac3565b610b1c565b34801561045b57600080fd5b506101bc73deaddeaddeaddeaddeaddeaddeaddeaddeaddead81565b34801561048357600080fd5b50610314610492366004612b68565b610d99565b3480156104a357600080fd5b506001546101bc906001600160a01b031681565b3480156104c357600080fd5b5061025b6104d23660046128d4565b611538565b3480156104e357600080fd5b5061025b670de0b6b3a764000081565b3480156104ff57600080fd5b5061025b7fcb0c9f4264546b15be9801ecb11df7e43bfc6841609fc1e4e9de5b3a5973af3881565b34801561053357600080fd5b50610314610542366004612aa8565b611b8c565b600060028383604051602001610567929190918252602082015260400190565b60408051601f198184030181529082905261058191612ba4565b602060405180830381855afa15801561059e573d6000803e3d6000fd5b5050506040513d601f19601f820116820180604052508101906105c19190612bc0565b90505b92915050565b60006105c482611c12565b6105e781670de0b6b3a7640000612bef565b34146106345760405162461bcd60e51b8152602060048201526017602482015276125b9d985b1a59081dda5d1a191c985dc8185b5bdd5b9d604a1b60448201526064015b60405180910390fd5b60005b818110156106d65761066083838381811061065457610654612c06565b905060200201356105ca565b5060045463ffffffff167f1f02f23951a2962fd940e8862c7a253adfe945910a3cd65e9e7616b1f399ddca84848481811061069d5761069d612c06565b90506020020135426040516106bc929190918252602082015260400190565b60405180910390a2806106ce81612c1c565b915050610637565b505050565b6000546001600160a01b031633146107055760405162461bcd60e51b815260040161062b90612c35565b600080546001600160a01b03191681556040805182815260208101929092527f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e0910160405180910390a1565b6001546001600160a01b031633146107ab5760405162461bcd60e51b815260206004820152601b60248201527f43616c6c6572206973206e6f742070656e64696e67206f776e65720000000000604482015260640161062b565b60008054600180546001600160a01b03198084166001600160a01b038084169190911786559116909155604080519190921680825260208201939093527f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e091015b60405180910390a150565b6007805461082490612c62565b80601f016020809104026020016040519081016040528092919081815260200182805461085090612c62565b801561089d5780601f106108725761010080835404028352916020019161089d565b820191906000526020600020905b81548152906001019060200180831161088057829003601f168201915b505050505081565b670de0b6b3a764000034146108f65760405162461bcd60e51b8152602060048201526017602482015276125b9d985b1a59081dda5d1a191c985dc8185b5bdd5b9d604a1b604482015260640161062b565b6108ff816105ca565b506004546040805183815242602082015263ffffffff909216917f1f02f23951a2962fd940e8862c7a253adfe945910a3cd65e9e7616b1f399ddca910160405180910390a250565b6000546001600160a01b031633146109715760405162461bcd60e51b815260040161062b90612c35565b806000036109c15760405162461bcd60e51b815260206004820152601a60248201527f566572696669657220636f756e742063616e6e6f742062652030000000000000604482015260640161062b565b6000849003610a125760405162461bcd60e51b815260206004820152601e60248201527f4465706f736974207363726970742063616e6e6f7420626520656d7074790000604482015260640161062b565b6006610a1f858783612d00565b506007610a2d838583612d00565b5060058190556040517f89ed79f38bee253aee2fb8d52df0d71b4aaf0843800d093a499a55eeca455c3490610a6b9087908790879087908790612dea565b60405180910390a15050505050565b6000546001600160a01b03163314610aa45760405162461bcd60e51b815260040161062b90612c35565b6004805465010000000000600160c81b031916650100000000006001600160a01b038481168281029390931793849055604080519290940416815260208101919091527ffbe5b6cbafb274f445d7fed869dc77a838d8243a22c460de156560e8857cad03910161080c565b6006805461082490612c62565b3373deaddeaddeaddeaddeaddeaddeaddeaddeaddead14610b7f5760405162461bcd60e51b815260206004820152601f60248201527f63616c6c6572206973206e6f74207468652073797374656d2063616c6c657200604482015260640161062b565b600454640100000000900460ff1615610bda5760405162461bcd60e51b815260206004820152601f60248201527f436f6e747261637420697320616c726561647920696e697469616c697a656400604482015260640161062b565b81600003610c2a5760405162461bcd60e51b815260206004820152601a60248201527f566572696669657220636f756e742063616e6e6f742062652030000000000000604482015260640161062b565b6000859003610c7b5760405162461bcd60e51b815260206004820152601e60248201527f4465706f736974207363726970742063616e6e6f7420626520656d7074790000604482015260640161062b565b6004805464ff000000001916640100000000179055610c9987611d93565b6006610ca6868883612d00565b506007610cb4848683612d00565b5060058290556004805465010000000000600160c81b03191678deaddeaddeaddeaddeaddeaddeaddeaddeaddead0000000000179055600080546001600160a01b0319166001600160a01b0383161781556040805191825273deaddeaddeaddeaddeaddeaddeaddeaddeaddead60208301527ffbe5b6cbafb274f445d7fed869dc77a838d8243a22c460de156560e8857cad03910160405180910390a17f89ed79f38bee253aee2fb8d52df0d71b4aaf0843800d093a499a55eeca455c348686868686604051610d88959493929190612dea565b60405180910390a150505050505050565b6004546501000000000090046001600160a01b03163314610dfc5760405162461bcd60e51b815260206004820152601a60248201527f63616c6c6572206973206e6f7420746865206f70657261746f72000000000000604482015260640161062b565b6000610e5a610e0e6020840184612e24565b610e1e6040850160208601612e4e565b610e2b6040860186612e78565b610e386060880188612e78565b610e4560808a018a612e78565b610e5560c08c0160a08d01612e24565b611e26565b60008181526009602052604090205490915060ff1615610eb25760405162461bcd60e51b81526020600482015260136024820152721ddd1e125908185b1c9958591e481cdc195b9d606a1b604482015260640161062b565b60008181526009602052604090819020805460ff19166001179055610f1790610edd90840184612e78565b8080601f016020809104026020016040519081016040528093929190818152602001838380828437600092019190915250611e6e92505050565b610f635760405162461bcd60e51b815260206004820152601d60248201527f56696e206973206e6f742070726f7065726c7920666f726d6174746564000000604482015260640161062b565b610fad610f736060840184612e78565b8080601f016020809104026020016040519081016040528093929190818152602001838380828437600092019190915250611f1d92505050565b610ff95760405162461bcd60e51b815260206004820152601e60248201527f566f7574206973206e6f742070726f7065726c7920666f726d61747465640000604482015260640161062b565b600061104561100b6040850185612e78565b8080601f016020809104026020016040519081016040528093929190818152602001838380828437600092019190915250611fbf92505050565b915050806001146110915760405162461bcd60e51b815260206004820152601660248201527513db9b1e481bdb99481a5b9c1d5d08185b1b1bddd95960521b604482015260640161062b565b6110dd6110a16080850185612e78565b8080601f016020809104026020016040519081016040528093929190818152602001838380828437600092019190915250859250611fd6915050565b6111335760405162461bcd60e51b815260206004820152602160248201527f5769746e657373206973206e6f742070726f7065726c7920666f726d617474656044820152601960fa1b606482015260840161062b565b6001603160981b01634ffd344a60e08501358461115360c0880188612e78565b8861010001356040518663ffffffff1660e01b8152600401611179959493929190612ebf565b602060405180830381865afa158015611196573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906111ba9190612ef1565b6112065760405162461bcd60e51b815260206004820152601b60248201527f5472616e73616374696f6e206973206e6f7420696e20626c6f636b0000000000604482015260640161062b565b60006112526112186080860186612e78565b8080601f01602080910402602001604051908101604052809392919081815260200183838082843760009201829052509250612056915050565b9050600061125f82611fbf565b91505060055460026112719190612f13565b81146112b75760405162461bcd60e51b8152602060048201526015602482015274496e76616c6964207769746e657373206974656d7360581b604482015260640161062b565b60006112c583600554612143565b90506000600680546112d690612c62565b9150600090506112e7838284612317565b905061137d81600680546112fa90612c62565b80601f016020809104026020016040519081016040528092919081815260200182805461132690612c62565b80156113735780601f1061134857610100808354040283529160200191611373565b820191906000526020600020905b81548152906001019060200180831161135657829003601f168201915b50505050506123db565b6113c25760405162461bcd60e51b8152602060048201526016602482015275125b9d985b1a590819195c1bdcda5d081cd8dc9a5c1d60521b604482015260640161062b565b60006113f16113d2846014612f13565b6113dd856014612f13565b86516113e99190612f26565b869190612317565b905061140481600780546112fa90612c62565b6114485760405162461bcd60e51b8152602060048201526015602482015274092dcecc2d8d2c840e6c6e4d2e0e840e6eaccccd2f605b1b604482015260640161062b565b6000611453856124a7565b604080518b81524260208201529192507f98e783c3864bbf744a057ef605a2a61701c3b62b5ed68b3745b99094497daf1f910160405180910390a16000816001600160a01b0316670de0b6b3a764000060405160006040518083038185875af1925050503d80600081146114e3576040519150601f19603f3d011682016040523d82523d6000602084013e6114e8565b606091505b505090508061152b5760405162461bcd60e51b815260206004820152600f60248201526e151c985b9cd9995c8819985a5b1959608a1b604482015260640161062b565b5050505050505050505050565b60008160000361156957507fcb0c9f4264546b15be9801ecb11df7e43bfc6841609fc1e4e9de5b3a5973af38919050565b8160010361159857507f455b22fd2c80e024797f8d83d31a0b6b11aa024ecffb905b1d691d657434b90a919050565b816002036115c757507f480c45bfe41828a16e4bf0bd7a1db34d2ec4d239101daf0b774821ed2dfca761919050565b816003036115f657507f29f2f8c3c9d792bd9ebdc71486151113b73af357a205dd41760f941555e26146919050565b8160040361162557507fd0fb88bcc6243bb6021b49d377e1655d1e61fb08a659b9511680f83824d64197919050565b8160050361165457507f5c7fac0890e73fb2e0d8fb3063c6786a2c63da95187efe29da4bce99d621d0ba919050565b8160060361168357507fcb08837032cc923c34faece314b3e13158b7fda962321262618d4bcc46217eb2919050565b816007036116b257507f229c0a76b756fc3db3266dc0f8e571d113ca44e0cb7326bee03d35331748091f919050565b816008036116e157507f8270abf4c13bfeb13ee8967544be4d343424fa3910ec7ad995873ca0d86daf69919050565b8160090361171057507f2d338a30d2a6bb5169df7cc8d61b6578d35568f6e1f09eda43f5bd36ad68be67919050565b81600a0361173f57507f6609db0b330090c86c349ad31f986c5f2a346461eb6f160a0e0a865d39260df6919050565b81600b0361176e57507f81861227312c9b868eb34b8cf216893c0db60b6b5c5e05f549f3ab6811b9f3d6919050565b81600c0361179d57507f1f7af2d9c7e25a85c9035abd0d8c2c7b993754a4af7250924bc55071770f75ef919050565b81600d036117cc57507f45d98c88c1c60a5d35eabe7a4cf3b2ba3bee0d8a4617f7bf485a5bd93749d3f0919050565b81600e036117fb57507f11b8807d04fe98c0bd60dec1890026baa1d83f51b37e365a45b5c87028aaf6c9919050565b81600f0361182a57507f6a43477876ca14f6d714ab184a94b3a8d324e29085646fd2bc3663427c512332919050565b8160100361185957507f2e2ca637ce5b8e8b33629f637c7fd77c7ac300ae409e64898d38b4c177280e43919050565b8160110361188857507f212db654d1d3a4e31fd8b86d3545babbf23ce592753c50936b30b1eb34d6db2a919050565b816012036118b757507f7818b4041e25a0bcd1bf0528728f20c6976f0923d5038facff21524ccd971d75919050565b816013036118e657507f538977a76a1b4557dd0e98d557d9a24d88349d83220ed84feb13c79f8ae83c7c919050565b8160140361191557507f9f3efb03c31cf43571e1e5395e2f71fcaabc491ca72631b44ec9cf99110821be919050565b8160150361194457507ffb29f69c3f45b34a9e0b7a4007a953190aa2618deef63b15ea4dd10998785734919050565b8160160361197357507f3d12f73b1f682ed24aa0b1a39df347240a74a64b5e15312466368dd943e769bc919050565b816017036119a257507f5bce4a357cef84ee3edf0669ec908843281b2d19072f58eff8d6503468b0c8d6919050565b816018036119d157507f069835ff0850f45ad28f01399d6af695a96d056589cc0ac9259e66beae87cd3c919050565b81601903611a0057507fdbdece04a4bafc538705847f0c28d441f57c7b6dbf8a803ca0e5b097857e0513919050565b81601a03611a2f57507f020d43e87ea83e8ad54ca1eb11d826a2cd75823b5f6a91a6568839b42551f727919050565b81601b03611a5e57507f19a652f1c22915bd595b81d87a7dd5cc01ba7d82ba78882949373b6220d3a504919050565b81601c03611a8d57507f4138c0097adba86ca3c19d2181a21b8e331c42c1fdb3ce8cfd953a4553279ef1919050565b81601d03611abc57507ffdc8ebd533132c3178ab8434060ae1007fc3b672fcf270d30b57f8e12ca7fa27919050565b81601e03611aeb57507ff0b266c6a0adb776bf7b9fafe1f02c99f35ba89067bcedb8f8f267002d51bceb919050565b81601f03611b1a57507f2afd595f486a771bf9653b9333d78bf101fad1f5ddb0db960c5a1450200061db919050565b81602003611b4957507f35c59abafcc58285f02e048ba62334323f15a2d2ea0a033f8df2fbee3344902d919050565b60405162461bcd60e51b8152602060048201526013602482015272496e646578206f7574206f6620626f756e647360681b604482015260640161062b565b919050565b6000546001600160a01b03163314611bb65760405162461bcd60e51b815260040161062b90612c35565b600180546001600160a01b0319166001600160a01b038381169182179092556000546040805191909316815260208101919091527fed8889f560326eb138920d842192f0eb3dd22b4f139c87a2c57538e05bae1278910161080c565b60045460015460009163ffffffff90811691611c3891600160a01b90910416600261304c565b63ffffffff168163ffffffff1603611cab5760405162461bcd60e51b815260206004820152603060248201527f4d65726b6c6520747265652069732066756c6c2e204e6f206d6f7265206c656160448201526f1d995cc818d85b88189948185919195960821b606482015260840161062b565b8083600080805b60015463ffffffff600160a01b90910481169082161015611d5d57611cd860028661307f565b63ffffffff16600003611d1657839250611cf78163ffffffff16611538565b63ffffffff821660009081526002602052604090208590559150611d32565b63ffffffff811660009081526002602052604090205492508391505b611d3c8383610547565b9350611d496002866130a2565b945080611d55816130c5565b915050611cb2565b506003839055611d6e8560016130e8565b6004805463ffffffff191663ffffffff92909216919091179055509295945050505050565b6001805463ffffffff60a01b1916600160a01b63ffffffff84160217905560005b60015463ffffffff600160a01b90910481169082161015611e0657611dde8163ffffffff16611538565b63ffffffff821660009081526002602052604090205580611dfe816130c5565b915050611db4565b50600154611e2090600160a01b900463ffffffff16611538565b60035550565b6000611e608a8a8a8a8a8a8a8a8a604051602001611e4c9998979695949392919061310c565b6040516020818303038152906040526124dd565b9a9950505050505050505050565b6000806000611e7c84611fbf565b9092509050801580611e8f575060001982145b15611e9e575060009392505050565b6000611eab836001612f13565b905060005b82811015611f105785518210611ecc5750600095945050505050565b6000611ed88784612504565b90506000198103611ef0575060009695505050505050565b611efa8184612f13565b9250508080611f0890612c1c565b915050611eb0565b5093519093149392505050565b6000806000611f2b84611fbf565b9092509050801580611f3e575060001982145b15611f4d575060009392505050565b6000611f5a836001612f13565b905060005b82811015611f105785518210611f7b5750600095945050505050565b6000611f87878461254d565b90506000198103611f9f575060009695505050505050565b611fa98184612f13565b9250508080611fb790612c1c565b915050611f5f565b600080611fcd8360006125b1565b91509150915091565b600081600003611fe8575060006105c4565b6000805b8381101561204a5784518210612007576000925050506105c4565b60006120138684612755565b9050600019810361202a57600093505050506105c4565b6120348184612f13565b925050808061204290612c1c565b915050611fec565b50835114905092915050565b606060008060005b848110156120d9576120708683612755565b925060001983036120bb5760405162461bcd60e51b815260206004820152601560248201527442616420566172496e7420696e207769746e65737360581b604482015260640161062b565b6120c58383612f13565b9150806120d181612c1c565b91505061205e565b506120e48582612755565b9150600019820361212f5760405162461bcd60e51b815260206004820152601560248201527442616420566172496e7420696e207769746e65737360581b604482015260640161062b565b61213a858284612317565b95945050505050565b606060008061215185611fbf565b9092509050600182016121b15760405162461bcd60e51b815260206004820152602260248201527f52656164206f76657272756e20647572696e6720566172496e742070617273696044820152616e6760f01b606482015260840161062b565b8084106121f35760405162461bcd60e51b815260206004820152601060248201526f2b34b7103932b0b21037bb32b9393ab760811b604482015260640161062b565b600080612201846001612f13565b905060005b868110156122965761221888836125b1565b9095509250600183016122625760405162461bcd60e51b815260206004820152601260248201527142616420566172496e7420696e206974656d60701b604482015260640161062b565b8261226e866001612f13565b6122789190612f13565b6122829083612f13565b91508061228e81612c1c565b915050612206565b506122a187826125b1565b9094509150600182016122eb5760405162461bcd60e51b815260206004820152601260248201527142616420566172496e7420696e206974656d60701b604482015260640161062b565b61230c816122f98685612f13565b612304906001612f13565b899190612317565b979650505050505050565b60608160000361233657506040805160208101909152600081526123d4565b60006123428385612f13565b90508381118015612354575080855110155b6123965760405162461bcd60e51b8152602060048201526013602482015272536c696365206f7574206f6620626f756e647360681b604482015260640161062b565b604051915082604083010160405282825283850182038460208701018481015b808210156123cf578151838301526020820191506123b6565b505050505b9392505050565b600081518351146124255760405162461bcd60e51b8152602060048201526014602482015273098cadccee8d0e640c8de40dcdee840dac2e8c6d60631b604482015260640161062b565b825160005b8181101561249c5783818151811061244457612444612c06565b602001015160f81c60f81b6001600160f81b03191685828151811061246b5761246b612c06565b01602001516001600160f81b0319161461248a576000925050506105c4565b8061249481612c1c565b91505061242a565b506001949350505050565b600080600680546124b790612c62565b9150600090506124c984836014612317565b6124d290613174565b60601c949350505050565b60006020600083516020850160025afa50602060006020600060025afa5050600051919050565b600080600061251385856127fd565b90925090506001820161252c57600019925050506105c4565b80612538836025612f13565b6125429190612f13565b61213a906004612f13565b600061255a826009612f13565b8351101561256b57506000196105c4565b6000806125828561257d866008612f13565b6125b1565b90925090506001820161259b57600019925050506105c4565b806125a7836009612f13565b61213a9190612f13565b60008060006125c0858561283f565b90508060ff166000036125f55760008585815181106125e1576125e1612c06565b016020015190935060f81c915061274e9050565b836126018260016131b0565b60ff1661260e9190612f13565b85511015612625576000196000925092505061274e565b60008160ff166002036126695761265e61264a612643876001612f13565b88906128c5565b62ffff0060e882901c1660f89190911c1790565b61ffff169050612744565b8160ff166004036126b8576126ab612685612643876001612f13565b60d881901c63ff00ff001662ff00ff60e89290921c9190911617601081811b91901c1790565b63ffffffff169050612744565b8160ff16600803612744576127376126d4612643876001612f13565b60c01c64ff000000ff600882811c91821665ff000000ff009390911b92831617601090811b67ffffffffffffffff1666ff00ff00ff00ff9290921667ff00ff00ff00ff009093169290921790911c65ffff0000ffff1617602081811c91901b1790565b67ffffffffffffffff1690505b60ff909116925090505b9250929050565b600080600061276485856125b1565b90925090506001820161277d57600019925050506105c4565b60008061278b846001612f13565b905060005b838110156127f2576127a288836125b1565b9095509250600183016127be57600019955050505050506105c4565b826127ca866001612f13565b6127d49190612f13565b6127de9083612f13565b9150806127ea81612c1c565b915050612790565b509695505050505050565b60008061280b836025612f13565b8451101561282057506000199050600061274e565b6000806128328661257d876024612f13565b9097909650945050505050565b600082828151811061285357612853612c06565b016020015160f81c60ff0361286a575060086105c4565b82828151811061287c5761287c612c06565b016020015160f81c60fe03612893575060046105c4565b8282815181106128a5576128a5612c06565b016020015160f81c60fd036128bc575060026105c4565b50600092915050565b60006105c18383016020015190565b6000602082840312156128e657600080fd5b5035919050565b6000806040838503121561290057600080fd5b50508035926020909101359150565b6000806020838503121561292257600080fd5b823567ffffffffffffffff8082111561293a57600080fd5b818501915085601f83011261294e57600080fd5b81358181111561295d57600080fd5b8660208260051b850101111561297257600080fd5b60209290920196919550909350505050565b60005b8381101561299f578181015183820152602001612987565b50506000910152565b60208152600082518060208401526129c7816040850160208701612984565b601f01601f19169190910160400192915050565b60008083601f8401126129ed57600080fd5b50813567ffffffffffffffff811115612a0557600080fd5b60208301915083602082850101111561274e57600080fd5b600080600080600060608688031215612a3557600080fd5b853567ffffffffffffffff80821115612a4d57600080fd5b612a5989838a016129db565b90975095506020880135915080821115612a7257600080fd5b50612a7f888289016129db565b96999598509660400135949350505050565b80356001600160a01b0381168114611b8757600080fd5b600060208284031215612aba57600080fd5b6105c182612a91565b600080600080600080600060a0888a031215612ade57600080fd5b873563ffffffff81168114612af257600080fd5b9650602088013567ffffffffffffffff80821115612b0f57600080fd5b612b1b8b838c016129db565b909850965060408a0135915080821115612b3457600080fd5b50612b418a828b016129db565b90955093505060608801359150612b5a60808901612a91565b905092959891949750929550565b600060208284031215612b7a57600080fd5b813567ffffffffffffffff811115612b9157600080fd5b820161012081850312156123d457600080fd5b60008251612bb6818460208701612984565b9190910192915050565b600060208284031215612bd257600080fd5b5051919050565b634e487b7160e01b600052601160045260246000fd5b80820281158282048414176105c4576105c4612bd9565b634e487b7160e01b600052603260045260246000fd5b600060018201612c2e57612c2e612bd9565b5060010190565b60208082526013908201527221b0b63632b91034b9903737ba1037bbb732b960691b604082015260600190565b600181811c90821680612c7657607f821691505b602082108103612c9657634e487b7160e01b600052602260045260246000fd5b50919050565b634e487b7160e01b600052604160045260246000fd5b601f8211156106d657600081815260208120601f850160051c81016020861015612cd95750805b601f850160051c820191505b81811015612cf857828155600101612ce5565b505050505050565b67ffffffffffffffff831115612d1857612d18612c9c565b612d2c83612d268354612c62565b83612cb2565b6000601f841160018114612d605760008515612d485750838201355b600019600387901b1c1916600186901b178355612dba565b600083815260209020601f19861690835b82811015612d915786850135825560209485019460019092019101612d71565b5086821015612dae5760001960f88860031b161c19848701351681555b505060018560011b0183555b5050505050565b81835281816020850137506000828201602090810191909152601f909101601f19169091010190565b606081526000612dfe606083018789612dc1565b8281036020840152612e11818688612dc1565b9150508260408301529695505050505050565b600060208284031215612e3657600080fd5b81356001600160e01b0319811681146123d457600080fd5b600060208284031215612e6057600080fd5b81356001600160f01b0319811681146123d457600080fd5b6000808335601e19843603018112612e8f57600080fd5b83018035915067ffffffffffffffff821115612eaa57600080fd5b60200191503681900382131561274e57600080fd5b858152846020820152608060408201526000612edf608083018587612dc1565b90508260608301529695505050505050565b600060208284031215612f0357600080fd5b815180151581146123d457600080fd5b808201808211156105c4576105c4612bd9565b818103818111156105c4576105c4612bd9565b60018163ffffffff825b80861115612f7757828204831115612f5d57612f5d612bd9565b80861615612f6a57928202925b94851c9491800291612f43565b50509250929050565b600082612f8f575060016105c4565b81612f9c575060006105c4565b8160018114612fb25760028114612fbc57612fed565b60019150506105c4565b60ff841115612fcd57612fcd612bd9565b6001841b915063ffffffff821115612fe757612fe7612bd9565b506105c4565b5060208310610133831016604e8410600b8410161715613024575081810a63ffffffff81111561301f5761301f612bd9565b6105c4565b61302e8383612f39565b8063ffffffff0482111561304457613044612bd9565b029392505050565b600063ffffffff613061818516828516612f80565b949350505050565b634e487b7160e01b600052601260045260246000fd5b600063ffffffff8084168061309657613096613069565b92169190910692915050565b600063ffffffff808416806130b9576130b9613069565b92169190910492915050565b600063ffffffff8083168181036130de576130de612bd9565b6001019392505050565b63ffffffff81811683821601908082111561310557613105612bd9565b5092915050565b6001600160e01b03198a811682526001600160f01b03198a166004830152600090888a60068501378883016006810160008152888a823750878101905060068101600081528688823750931692909301600681019290925250600a0198975050505050505050565b805160208201516bffffffffffffffffffffffff1980821692919060148310156131a85780818460140360031b1b83161693505b505050919050565b60ff81811683821601908111156105c4576105c4612bd956fea26469706673582212203d200dc92c6a08f66becf93d34dfc63eaa53be8b17c588055f28c2d27f8eeef764736f6c63430008150033")), + 0, + HashMap::new(), + )); +} + +#[test] +fn test_sys_bitcoin_light_client() { + let (mut config, dev_signer, _) = + get_evm_config_starting_base_fee(U256::from_str("1000000").unwrap(), None, 1); + + config_push_contracts(&mut config); + let (evm, mut working_set) = get_evm(&config); assert_eq!( @@ -70,6 +84,28 @@ fn test_sys_bitcoin_light_client() { log_index_start: 0, diff_size: 348, }, + Receipt { + receipt: reth_primitives::Receipt { + tx_type: reth_primitives::TxType::Eip1559, + success: true, + cumulative_gas_used: 1147965, + logs: vec![ + Log { + address: Bridge::address(), + topics: vec![b256!("fbe5b6cbafb274f445d7fed869dc77a838d8243a22c460de156560e8857cad03")], + data: Bytes::from_static(&hex!("0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000deaddeaddeaddeaddeaddeaddeaddeaddeaddead")), + }, + Log { + address: Bridge::address(), + topics: vec![b256!("89ed79f38bee253aee2fb8d52df0d71b4aaf0843800d093a499a55eeca455c34")], + data: Bytes::from_static(&hex!("00000000000000000000000000000000000000000000000000000000000000600000000000000000000000000000000000000000000000000000000000000140000000000000000000000000000000000000000000000000000000000000000500000000000000000000000000000000000000000000000000000000000000afc3203402ede68395331e2797e1d8fd2ba951386baab32d1440252c3214e0708fe479ad20c18c593480f4f55a3fd7617c9df6e3dabc80fca5927f66d20050c82a2012be7aad2089c310c07b3c3901562a3f000c4a477fcb5ebfd362de3d07a0bff927f2911301ad2067de68f8eb816c86396802b389dedec01703d79e9910e0c846f48920a3e33dd7ad2040f1506702e400b8d1aed2de05bf776e6d7602378ab0834a7d771039454af56ead51006314000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000016800000000000000000000000000000000000000000000000000000000000000")) + } + ] + }, + gas_used: 1030769, + log_index_start: 1, + diff_size: 2972, + } ] ); @@ -78,7 +114,7 @@ fn test_sys_bitcoin_light_client() { let system_account = evm.accounts.get(&SYSTEM_SIGNER, &mut working_set).unwrap(); // The system caller balance is unchanged(if exists)/or should be 0 assert_eq!(system_account.info.balance, U256::from(0)); - assert_eq!(system_account.info.nonce, 2); + assert_eq!(system_account.info.nonce, 3); let hash = evm .get_call( @@ -113,12 +149,16 @@ fn test_sys_bitcoin_light_client() { // New L1 block №2 evm.begin_soft_confirmation_hook( - [2u8; 32], - 2, - [3u8; 32], - &[10u8; 32], - l1_fee_rate, - 42, + &HookSoftConfirmationInfo { + da_slot_hash: [2u8; 32], + da_slot_height: 2, + da_slot_txs_commitment: [3u8; 32], + pre_state_root: [10u8; 32].to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate, + timestamp: 42, + }, &mut working_set, ); { @@ -144,14 +184,14 @@ fn test_sys_bitcoin_light_client() { let system_account = evm.accounts.get(&SYSTEM_SIGNER, &mut working_set).unwrap(); // The system caller balance is unchanged(if exists)/or should be 0 assert_eq!(system_account.info.balance, U256::from(0)); - assert_eq!(system_account.info.nonce, 3); + assert_eq!(system_account.info.nonce, 4); let receipts: Vec<_> = evm .receipts .iter(&mut working_set.accessory_state()) .collect(); - assert_eq!(receipts.len(), 4); // 2 from #1 L1 block and 2 from #2 block - let receipts = receipts[2..].to_vec(); + assert_eq!(receipts.len(), 5); // 3 from first L2 block + 2 from second L2 block + let receipts = receipts[3..].to_vec(); assert_eq!(receipts, [ @@ -182,7 +222,7 @@ fn test_sys_bitcoin_light_client() { gas_used: 114235, log_index_start: 1, diff_size: 477, - } + }, ] ); @@ -234,13 +274,7 @@ fn test_sys_tx_gas_usage_effect_on_block_gas_limit() { 1, ); - config.data.push(AccountData::new( - BitcoinLightClient::address(), - U256::ZERO, - Bytes::from_static(&hex!("608060405234801561001057600080fd5b50600436106100a95760003560e01c806357e871e71161007157806357e871e71461014c57806361b207e214610155578063a91d8b3d14610182578063d269a03e146101a2578063d761753e146101b5578063ee82ac5e146101e857600080fd5b80630466efc4146100ae5780630e27bc11146100e15780631f578333146100f657806334cdf78d146101095780634ffd344a14610129575b600080fd5b6100ce6100bc366004610599565b60009081526002602052604090205490565b6040519081526020015b60405180910390f35b6100f46100ef3660046105b2565b610208565b005b6100f4610104366004610599565b610331565b6100ce610117366004610599565b60016020526000908152604090205481565b61013c61013736600461061d565b6103df565b60405190151581526020016100d8565b6100ce60005481565b6100ce610163366004610599565b6000908152600160209081526040808320548352600290915290205490565b6100ce610190366004610599565b60026020526000908152604090205481565b61013c6101b036600461061d565b610405565b6101d073deaddeaddeaddeaddeaddeaddeaddeaddeaddead81565b6040516001600160a01b0390911681526020016100d8565b6100ce6101f6366004610599565b60009081526001602052604090205490565b3373deaddeaddeaddeaddeaddeaddeaddeaddeaddead146102705760405162461bcd60e51b815260206004820152601f60248201527f63616c6c6572206973206e6f74207468652073797374656d2063616c6c65720060448201526064015b60405180910390fd5b60008054908190036102b65760405162461bcd60e51b815260206004820152600f60248201526e139bdd081a5b9a5d1a585b1a5e9959608a1b6044820152606401610267565b60008181526001602081905260409091208490556102d5908290610678565b6000908155838152600260209081526040808320859055915482519081529081018590529081018390527f32eff959e2e8d1609edc4b39ccf75900aa6c1da5719f8432752963fdf008234f9060600160405180910390a1505050565b3373deaddeaddeaddeaddeaddeaddeaddeaddeaddead146103945760405162461bcd60e51b815260206004820152601f60248201527f63616c6c6572206973206e6f74207468652073797374656d2063616c6c6572006044820152606401610267565b600054156103da5760405162461bcd60e51b8152602060048201526013602482015272105b1c9958591e481a5b9a5d1a585b1a5e9959606a1b6044820152606401610267565b600055565b6000858152600160205260408120546103fb9086868686610410565b9695505050505050565b60006103fb86868686865b6000858152600260209081526040808320548151601f870184900484028101840190925285825291610463918891849190899089908190840183828082843760009201919091525089925061046e915050565b979650505050505050565b6000838514801561047d575081155b801561048857508251155b15610495575060016104a4565b6104a1858486856104ac565b90505b949350505050565b6000602084516104bc9190610699565b156104c9575060006104a4565b83516000036104da575060006104a4565b818560005b8651811015610549576104f3600284610699565b6001036105175761051061050a8883016020015190565b83610556565b9150610530565b61052d826105288984016020015190565b610556565b91505b60019290921c91610542602082610678565b90506104df565b5090931495945050505050565b6000610562838361056b565b90505b92915050565b60008260005281602052602060006040600060025afa50602060006020600060025afa505060005192915050565b6000602082840312156105ab57600080fd5b5035919050565b600080604083850312156105c557600080fd5b50508035926020909101359150565b60008083601f8401126105e657600080fd5b50813567ffffffffffffffff8111156105fe57600080fd5b60208301915083602082850101111561061657600080fd5b9250929050565b60008060008060006080868803121561063557600080fd5b8535945060208601359350604086013567ffffffffffffffff81111561065a57600080fd5b610666888289016105d4565b96999598509660600135949350505050565b8082018082111561056557634e487b7160e01b600052601160045260246000fd5b6000826106b657634e487b7160e01b600052601260045260246000fd5b50069056fea26469706673582212203f38cf5ee903bac8d195ec0eca1aa029b26a4571354479e22036d9625b2c509764736f6c63430008190033")), - 0, - HashMap::new() - )); + config_push_contracts(&mut config); let (evm, mut working_set) = get_evm(&config); let l1_fee_rate = 0; @@ -250,12 +284,16 @@ fn test_sys_tx_gas_usage_effect_on_block_gas_limit() { let context = C::new(sender_address, sequencer_address, 1); evm.begin_soft_confirmation_hook( - [5u8; 32], - 1, - [42u8; 32], - &[10u8; 32], - l1_fee_rate, - 0, + &HookSoftConfirmationInfo { + da_slot_hash: [5u8; 32], + da_slot_height: 1, + da_slot_txs_commitment: [42u8; 32], + pre_state_root: [10u8; 32].to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate: 1, + timestamp: 0, + }, &mut working_set, ); { @@ -277,12 +315,16 @@ fn test_sys_tx_gas_usage_effect_on_block_gas_limit() { evm.finalize_hook(&[99u8; 32].into(), &mut working_set.accessory_state()); evm.begin_soft_confirmation_hook( - [10u8; 32], - 2, - [43u8; 32], - &[10u8; 32], - l1_fee_rate, - 0, + &HookSoftConfirmationInfo { + da_slot_hash: [10u8; 32], + da_slot_height: 2, + da_slot_txs_commitment: [43u8; 32], + pre_state_root: [10u8; 32].to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate, + timestamp: 0, + }, &mut working_set, ); { @@ -293,6 +335,8 @@ fn test_sys_tx_gas_usage_effect_on_block_gas_limit() { let mut rlp_transactions = Vec::new(); + // Check: Given now we also push bridge contract, is the following calculation correct? + // the amount of gas left is 30_000_000 - 73581 = 29926419 // send barely enough gas to reach the limit // one publish event message is 26388 gas diff --git a/crates/evm/src/tests/utils.rs b/crates/evm/src/tests/utils.rs index fffc6419e..05a5b4e9d 100644 --- a/crates/evm/src/tests/utils.rs +++ b/crates/evm/src/tests/utils.rs @@ -2,6 +2,7 @@ use lazy_static::lazy_static; use reth_primitives::hex_literal::hex; use reth_primitives::B256; use sov_modules_api::default_context::DefaultContext; +use sov_modules_api::hooks::HookSoftConfirmationInfo; use sov_modules_api::{Module, WorkingSet}; use sov_prover_storage_manager::{new_orphan_storage, SnapshotManager}; use sov_state::{DefaultStorageSpec, ProverStorage, Storage}; @@ -54,7 +55,19 @@ pub(crate) fn get_evm(config: &EvmConfig) -> (Evm, WorkingSet) { let mut working_set: WorkingSet = WorkingSet::new(storage.clone()); evm.finalize_hook(&root.into(), &mut working_set.accessory_state()); - evm.begin_soft_confirmation_hook([1u8; 32], 1, [2u8; 32], &root, 0, 0, &mut working_set); + evm.begin_soft_confirmation_hook( + &HookSoftConfirmationInfo { + da_slot_hash: [1u8; 32], + da_slot_height: 1, + da_slot_txs_commitment: [2u8; 32], + pre_state_root: root.to_vec(), + pub_key: vec![], + deposit_data: vec![], + l1_fee_rate: 0, + timestamp: 0, + }, + &mut working_set, + ); evm.end_soft_confirmation_hook(&mut working_set); let root = commit(working_set, storage.clone()); diff --git a/crates/sequencer-client/src/lib.rs b/crates/sequencer-client/src/lib.rs index e1e3e39c9..58cc53fdc 100644 --- a/crates/sequencer-client/src/lib.rs +++ b/crates/sequencer-client/src/lib.rs @@ -81,6 +81,7 @@ pub struct GetSoftBatchResponse { pub post_state_root: Vec, #[serde(with = "hex::serde")] pub soft_confirmation_signature: Vec, + pub deposit_data: Vec, // Vec wrapper around deposit data #[serde(with = "hex::serde")] pub pub_key: Vec, pub l1_fee_rate: u64, @@ -101,6 +102,7 @@ impl From for SignedSoftConfirmationBatch { .into_iter() .map(|tx| tx.tx) .collect(), + val.deposit_data.into_iter().map(|tx| tx.tx).collect(), val.soft_confirmation_signature, val.pub_key, val.timestamp, diff --git a/crates/sequencer/src/sequencer.rs b/crates/sequencer/src/sequencer.rs index 59f123402..150482eaa 100644 --- a/crates/sequencer/src/sequencer.rs +++ b/crates/sequencer/src/sequencer.rs @@ -208,6 +208,7 @@ where da_slot_txs_commitment: da_block.header().txs_commitment().into(), pre_state_root: self.state_root.clone().as_ref().to_vec(), pub_key: self.sov_tx_signer_priv_key.pub_key().try_to_vec().unwrap(), + deposit_data: vec![], l1_fee_rate, timestamp, }; @@ -266,6 +267,7 @@ where da_block.header().txs_commitment().into(), self.state_root.clone().as_ref().to_vec(), txs, + vec![], l1_fee_rate, timestamp, ); @@ -324,6 +326,7 @@ where tx_receipts: batch_receipt.tx_receipts, soft_confirmation_signature: signed_soft_batch.signature().to_vec(), pub_key: signed_soft_batch.pub_key().to_vec(), + deposit_data: vec![], l1_fee_rate: signed_soft_batch.l1_fee_rate(), timestamp: signed_soft_batch.timestamp(), }; @@ -585,6 +588,7 @@ where soft_confirmation.pre_state_root(), soft_confirmation.l1_fee_rate(), soft_confirmation.txs(), + soft_confirmation.deposit_data(), signature.try_to_vec().unwrap(), self.sov_tx_signer_priv_key.pub_key().try_to_vec().unwrap(), soft_confirmation.timestamp(), diff --git a/crates/soft-confirmation-rule-enforcer/src/tests/hooks_tests.rs b/crates/soft-confirmation-rule-enforcer/src/tests/hooks_tests.rs index 8565c6191..1d796288e 100644 --- a/crates/soft-confirmation-rule-enforcer/src/tests/hooks_tests.rs +++ b/crates/soft-confirmation-rule-enforcer/src/tests/hooks_tests.rs @@ -43,6 +43,7 @@ fn begin_soft_confirmation_hook_checks_limiting_number() { vec![], vec![], vec![], + vec![], 10, ); @@ -76,6 +77,7 @@ fn begin_soft_confirmation_hook_checks_l1_fee_rate() { vec![], vec![], vec![], + vec![], 1, ); @@ -223,6 +225,7 @@ fn begin_soft_confirmation_hook_checks_timestamp() { vec![], vec![], vec![], + vec![], original_timestamp, ); @@ -246,6 +249,7 @@ fn begin_soft_confirmation_hook_checks_timestamp() { vec![], vec![], vec![], + vec![], original_timestamp - 1000, ); @@ -283,6 +287,7 @@ fn begin_soft_confirmation_hook_checks_timestamp() { vec![], vec![], vec![], + vec![], original_timestamp + 1000, ); diff --git a/crates/soft-confirmation-rule-enforcer/src/tests/query_tests.rs b/crates/soft-confirmation-rule-enforcer/src/tests/query_tests.rs index 622e0fe7f..c8a13050f 100644 --- a/crates/soft-confirmation-rule-enforcer/src/tests/query_tests.rs +++ b/crates/soft-confirmation-rule-enforcer/src/tests/query_tests.rs @@ -19,6 +19,7 @@ fn block_count_per_da_hash_must_be_correct() { vec![], vec![], vec![], + vec![], 0, ); // call begin_slot_hook a couple times for da hash 0 @@ -80,6 +81,7 @@ fn get_max_l1_fee_rate_change_percentage_must_be_correct() { vec![], vec![], vec![], + vec![], 0, ); @@ -121,6 +123,7 @@ fn get_last_l1_fee_rate_must_be_correct() { vec![], vec![], vec![], + vec![], 0, ); soft_confirmation_rule_enforcer @@ -162,6 +165,7 @@ fn get_last_timestamp_must_be_correct() { vec![], vec![], vec![], + vec![], timestamp, ); soft_confirmation_rule_enforcer diff --git a/crates/sovereign-sdk/full-node/db/sov-db/src/ledger_db/mod.rs b/crates/sovereign-sdk/full-node/db/sov-db/src/ledger_db/mod.rs index b326ac7cf..f5af5d6fa 100644 --- a/crates/sovereign-sdk/full-node/db/sov-db/src/ledger_db/mod.rs +++ b/crates/sovereign-sdk/full-node/db/sov-db/src/ledger_db/mod.rs @@ -247,6 +247,8 @@ impl LedgerDB { batch_receipt: SoftBatchReceipt, include_tx_body: bool, ) -> Result<(), anyhow::Error> { + let mut batch_receipt = batch_receipt; + // Create a scope to ensure that the lock is released before we commit to the db let mut current_item_numbers = { let mut next_item_numbers = self.next_item_numbers.lock().unwrap(); @@ -286,6 +288,7 @@ impl LedgerDB { // Sequencer full nodes need to store the tx body as they are the only ones that have it if !include_tx_body { tx_to_store.body = None; + batch_receipt.deposit_data = vec![]; } self.put_transaction( @@ -309,6 +312,7 @@ impl LedgerDB { post_state_root: batch_receipt.post_state_root, soft_confirmation_signature: batch_receipt.soft_confirmation_signature, pub_key: batch_receipt.pub_key, + deposit_data: batch_receipt.deposit_data, l1_fee_rate: batch_receipt.l1_fee_rate, timestamp: batch_receipt.timestamp, }; diff --git a/crates/sovereign-sdk/full-node/db/sov-db/src/schema/types.rs b/crates/sovereign-sdk/full-node/db/sov-db/src/schema/types.rs index 510293214..3f178c19c 100644 --- a/crates/sovereign-sdk/full-node/db/sov-db/src/schema/types.rs +++ b/crates/sovereign-sdk/full-node/db/sov-db/src/schema/types.rs @@ -4,7 +4,9 @@ use std::sync::Arc; use borsh::{BorshDeserialize, BorshSerialize}; use serde::de::DeserializeOwned; use serde::{Deserialize, Serialize}; -use sov_rollup_interface::rpc::{BatchResponse, SoftBatchResponse, TxIdentifier, TxResponse}; +use sov_rollup_interface::rpc::{ + BatchResponse, HexTx, SoftBatchResponse, TxIdentifier, TxResponse, +}; use sov_rollup_interface::stf::{Event, EventKey, TransactionReceipt}; /// A cheaply cloneable bytes abstraction for use within the trust boundary of the node @@ -84,6 +86,8 @@ pub struct StoredSoftBatch { pub tx_range: std::ops::Range, /// The transactions which occurred in this batch. pub txs: Vec, + /// Deposit data coming from the L1 chain + pub deposit_data: Vec>, /// Pre state root pub pre_state_root: Vec, /// Post state root @@ -121,6 +125,11 @@ impl TryFrom for SoftBatchResponse { post_state_root: value.post_state_root, soft_confirmation_signature: value.soft_confirmation_signature, pub_key: value.pub_key, + deposit_data: value + .deposit_data + .into_iter() + .map(|tx_vec| HexTx { tx: tx_vec }) + .collect(), l1_fee_rate: value.l1_fee_rate, timestamp: value.timestamp, }) diff --git a/crates/sovereign-sdk/full-node/sov-stf-runner/src/runner.rs b/crates/sovereign-sdk/full-node/sov-stf-runner/src/runner.rs index 97207c4f7..125228816 100644 --- a/crates/sovereign-sdk/full-node/sov-stf-runner/src/runner.rs +++ b/crates/sovereign-sdk/full-node/sov-stf-runner/src/runner.rs @@ -466,6 +466,11 @@ where tx_receipts: batch_receipt.tx_receipts, soft_confirmation_signature: soft_batch.soft_confirmation_signature, pub_key: soft_batch.pub_key, + deposit_data: soft_batch + .deposit_data + .into_iter() + .map(|x| x.tx) + .collect(), l1_fee_rate: soft_batch.l1_fee_rate, timestamp: soft_batch.timestamp, }; @@ -836,6 +841,7 @@ where tx_receipts: batch_receipt.tx_receipts, soft_confirmation_signature: soft_batch.soft_confirmation_signature, pub_key: soft_batch.pub_key, + deposit_data: soft_batch.deposit_data.into_iter().map(|x| x.tx).collect(), l1_fee_rate: soft_batch.l1_fee_rate, timestamp: soft_batch.timestamp, }; diff --git a/crates/sovereign-sdk/module-system/sov-modules-api/src/hooks.rs b/crates/sovereign-sdk/module-system/sov-modules-api/src/hooks.rs index c4c77fdc0..4456d06c3 100644 --- a/crates/sovereign-sdk/module-system/sov-modules-api/src/hooks.rs +++ b/crates/sovereign-sdk/module-system/sov-modules-api/src/hooks.rs @@ -125,6 +125,8 @@ pub struct HookSoftConfirmationInfo { pub pre_state_root: Vec, /// Public key of signer pub pub_key: Vec, + /// Deposit data from the L1 chain + pub deposit_data: Vec>, /// L1 fee rate pub l1_fee_rate: u64, /// Timestamp @@ -139,6 +141,7 @@ impl From for HookSoftConfirmationInfo { da_slot_txs_commitment: signed_soft_confirmation_batch.da_slot_txs_commitment(), pre_state_root: signed_soft_confirmation_batch.pre_state_root(), pub_key: signed_soft_confirmation_batch.sequencer_pub_key().to_vec(), + deposit_data: signed_soft_confirmation_batch.deposit_data(), l1_fee_rate: signed_soft_confirmation_batch.l1_fee_rate(), timestamp: signed_soft_confirmation_batch.timestamp(), } @@ -156,6 +159,7 @@ impl From for SignedSoftConfirmationBatch { val.l1_fee_rate, vec![], vec![], + vec![], val.pub_key.clone(), val.timestamp, ) @@ -188,6 +192,10 @@ impl HookSoftConfirmationInfo { self.try_to_vec().unwrap() } + pub fn deposit_data(&self) -> Vec> { + self.deposit_data.clone() + } + pub fn l1_fee_rate(&self) -> u64 { self.l1_fee_rate } diff --git a/crates/sovereign-sdk/module-system/sov-modules-stf-blueprint/src/lib.rs b/crates/sovereign-sdk/module-system/sov-modules-stf-blueprint/src/lib.rs index 84170bde5..5b78dc713 100644 --- a/crates/sovereign-sdk/module-system/sov-modules-stf-blueprint/src/lib.rs +++ b/crates/sovereign-sdk/module-system/sov-modules-stf-blueprint/src/lib.rs @@ -586,6 +586,7 @@ fn verify_soft_batch_signature( soft_batch.da_slot_txs_commitment(), soft_batch.pre_state_root(), soft_batch.txs(), + soft_batch.deposit_data(), soft_batch.l1_fee_rate(), soft_batch.timestamp(), ); diff --git a/crates/sovereign-sdk/rollup-interface/src/node/rpc/mod.rs b/crates/sovereign-sdk/rollup-interface/src/node/rpc/mod.rs index 079bbcc63..5a5232865 100644 --- a/crates/sovereign-sdk/rollup-interface/src/node/rpc/mod.rs +++ b/crates/sovereign-sdk/rollup-interface/src/node/rpc/mod.rs @@ -207,6 +207,8 @@ pub struct SoftBatchResponse { /// Public key of the signer #[serde(with = "hex::serde")] pub pub_key: Vec, + /// Deposit data from the L1 chain + pub deposit_data: Vec, // Vec wrapper around deposit data /// Base layer fee rate sats/wei etc. per byte. pub l1_fee_rate: u64, /// Sequencer's block timestamp. diff --git a/crates/sovereign-sdk/rollup-interface/src/state_machine/soft_confirmation.rs b/crates/sovereign-sdk/rollup-interface/src/state_machine/soft_confirmation.rs index f07800085..9c9950b23 100644 --- a/crates/sovereign-sdk/rollup-interface/src/state_machine/soft_confirmation.rs +++ b/crates/sovereign-sdk/rollup-interface/src/state_machine/soft_confirmation.rs @@ -16,11 +16,13 @@ pub struct UnsignedSoftConfirmationBatch { da_slot_txs_commitment: [u8; 32], pre_state_root: Vec, txs: Vec>, + deposit_data: Vec>, l1_fee_rate: u64, timestamp: u64, } impl UnsignedSoftConfirmationBatch { + #[allow(clippy::too_many_arguments)] /// Creates a new unsigned soft confirmation batch pub fn new( da_slot_height: u64, @@ -28,6 +30,7 @@ impl UnsignedSoftConfirmationBatch { da_slot_txs_commitment: [u8; 32], pre_state_root: Vec, txs: Vec>, + deposit_data: Vec>, l1_fee_rate: u64, timestamp: u64, ) -> Self { @@ -37,6 +40,7 @@ impl UnsignedSoftConfirmationBatch { da_slot_txs_commitment, pre_state_root, txs, + deposit_data, l1_fee_rate, timestamp, } @@ -61,6 +65,10 @@ impl UnsignedSoftConfirmationBatch { pub fn txs(&self) -> Vec> { self.txs.clone() } + /// Deposit data from L1 chain + pub fn deposit_data(&self) -> Vec> { + self.deposit_data.clone() + } /// Base layer fee rate sats/wei etc. per byte. pub fn l1_fee_rate(&self) -> u64 { self.l1_fee_rate @@ -83,6 +91,7 @@ pub struct SignedSoftConfirmationBatch { l1_fee_rate: u64, txs: Vec>, signature: Vec, + deposit_data: Vec>, pub_key: Vec, timestamp: u64, } @@ -98,6 +107,7 @@ impl SignedSoftConfirmationBatch { pre_state_root: Vec, l1_fee_rate: u64, txs: Vec>, + deposit_data: Vec>, signature: Vec, pub_key: Vec, timestamp: u64, @@ -110,6 +120,7 @@ impl SignedSoftConfirmationBatch { pre_state_root, l1_fee_rate, txs, + deposit_data, signature, pub_key, timestamp, @@ -151,6 +162,11 @@ impl SignedSoftConfirmationBatch { self.txs.clone() } + /// Deposit data + pub fn deposit_data(&self) -> Vec> { + self.deposit_data.clone() + } + /// Signature of the sequencer pub fn signature(&self) -> Vec { self.signature.clone() diff --git a/crates/sovereign-sdk/rollup-interface/src/state_machine/stf.rs b/crates/sovereign-sdk/rollup-interface/src/state_machine/stf.rs index 269410355..dee9b05fc 100644 --- a/crates/sovereign-sdk/rollup-interface/src/state_machine/stf.rs +++ b/crates/sovereign-sdk/rollup-interface/src/state_machine/stf.rs @@ -99,6 +99,8 @@ pub struct SoftBatchReceipt pub soft_confirmation_signature: Vec, /// Sequencer public key pub pub_key: Vec, + /// Deposit data from the L1 chain + pub deposit_data: Vec>, /// Base layer fee rate sats/wei etc. per byte. pub l1_fee_rate: u64, /// Sequencer's block timestamp