diff --git a/frame/balances/src/lib.rs b/frame/balances/src/lib.rs index cfbbde4..6a321cd 100644 --- a/frame/balances/src/lib.rs +++ b/frame/balances/src/lib.rs @@ -1390,6 +1390,12 @@ impl, I: 'static> Currency for Pallet where if amount.is_zero() { return Ok(()) } let min_balance = Self::account(who).frozen(reasons.into()); ensure!(new_balance >= min_balance, Error::::LiquidityRestrictions); + + // SBP M2 review: You may want to extract this logic in a custom CurrencyAdapter + // (to be used on the Transaction Payment pallet's OnChargeTransaction param) + // This would be implemented in the withdraw_fee function, accessing state from + // a custom pallet (e.g. account_limits), before calling the Currency withdraw function. + // This would obviate the need for maintaining a local fork of the FRAME balances pallet ;) match reasons { WithdrawReasons::TRANSFER => { if amount.is_zero() { return Ok(()) } diff --git a/pallets/validator-set/src/lib.rs b/pallets/validator-set/src/lib.rs index d514804..ff945a1 100644 --- a/pallets/validator-set/src/lib.rs +++ b/pallets/validator-set/src/lib.rs @@ -8,6 +8,12 @@ #![cfg_attr(not(feature = "std"), no_std)] +// SBP M2 review: Just want to emphasize that this pallet is an example of an approach +// for handling a dynamic validator set, but this has not gone through the same thorough +// quality review process that the FRAME library has. +// As stated in the README: this code not audited and reviewed for production use cases. +// You can expect bugs and security vulnerabilities. Do not use it as-is in real applications. + use sp_std::prelude::*; use frame_support::{ StorageValue, diff --git a/runtime/src/lib.rs b/runtime/src/lib.rs index 5f52bdd..33a5cda 100644 --- a/runtime/src/lib.rs +++ b/runtime/src/lib.rs @@ -51,7 +51,7 @@ pub use frame_support::{ ConsensusEngineId, }; use pallet_evm::{ - Account as EVMAccount, FeeCalculator, HashedAddressMapping, + Account as EVMAccount, FeeCalculator, EnsureAddressTruncated, Runner, }; use fp_rpc::{TransactionStatus}; @@ -367,6 +367,34 @@ impl FeeCalculator for FixedGasPrice { } } +pub struct LookupAddressMapping(sp_std::marker::PhantomData); + +impl pallet_evm::AddressMapping for LookupAddressMapping +where + AccountId32: Clone + From<::AccountId>, +{ + fn into_account_id(address: H160) -> AccountId32 { + // SBP M2: would be best to have an option to match on Some | None + let account = pallet_account_service::Module::::from_ethereum( + &AccountServiceEnum::Ethereum(address.to_fixed_bytes()), + ) + .into(); + let account_id = if account == AccountId32::new([0u8; 32]) { + // SBP M2: is this case for L2 address that haven't been bound to an L1 address ? + // What's the rationale for _not_ using a hash here ? + // Maybe you could just fallback to the evm pallet's HashedAddressMapping. + let mut data = [0u8; 32]; + data[0..4].copy_from_slice(b"evm:"); + data[4..24].copy_from_slice(&address[..]); + // let hash = H::hash(&data); + AccountId32::new(data) + } else { + account + }; + account_id + } +} + parameter_types! { pub const ChainId: u64 = 1140; } @@ -376,7 +404,7 @@ impl pallet_evm::Config for Runtime { type GasWeightMapping = (); type CallOrigin = EnsureAddressTruncated; type WithdrawOrigin = EnsureAddressTruncated; - type AddressMapping = HashedAddressMapping; + type AddressMapping = LookupAddressMapping; type Currency = Balances; type Event = Event; type Runner = pallet_evm::runner::stack::Runner;