diff --git a/Cargo.lock b/Cargo.lock index 3ba948241..50b11631c 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -2778,6 +2778,7 @@ dependencies = [ "dc-inflation", "dc-types", "ethabi", + "fp-evm", "frame-benchmarking", "frame-support", "frame-system", diff --git a/pallet/deposit/Cargo.toml b/pallet/deposit/Cargo.toml index 97b929656..2a55fcfcf 100644 --- a/pallet/deposit/Cargo.toml +++ b/pallet/deposit/Cargo.toml @@ -19,6 +19,9 @@ darwinia-staking-traits = { workspace = true } dc-inflation = { workspace = true } dc-types = { workspace = true } +# frontier +fp-evm = { workspace = true } + # polkadot-sdk frame-support = { workspace = true } frame-system = { workspace = true } @@ -49,6 +52,9 @@ std = [ "darwinia-staking-traits/std", "dc-inflation/std", + # frontier + "fp-evm/std", + # polkadot-sdk "frame-support/std", "frame-system/std", diff --git a/pallet/deposit/src/lib.rs b/pallet/deposit/src/lib.rs index e096478c8..5a740937a 100644 --- a/pallet/deposit/src/lib.rs +++ b/pallet/deposit/src/lib.rs @@ -49,6 +49,8 @@ use ethabi::{Function, Param, ParamType, StateMutability, Token}; // darwinia use dc_inflation::MILLISECS_PER_YEAR; use dc_types::{Balance, Moment}; +// frontier +use fp_evm::{CallOrCreateInfo, ExitReason}; // polkadot-sdk use frame_support::{ pallet_prelude::*, @@ -136,6 +138,10 @@ pub mod pallet { DepositNotInUse, /// Deposit is already expired. DepositAlreadyExpired, + /// Invalid deposit contract. + InvalidDepositContract, + /// Migration interaction with deposit contract failed. + MigrationFailedOnContract, } /// All deposits. @@ -335,7 +341,7 @@ pub mod pallet { T::Ring::transfer(&account_id(), &who, to_claim.0, AllowDeath)?; T::Ring::transfer(&account_id(), &T::Treasury::get(), to_migrate.0, AllowDeath)?; - T::DepositMigrator::migrate(who.clone(), to_migrate.0, to_migrate.2); + T::DepositMigrator::migrate(who.clone(), to_migrate.0, to_migrate.2)?; Self::deposit_event(Event::DepositsClaimed { owner: who.clone(), @@ -458,7 +464,9 @@ where T: Config, { /// Migrate to contract. - fn migrate(_: T::AccountId, _: Balance, _: Vec<(Balance, Moment, Moment)>) {} + fn migrate(_: T::AccountId, _: Balance, _: Vec<(Balance, Moment, Moment)>) -> DispatchResult { + Ok(()) + } } impl MigrateToContract for () where T: Config {} @@ -484,16 +492,14 @@ where T: Config + darwinia_ethtx_forwarder::Config, T::AccountId: Into, { - fn migrate(who: T::AccountId, total: Balance, deposits: Vec<(Balance, Moment, Moment)>) { - let Some(dc) = >::get() else { - log::error!("deposit contract must be some; qed"); - - return; - }; - let dc = dc.into(); - + fn migrate( + who: T::AccountId, + total: Balance, + deposits: Vec<(Balance, Moment, Moment)>, + ) -> DispatchResult { + let dc = >::get().ok_or(>::InvalidDepositContract)?.into(); #[allow(deprecated)] - darwinia_ethtx_forwarder::quick_forward_transact::( + let exit_reason = match darwinia_ethtx_forwarder::quick_forward_transact::( T::Treasury::get().into(), Function { name: "migrate".into(), @@ -535,7 +541,17 @@ where dc, total.into(), 1_000_000.into(), - ) + )? + .1 + { + CallOrCreateInfo::Call(i) => i.exit_reason, + CallOrCreateInfo::Create(i) => i.exit_reason, + }; + + match exit_reason { + ExitReason::Succeed(_) => Ok(()), + _ => Err(>::MigrationFailedOnContract)?, + } } } diff --git a/pallet/ethtx-forwarder/src/lib.rs b/pallet/ethtx-forwarder/src/lib.rs index 0f01756f2..6ff411df7 100644 --- a/pallet/ethtx-forwarder/src/lib.rs +++ b/pallet/ethtx-forwarder/src/lib.rs @@ -33,10 +33,16 @@ use ethereum::{ use scale_info::TypeInfo; // frontier use fp_ethereum::{TransactionData, ValidatedTransaction}; -use fp_evm::{CheckEvmTransaction, CheckEvmTransactionConfig, TransactionValidationError}; +use fp_evm::{ + CallOrCreateInfo, CheckEvmTransaction, CheckEvmTransactionConfig, TransactionValidationError, +}; use pallet_evm::{FeeCalculator, GasWeightMapping, Runner}; // polkadot-sdk -use frame_support::{dispatch::DispatchResultWithPostInfo, traits::EnsureOrigin, PalletError}; +use frame_support::{ + dispatch::{DispatchErrorWithPostInfo, DispatchResultWithPostInfo, PostDispatchInfo}, + traits::EnsureOrigin, + PalletError, +}; use sp_core::{Get, H160, H256, U256}; use sp_runtime::{ traits::{BadOrigin, UniqueSaturatedInto}, @@ -121,7 +127,7 @@ pub mod pallet { origin: OriginFor, request: ForwardRequest, ) -> DispatchResultWithPostInfo { - Self::forward_transact_inner(ensure_forward_transact(origin)?, request) + Self::forward_transact_inner(ensure_forward_transact(origin)?, request).map(|(r, _)| r) } } } @@ -150,19 +156,19 @@ impl Pallet { None, ::config(), ) - .map_err(|err| err.error.into()) + .map_err(|e| e.error.into()) } pub fn forward_transact_inner( source: H160, request: ForwardRequest, - ) -> DispatchResultWithPostInfo { + ) -> Result<(PostDispatchInfo, CallOrCreateInfo), DispatchErrorWithPostInfo> { let transaction = Self::validated_transaction(source, request)?; #[cfg(feature = "evm-tracing")] return Self::trace_tx(source, transaction); #[cfg(not(feature = "evm-tracing"))] - return T::ValidatedTransaction::apply(source, transaction).map(|(post_info, _)| post_info); + return T::ValidatedTransaction::apply(source, transaction); } fn validated_transaction( @@ -280,51 +286,65 @@ impl Pallet { } #[cfg(feature = "evm-tracing")] - fn trace_tx(source: H160, transaction: Transaction) -> DispatchResultWithPostInfo { + fn trace_tx( + source: H160, + transaction: Transaction, + ) -> Result<(PostDispatchInfo, CallOrCreateInfo), DispatchErrorWithPostInfo> { + // frontier + use fp_evm::{CallInfo, ExitSucceed, UsedGas}; // moonbeam use moonbeam_evm_tracer::tracer::EvmTracer; // polkadot-sdk - use frame_support::{dispatch::PostDispatchInfo, storage::unhashed}; + use frame_support::storage::unhashed; use xcm_primitives::{EthereumXcmTracingStatus, ETHEREUM_XCM_TRACING_STORAGE_KEY}; + let default_r = || { + Ok(( + ().into(), + CallOrCreateInfo::Call(CallInfo { + exit_reason: ExitSucceed::Returned.into(), + value: Default::default(), + used_gas: UsedGas { + standard: Default::default(), + effective: Default::default(), + }, + weight_info: Default::default(), + logs: Default::default(), + }), + )) + }; + match unhashed::get(ETHEREUM_XCM_TRACING_STORAGE_KEY) { Some(EthereumXcmTracingStatus::Block) => { EvmTracer::emit_new(); - let mut res = Ok(PostDispatchInfo::default()); + let mut r = default_r(); EvmTracer::new().trace(|| { - res = T::ValidatedTransaction::apply(source, transaction) - .map(|(post_info, _)| post_info); + r = T::ValidatedTransaction::apply(source, transaction); }); - res + r }, Some(EthereumXcmTracingStatus::Transaction(traced_transaction_hash)) => { if transaction.hash() == traced_transaction_hash { - let mut res = Ok(PostDispatchInfo::default()); + let mut r = default_r(); EvmTracer::new().trace(|| { - res = T::ValidatedTransaction::apply(source, transaction) - .map(|(post_info, _)| post_info); + r = T::ValidatedTransaction::apply(source, transaction); }); unhashed::put::( ETHEREUM_XCM_TRACING_STORAGE_KEY, &EthereumXcmTracingStatus::TransactionExited, ); - res + r } else { T::ValidatedTransaction::apply(source, transaction) - .map(|(post_info, _)| post_info) } }, - Some(EthereumXcmTracingStatus::TransactionExited) => Ok(PostDispatchInfo { - actual_weight: None, - pays_fee: frame_support::pallet_prelude::Pays::No, - }), - None => - T::ValidatedTransaction::apply(source, transaction).map(|(post_info, _)| post_info), + Some(EthereumXcmTracingStatus::TransactionExited) => default_r(), + None => T::ValidatedTransaction::apply(source, transaction), } } } @@ -386,19 +406,17 @@ pub fn quick_forward_transact( call: H160, value: U256, gas_limit: U256, -) where +) -> Result<(PostDispatchInfo, CallOrCreateInfo), DispatchError> +where T: Config, { log::info!("forwarding {function:?} to {call:?} with {{ input: {input:?}, value: {value:?} }}"); - let input = match function.encode_input(input) { - Ok(i) => i, - Err(e) => { - log::error!("failed to encode input due to {e:?}"); + let input = function.encode_input(input).map_err(|e| { + log::error!("failed to encode input due to {e:?}"); - return; - }, - }; + DispatchError::from("failed to encode input") + })?; let req = ForwardRequest { tx_type: TxType::LegacyTransaction, action: TransactionAction::Call(call), @@ -407,7 +425,5 @@ pub fn quick_forward_transact( gas_limit, }; - if let Err(e) = >::forward_transact_inner(source, req) { - log::error!("failed to forward ethtx due to {e:?}"); - } + >::forward_transact_inner(source, req).map_err(|e| e.error) } diff --git a/pallet/staking/src/lib.rs b/pallet/staking/src/lib.rs index 53af7c9cc..8447b777c 100644 --- a/pallet/staking/src/lib.rs +++ b/pallet/staking/src/lib.rs @@ -1283,7 +1283,7 @@ where let rsc = rsc.into(); #[allow(deprecated)] - darwinia_ethtx_forwarder::quick_forward_transact::( + if let Err(e) = darwinia_ethtx_forwarder::quick_forward_transact::( ::Treasury::get().into(), Function { name: "distributeReward".into(), @@ -1300,7 +1300,9 @@ where rsc, amount.into(), 1_000_000.into(), - ); + ) { + log::error!("failed to forward call due to {e:?}"); + } } } @@ -1323,7 +1325,7 @@ where let ksc = ksc.into(); #[allow(deprecated)] - darwinia_ethtx_forwarder::quick_forward_transact::( + if let Err(e) = darwinia_ethtx_forwarder::quick_forward_transact::( ::Treasury::get().into(), Function { name: "distributeRewards".into(), @@ -1340,7 +1342,9 @@ where ksc, amount.into(), 1_000_000.into(), - ); + ) { + log::error!("failed to forward call due to {e:?}"); + } } }